diff --git a/.classpath b/.classpath new file mode 100644 index 0000000..5363e0b --- /dev/null +++ b/.classpath @@ -0,0 +1,20 @@ + + + + + + + + + + + + + + + + + + + + diff --git a/.gradle/5.6.3/executionHistory/executionHistory.bin b/.gradle/5.6.3/executionHistory/executionHistory.bin new file mode 100644 index 0000000..e1c2ea5 Binary files /dev/null and b/.gradle/5.6.3/executionHistory/executionHistory.bin differ diff --git a/.gradle/5.6.3/executionHistory/executionHistory.lock b/.gradle/5.6.3/executionHistory/executionHistory.lock new file mode 100644 index 0000000..48ae257 Binary files /dev/null and b/.gradle/5.6.3/executionHistory/executionHistory.lock differ diff --git a/.gradle/5.6.3/fileChanges/last-build.bin b/.gradle/5.6.3/fileChanges/last-build.bin new file mode 100644 index 0000000..f76dd23 Binary files /dev/null and b/.gradle/5.6.3/fileChanges/last-build.bin differ diff --git a/.gradle/5.6.3/fileContent/fileContent.lock b/.gradle/5.6.3/fileContent/fileContent.lock new file mode 100644 index 0000000..f0b2fdc Binary files /dev/null and b/.gradle/5.6.3/fileContent/fileContent.lock differ diff --git a/.gradle/5.6.3/fileHashes/fileHashes.bin b/.gradle/5.6.3/fileHashes/fileHashes.bin new file mode 100644 index 0000000..774f62f Binary files /dev/null and b/.gradle/5.6.3/fileHashes/fileHashes.bin differ diff --git a/.gradle/5.6.3/fileHashes/fileHashes.lock b/.gradle/5.6.3/fileHashes/fileHashes.lock new file mode 100644 index 0000000..74d97f2 Binary files /dev/null and b/.gradle/5.6.3/fileHashes/fileHashes.lock differ diff --git a/.gradle/5.6.3/gc.properties b/.gradle/5.6.3/gc.properties new file mode 100644 index 0000000..e69de29 diff --git a/.gradle/5.6.3/javaCompile/javaCompile.lock b/.gradle/5.6.3/javaCompile/javaCompile.lock new file mode 100644 index 0000000..0c4d516 Binary files /dev/null and b/.gradle/5.6.3/javaCompile/javaCompile.lock differ diff --git a/.gradle/5.6.3/javaCompile/taskHistory.bin b/.gradle/5.6.3/javaCompile/taskHistory.bin new file mode 100644 index 0000000..ee0fcb8 Binary files /dev/null and b/.gradle/5.6.3/javaCompile/taskHistory.bin differ diff --git a/.gradle/buildOutputCleanup/buildOutputCleanup.lock b/.gradle/buildOutputCleanup/buildOutputCleanup.lock new file mode 100644 index 0000000..c9f695e Binary files /dev/null and b/.gradle/buildOutputCleanup/buildOutputCleanup.lock differ diff --git a/.gradle/buildOutputCleanup/cache.properties b/.gradle/buildOutputCleanup/cache.properties new file mode 100644 index 0000000..0a62c99 --- /dev/null +++ b/.gradle/buildOutputCleanup/cache.properties @@ -0,0 +1,2 @@ +#Wed May 25 11:46:18 CST 2022 +gradle.version=5.6.3 diff --git a/.gradle/buildOutputCleanup/outputFiles.bin b/.gradle/buildOutputCleanup/outputFiles.bin new file mode 100644 index 0000000..30da95d Binary files /dev/null and b/.gradle/buildOutputCleanup/outputFiles.bin differ diff --git a/.gradle/vcs-1/gc.properties b/.gradle/vcs-1/gc.properties new file mode 100644 index 0000000..e69de29 diff --git a/.project b/.project new file mode 100644 index 0000000..5bace34 --- /dev/null +++ b/.project @@ -0,0 +1,47 @@ + + + TBMS + + + + + + org.eclipse.jdt.core.javabuilder + + + + + org.eclipse.wst.common.project.facet.core.builder + + + + + org.eclipse.wst.validation.validationbuilder + + + + + org.eclipse.buildship.core.gradleprojectbuilder + + + + + + org.eclipse.jdt.core.javanature + org.eclipse.wst.common.project.facet.core.nature + org.eclipse.wst.common.modulecore.ModuleCoreNature + org.eclipse.jem.workbench.JavaEMFNature + org.eclipse.buildship.core.gradleprojectnature + + + + 0 + + 30 + + org.eclipse.core.resources.regexFilterMatcher + node_modules|.git|__CREATED_BY_JAVA_LANGUAGE_SERVER__ + + + + diff --git a/a-clean-deploy-2fi-db.bat b/a-clean-deploy-2fi-db.bat new file mode 100644 index 0000000..22c339e --- /dev/null +++ b/a-clean-deploy-2fi-db.bat @@ -0,0 +1,8 @@ +@echo off +copy /Y src\main\webapp\WEB-INF\classes\log4j.properties.prod src\main\webapp\WEB-INF\classes\log4j.properties +copy /Y src\main\webapp\WEB-INF\app.properties.local src\main\webapp\WEB-INF\app.properties +copy /Y src\main\webapp\META-INF\context.xml.2fi src\main\webapp\META-INF\context.xml +call a-clean-undeploy +call gradlew clean war +copy build\libs\%PROJECT_NAME%.war "%TC_BASE%\webapps" +call on \ No newline at end of file diff --git a/a-clean-deploy-local-db.bat b/a-clean-deploy-local-db.bat new file mode 100644 index 0000000..b68eb38 --- /dev/null +++ b/a-clean-deploy-local-db.bat @@ -0,0 +1,8 @@ +@echo off +copy /Y src\main\webapp\WEB-INF\classes\log4j.properties.prod src\main\webapp\WEB-INF\classes\log4j.properties +copy /Y src\main\webapp\WEB-INF\app.properties.local src\main\webapp\WEB-INF\app.properties +copy /Y src\main\webapp\META-INF\context.xml.local src\main\webapp\META-INF\context.xml +call a-clean-undeploy +call gradlew clean war +copy build\libs\%PROJECT_NAME%.war "%TC_BASE%\webapps" +call on \ No newline at end of file diff --git a/a-clean-undeploy.bat b/a-clean-undeploy.bat new file mode 100644 index 0000000..f2ac783 --- /dev/null +++ b/a-clean-undeploy.bat @@ -0,0 +1,6 @@ +@echo off +call setenv +call off +del "%TC_BASE%\webapps\%PROJECT_NAME%.war" +rd /s /q "%TC_BASE%\webapps\%PROJECT_NAME%" +rd /s /q "%TC_BASE%\work\Catalina\localhost\%PROJECT_NAME%" \ No newline at end of file diff --git a/a-create-war-for-prod.bat b/a-create-war-for-prod.bat new file mode 100644 index 0000000..785dd4f --- /dev/null +++ b/a-create-war-for-prod.bat @@ -0,0 +1,5 @@ +@echo off +copy /Y src\main\webapp\WEB-INF\classes\log4j.properties.prod src\main\webapp\WEB-INF\classes\log4j.properties +copy /Y src\main\webapp\WEB-INF\app.properties.prod src\main\webapp\WEB-INF\app.properties +copy /Y src\main\webapp\META-INF\context.xml.2fi src\main\webapp\META-INF\context.xml +call gradlew clean war \ No newline at end of file diff --git a/build.gradle b/build.gradle new file mode 100644 index 0000000..1e141c4 --- /dev/null +++ b/build.gradle @@ -0,0 +1,89 @@ +apply plugin: 'java' +apply plugin: 'eclipse' +apply plugin: 'war' + +sourceCompatibility = 11 +targetCompatibility = 11 + +tasks.withType(JavaCompile) { + options.encoding = 'UTF-8' +} + +repositories { + jcenter() + mavenCentral() + maven { + url 'http://jaspersoft.jfrog.io/jaspersoft/third-party-ce-artifacts/' + } +} + +war { + archiveName = 'tbms.war' + classpath = classpath - sourceSets.main.output + from (jar) { + into 'WEB-INF/lib' + } +} + +dependencies { + + // for JDK 11 + compile 'javax.xml.bind:jaxb-api:2.3.1' + compile 'javax.annotation:javax.annotation-api:1.3.2' + compile 'com.sun.activation:javax.activation:1.2.0' + + compile 'org.springframework:spring-context:4.3.14.RELEASE' + compile 'org.springframework:spring-context-support:4.3.14.RELEASE' + compile 'org.springframework:spring-orm:4.3.14.RELEASE' + compile 'org.springframework:spring-webmvc:4.3.14.RELEASE' + + compile 'org.springframework.security:spring-security-config:4.2.3.RELEASE' + compile 'org.springframework.security:spring-security-web:4.2.3.RELEASE' + + compile 'org.apache.commons:commons-lang3:3.5' + compile 'commons-fileupload:commons-fileupload:1.3.2' + compile 'org.apache.poi:poi:3.17' + compile 'org.apache.poi:poi-ooxml:3.17' + + compile 'org.freemarker:freemarker:2.3.23' + + compile 'org.hibernate:hibernate-core:5.2.12.Final' + compile 'org.hibernate.javax.persistence:hibernate-jpa-2.1-api:1.0.2.Final' + + compile 'com.fasterxml.jackson.core:jackson-core:2.8.8' + compile 'com.fasterxml.jackson.core:jackson-annotations:2.8.8' + compile 'com.fasterxml.jackson.core:jackson-databind:2.8.8.1' + + compile 'org.imgscalr:imgscalr-lib:4.2' + + compile(group: 'net.sf.jasperreports', name: 'jasperreports', version:'6.5.1') { + exclude(module: 'bcmail-jdk14') + exclude(module: 'bcprov-jdk14') + exclude(module: 'bctsp-jdk14') + exclude(module: 'castor-xml') + exclude(module: 'jackson-core') + exclude(module: 'jackson-annotations') + exclude(module: 'jackson-databind') + exclude(module: 'lucene-core') + exclude(module: 'lucene-analyzers-common') + exclude(module: 'lucene-queryparser') + exclude(module: 'olap4j') + } + + //providedCompile 'org.slf4j:slf4j-api:1.7.25' + //providedCompile 'org.slf4j:slf4j-log4j12:1.7.25' + + providedCompile 'javax.servlet:javax.servlet-api:3.1.0' + providedCompile 'mysql:mysql-connector-java:8.0.15' + + //testCompile 'junit:junit:4.12' + + compile 'com.google.zxing:javase:3.2.1' + + //mail + compile 'javax.mail:mail:1.4.7' + compile group: 'org.liquibase', name: 'liquibase-core', version: '3.5.3' + + fileTree(dir: 'lib', include: '*.jar') + +} diff --git a/conf/schema/schema_update.sql b/conf/schema/schema_update.sql new file mode 100644 index 0000000..c98eda4 --- /dev/null +++ b/conf/schema/schema_update.sql @@ -0,0 +1,295 @@ +-- anna 20/03/2020 +-- + +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('MEETING_MAINTAIN', 'Meeting', 'Maintain Meeting'); +INSERT INTO `tbmsdb`.`users_authorities` (`userId`, `authority`) VALUES ('1', 'MEETING_MAINTAIN'); +ALTER TABLE `tbmsdb`.`meeting` CHANGE COLUMN `datetime` `date` DATE NOT NULL ; + +-- anna 23/03/2020 +-- +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('ORDER_MAINTAIN', 'order', 'Maintain order'); +UPDATE `tbmsdb`.`authorities` SET `module`='customer' WHERE `authority`='CUSTOMER_MAINTAIN'; +UPDATE `tbmsdb`.`authorities` SET `module`='meeting' WHERE `authority`='MEETING_MAINTAIN'; +INSERT INTO `tbmsdb`.`users_authorities` (`userId`, `authority`) VALUES ('1', 'ORDER_MAINTAIN'); +ALTER TABLE `tbmsdb`.`order` RENAME TO `tbmsdb`.`orders` ; + +-- anna 31/03/2020 +-- + +ALTER TABLE `tbmsdb`.`orders` +ADD COLUMN `refNo` VARCHAR(100) NULL DEFAULT NULL AFTER `ref`; + +-- anna 07/04/2020 +-- + +ALTER TABLE `tbmsdb`.`files` +ADD COLUMN `skey` VARCHAR(16) NOT NULL AFTER `description`; + +-- anna 09/04/2020 +-- + +ALTER TABLE `tbmsdb`.`customer` +ADD COLUMN `companyName` VARCHAR(255) NULL AFTER `phone2`; + +-- anna 14/04/2020 +-- +ALTER TABLE `tbmsdb`.`customer` +CHANGE COLUMN `surname` `surname` VARCHAR(255) NULL DEFAULT NULL , +CHANGE COLUMN `firstName` `firstName` VARCHAR(255) NULL DEFAULT NULL ; + +-- anna 11/05/2020 +-- + +ALTER TABLE `tbmsdb`.`orders` +ADD INDEX `cust_order` (`id` ASC, `custId` ASC); +ALTER TABLE `tbmsdb`.`orders` +ADD INDEX `order_ref` (`id` ASC, `ref` ASC); +ALTER TABLE `tbmsdb`.`customer` +ADD INDEX `cust_ref` (`id` ASC, `ref` ASC); + +-- anna 15/05/2020 +-- + +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`, `description`) VALUES ('AMOUNT_REMIND', 'order', 'Order Amount Remind', NULL); + +DROP TABLE IF EXISTS `audit_log`; +CREATE TABLE `audit_log` ( + `tableName` varchar(30) NOT NULL, + `recordId` int(11) NOT NULL, + `modifiedBy` int(11) DEFAULT NULL, + `modified` datetime DEFAULT NULL, + `oldData` json DEFAULT NULL, + `newData` json DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=utf8; + + +-- anna 28/05/2020 +ALTER TABLE `tbmsdb`.`meeting` +CHANGE COLUMN `date` `date` DATETIME NOT NULL ; + + +-- Matthew +-- 09/06/2020 +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('ORDER_CANCEL', 'order', 'Order Cancel'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('MEETING_DELETE', 'meeting', 'Meeting Delete'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('CUSTOMER_DELETE', 'customer', 'Customer Delete'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('FILE_DELETE', 'file', 'File Delete'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('PAYMENT_REPORT', 'report', 'Payment Report Auth'); + +-- Jason Lam +-- 10/06/2020 +ALTER TABLE `tbmsdb`.`orders` +ADD COLUMN `outDate` DATE NULL AFTER `status`, +ADD COLUMN `outRemark` VARCHAR(255) NULL AFTER `outDate`, +ADD COLUMN `inDate` DATE NULL AFTER `outRemark`, +ADD COLUMN `inRemark` VARCHAR(255) NULL AFTER `inDate`; + +--Jason Lam +--11/06/2020 +ALTER TABLE `tbmsdb`.`orders` +ADD COLUMN `ignore` TINYINT(1) '0' AFTER `inRemark`; +ALTER TABLE `tbmsdb`.`orders` +CHANGE COLUMN `ignore` `ignoreC` TINYINT(1) NULL DEFAULT '0' ; + + +-- anna +-- 15/06/2020 +ALTER TABLE `tbmsdb`.`audit_log` +DROP COLUMN `oldData`, +CHANGE COLUMN `newData` `dataStr` JSON NULL DEFAULT NULL , +ADD COLUMN `actionStr` VARCHAR(255) NULL DEFAULT NULL AFTER `modified`, +ADD COLUMN `refId` INT(11) NULL DEFAULT NULL AFTER `dataStr`, +ADD COLUMN `refType` VARCHAR(255) NULL DEFAULT NULL AFTER `refId`; + +-- anna +-- 23/06/2020 +ALTER TABLE `tbmsdb`.`orders` +ADD COLUMN `workshopStatus` INT(11) NULL DEFAULT NULL AFTER `ignoreC`; + + +-- anna +-- 29/06/2020 + +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('ORDER_ITEM_DELETE', 'order', 'Order Item Delete'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('PAYMENT_DELETE', 'order', 'Payment Delete'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('WORKSHOP_MAINTAIN', 'workshop', 'Maintain Workshop'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('CALENDAR_VIEW', 'calendar', 'View Calendar'); + + +-- anna +-- 13/07/2020 +ALTER TABLE `tbmsdb`.`orders` +ADD COLUMN `targetCompleteDate` DATE NULL DEFAULT NULL AFTER `workshopStatus`; + +-- anna +-- 21/07/2020 +ALTER TABLE `tbmsdb`.`customer` +ADD COLUMN `tag` VARCHAR(255) NULL DEFAULT NULL AFTER `ref`; + +-- matthew +-- 07/09/2020 +INSERT INTO `tbmsdb`.`settings` (`name`, `value`) VALUES ('JS.version', '1'); + + +-- anna +-- 01/12/2020 +ALTER TABLE `tbmsdb`.`meeting` +ADD COLUMN `staffName` VARCHAR(45) NULL DEFAULT NULL AFTER `remarks`; + +ALTER TABLE `tbmsdb`.`orders` +ADD COLUMN `inStatus` INT(11) NULL DEFAULT NULL AFTER `targetCompleteDate`, +ADD COLUMN `outStatus` INT(11) NULL DEFAULT NULL AFTER `inStatus`; + +-- anna +-- 10/06/2021 +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('MATERIAL_MAINTAIN', 'price_list', 'Maintain Material'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('BAND_DELETE', 'price_list', 'Delete Band'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('VIEW_EXPECTED_PRICE', 'price_list', 'View Expected Price'); + +-- anna +-- 29/06/2021 +INSERT INTO `tbmsdb`.`settings` (`name`, `value`) VALUES ('MAIL.temp.subject', '[INVOICE] Order No.: {$orderNo}'); + +-- anna +-- 06/07/2021 +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('MATERIAL_MAIL_TEMPLATE', 'setup', 'Maintain Mail Template'); +INSERT INTO `tbmsdb`.`authorities` (`authority`, `module`, `name`) VALUES ('PRICE_LIST_VIEW', 'price_list', 'View Price List'); +UPDATE `tbmsdb`.`authorities` SET `authority`='PRICE_LIST_MAINTAIN', `name`='Maintain Price List' WHERE `authority`='MATERIAL_MAINTAIN'; + +-- anna +-- 19/07/2021 +CREATE TABLE `material_band` ( + `id` int(11) NOT NULL AUTO_INCREMENT, + `versionId` mediumint(8) unsigned NOT NULL DEFAULT '0', + `deleted` tinyint(1) NOT NULL DEFAULT '0', + `createdBy` int(11) DEFAULT NULL, + `modifiedBy` int(11) DEFAULT NULL, + `created` datetime DEFAULT NULL, + `modified` datetime DEFAULT NULL, + `name` varchar(255) NOT NULL, + `fileId` int(11) DEFAULT NULL, + `expectedPriceFormula` varchar(255) DEFAULT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8; + +CREATE TABLE `material_item` ( + `id` int(11) NOT NULL AUTO_INCREMENT, + `versionId` mediumint(8) unsigned NOT NULL DEFAULT '0', + `deleted` tinyint(1) NOT NULL DEFAULT '0', + `createdBy` int(11) DEFAULT NULL, + `modifiedBy` int(11) DEFAULT NULL, + `created` datetime DEFAULT NULL, + `modified` datetime DEFAULT NULL, + `bandId` int(11) DEFAULT NULL, + `name` varchar(255) DEFAULT NULL, + `bunch` varchar(255) DEFAULT NULL, + `itemNo` varchar(255) DEFAULT NULL, + `cost` decimal(18,4) DEFAULT '0.0000', + `suitPrice` decimal(18,4) DEFAULT NULL, + `jacketPrice` decimal(18,4) DEFAULT NULL, + `overcoatPrice` decimal(18,4) DEFAULT NULL, + `pantsPrice` decimal(18,4) DEFAULT NULL, + `otherPrice` decimal(18,4) DEFAULT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB AUTO_INCREMENT=22 DEFAULT CHARSET=utf8; + +-- anna +-- 10/01/2022 + +ALTER TABLE `tbmsdb`.`material_item` +ADD COLUMN `fabricNum` VARCHAR(255) NULL DEFAULT NULL AFTER `bunch`; + +-- anna +-- 4/03/2022 + +ALTER TABLE `tbmsdb`.`material_item` +ADD COLUMN `orderIdx` INT(11) NOT NULL DEFAULT 0 AFTER `otherPrice`; + +CREATE TABLE `user_settings` ( + `userId` int(11) NOT NULL, + `name` varchar(255) NOT NULL, + `value` varchar(1000) DEFAULT NULL, + `category` varchar(50) DEFAULT NULL, + `type` varchar(45) DEFAULT NULL, + PRIMARY KEY (`userId`,`name`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8; + +-- anna +-- 22/03/2022 + +CREATE TABLE `sys_groups` ( + `id` int(11) NOT NULL AUTO_INCREMENT, + `deleted` tinyint(1) NOT NULL, + `versionId` mediumint(8) unsigned NOT NULL, + `created` datetime DEFAULT NULL, + `createdBy` int(11) DEFAULT NULL, + `modified` datetime DEFAULT NULL, + `modifiedBy` int(11) DEFAULT NULL, + `name` varchar(50) NOT NULL, + `description` varchar(255) DEFAULT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8; + +ALTER TABLE `tbmsdb`.`groups` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`users` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`customer` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`files` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`files_blob` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`files_ref` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`material_band` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`material_item` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`meeting` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`order_item` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`orders` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`payment` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +ALTER TABLE `tbmsdb`.`message` +ADD COLUMN `sysGroupId` INT(11) NOT NULL DEFAULT 0 AFTER `id`; + +-- anna +-- 18/05/2022 + +ALTER TABLE `tbmsdb`.`sys_groups` +ADD COLUMN `mailBody` TEXT NULL DEFAULT NULL AFTER `description`, +ADD COLUMN `mailSubject` TEXT NULL DEFAULT NULL AFTER `mailBody`; + +ALTER TABLE `tbmsdb`.`sys_groups` +ADD COLUMN `companyName` VARCHAR(255) NULL DEFAULT NULL AFTER `mailSubject`, +ADD COLUMN `phone` VARCHAR(255) NULL DEFAULT NULL AFTER `companyName`, +ADD COLUMN `fax` VARCHAR(255) NULL DEFAULT NULL AFTER `phone`, +ADD COLUMN `email` VARCHAR(255) NULL DEFAULT NULL AFTER `fax`, +ADD COLUMN `address` VARCHAR(500) NULL DEFAULT NULL AFTER `email`; + +-- anna +-- 23/05/2022 + +ALTER TABLE `tbmsdb`.`sys_groups` +ADD COLUMN `smtp_host` VARCHAR(255) NULL DEFAULT NULL AFTER `address`, +ADD COLUMN `smtp_port` VARCHAR(5) NULL DEFAULT NULL AFTER `smtp_host`, +ADD COLUMN `smtp_username` VARCHAR(255) NULL DEFAULT NULL AFTER `smtp_port`, +ADD COLUMN `smtp_password` VARCHAR(255) NULL DEFAULT NULL AFTER `smtp_username`; + + diff --git a/conf/schema/trigger.sql b/conf/schema/trigger.sql new file mode 100644 index 0000000..b3b95c0 --- /dev/null +++ b/conf/schema/trigger.sql @@ -0,0 +1,12 @@ +-- +-- ON stock_ledger INSERT: SET part.balance = stock_ledger.balance +-- +DROP TRIGGER IF EXISTS `tbmsdb`.`stock_ledger_AFTER_INSERT`; + +DELIMITER $$ +USE `tbmsdb`$$ +CREATE DEFINER = `root`@`localhost` TRIGGER `tbmsdb`.`stock_ledger_AFTER_INSERT` AFTER INSERT ON `stock_ledger` FOR EACH ROW +BEGIN + UPDATE `part` SET `balance` = NEW.`balance` WHERE `id` = NEW.`partId`; +END$$ +DELIMITER ; diff --git a/conf/schema/truncate.sql b/conf/schema/truncate.sql new file mode 100644 index 0000000..10abb17 --- /dev/null +++ b/conf/schema/truncate.sql @@ -0,0 +1,6 @@ +-- SET FOREIGN_KEY_CHECKS=0; + +-- TRUNCATE `job`; + + +-- SET FOREIGN_KEY_CHECKS=1; \ No newline at end of file diff --git a/copy-js.sh b/copy-js.sh new file mode 100644 index 0000000..25fa15e --- /dev/null +++ b/copy-js.sh @@ -0,0 +1,3 @@ +#!/bin/bash +source ./setenv.sh +cp -r src/main/webapp/resources/js/* ${tc_instance}/webapps/sms/resources/js/ \ No newline at end of file diff --git a/create-resources-link.bat b/create-resources-link.bat new file mode 100644 index 0000000..3c1a638 --- /dev/null +++ b/create-resources-link.bat @@ -0,0 +1,3 @@ +@ECHO OFF +rd /S /Q C:\Tomcat\webapps\tbms\resources +mklink /J C:\Tomcat\webapps\tbms\resources C:\workspace\TBMS\src\main\webapp\resources diff --git a/deploy.sh b/deploy.sh new file mode 100644 index 0000000..edbdd62 --- /dev/null +++ b/deploy.sh @@ -0,0 +1,4 @@ +#!/bin/bash +bash ./undeploy.sh +bash ./publish.sh +bash ./on.sh \ No newline at end of file diff --git a/docs/SMS Functions.docx b/docs/SMS Functions.docx new file mode 100644 index 0000000..50d290a --- /dev/null +++ b/docs/SMS Functions.docx @@ -0,0 +1,47 @@ + Manage Master Data + Vendor + Equipment Type + Equipment + Equipment Part + Equipment and Parts relation + + Manage Preventive Maintenance (PM) Plan + Setup Preventive Maintenance Plan + Equipment + Plan name and description (e.g. checklist) + Frequency (e.g. Daily, Weekly, Monthly, Yearly) + Resp. Team/Person + Preferred timeslot (or Shift) + Preferred day of week (e.g. Monday, Tuesday) + Time required to perform the PM + Support file attachments + Provide daily and upcoming pending PM plan (i.e. Pending to do list) + Display all the details above, plus Last Performed Date + Upon PM completion, maintenance staff will create Service Log to record, then PM plan is completed (by matching Service Log with corresponding PM plan) + Incident Log should be created if any issues found during PM + + Manage Incident + Search Incident Logs + Create/Edit Incident Logs + Support file attachments + If part replacement is required, it's used as the base for Part Stock Out + + Manage Problem + Search Problem Logs + Create/Edit Problem Logs + Support linking to related Incident Logs + Support file attachments + + Manage Parts Inventory + Stock In/Out and Adjustment + Search Parts + Create/Edit Parts + Support re-order level, can filter list of parts that the balance is below re-order level + Support First-In-First-Out for Stock Out ??? + Parts I/O Ledger + + Android App + View PM Plans + Input Service and Incident Logs + Receive Incident service requests + diff --git a/docs/SMS Schema.xlsx b/docs/SMS Schema.xlsx new file mode 100644 index 0000000..a817dc6 Binary files /dev/null and b/docs/SMS Schema.xlsx differ diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties new file mode 100644 index 0000000..f04d6a2 --- /dev/null +++ b/gradle/wrapper/gradle-wrapper.properties @@ -0,0 +1,5 @@ +distributionBase=GRADLE_USER_HOME +distributionPath=wrapper/dists +distributionUrl=https\://services.gradle.org/distributions/gradle-5.6.3-bin.zip +zipStoreBase=GRADLE_USER_HOME +zipStorePath=wrapper/dists diff --git a/gradlew b/gradlew new file mode 100644 index 0000000..b0d6d0a --- /dev/null +++ b/gradlew @@ -0,0 +1,188 @@ +#!/usr/bin/env sh + +# +# Copyright 2015 the original author or authors. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +############################################################################## +## +## Gradle start up script for UN*X +## +############################################################################## + +# Attempt to set APP_HOME +# Resolve links: $0 may be a link +PRG="$0" +# Need this for relative symlinks. +while [ -h "$PRG" ] ; do + ls=`ls -ld "$PRG"` + link=`expr "$ls" : '.*-> \(.*\)$'` + if expr "$link" : '/.*' > /dev/null; then + PRG="$link" + else + PRG=`dirname "$PRG"`"/$link" + fi +done +SAVED="`pwd`" +cd "`dirname \"$PRG\"`/" >/dev/null +APP_HOME="`pwd -P`" +cd "$SAVED" >/dev/null + +APP_NAME="Gradle" +APP_BASE_NAME=`basename "$0"` + +# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' + +# Use the maximum available, or set MAX_FD != -1 to use that value. +MAX_FD="maximum" + +warn () { + echo "$*" +} + +die () { + echo + echo "$*" + echo + exit 1 +} + +# OS specific support (must be 'true' or 'false'). +cygwin=false +msys=false +darwin=false +nonstop=false +case "`uname`" in + CYGWIN* ) + cygwin=true + ;; + Darwin* ) + darwin=true + ;; + MINGW* ) + msys=true + ;; + NONSTOP* ) + nonstop=true + ;; +esac + +CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar + +# Determine the Java command to use to start the JVM. +if [ -n "$JAVA_HOME" ] ; then + if [ -x "$JAVA_HOME/jre/sh/java" ] ; then + # IBM's JDK on AIX uses strange locations for the executables + JAVACMD="$JAVA_HOME/jre/sh/java" + else + JAVACMD="$JAVA_HOME/bin/java" + fi + if [ ! -x "$JAVACMD" ] ; then + die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." + fi +else + JAVACMD="java" + which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." +fi + +# Increase the maximum file descriptors if we can. +if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then + MAX_FD_LIMIT=`ulimit -H -n` + if [ $? -eq 0 ] ; then + if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then + MAX_FD="$MAX_FD_LIMIT" + fi + ulimit -n $MAX_FD + if [ $? -ne 0 ] ; then + warn "Could not set maximum file descriptor limit: $MAX_FD" + fi + else + warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" + fi +fi + +# For Darwin, add options to specify how the application appears in the dock +if $darwin; then + GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" +fi + +# For Cygwin, switch paths to Windows format before running java +if $cygwin ; then + APP_HOME=`cygpath --path --mixed "$APP_HOME"` + CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` + JAVACMD=`cygpath --unix "$JAVACMD"` + + # We build the pattern for arguments to be converted via cygpath + ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` + SEP="" + for dir in $ROOTDIRSRAW ; do + ROOTDIRS="$ROOTDIRS$SEP$dir" + SEP="|" + done + OURCYGPATTERN="(^($ROOTDIRS))" + # Add a user-defined pattern to the cygpath arguments + if [ "$GRADLE_CYGPATTERN" != "" ] ; then + OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" + fi + # Now convert the arguments - kludge to limit ourselves to /bin/sh + i=0 + for arg in "$@" ; do + CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` + CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option + + if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition + eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` + else + eval `echo args$i`="\"$arg\"" + fi + i=$((i+1)) + done + case $i in + (0) set -- ;; + (1) set -- "$args0" ;; + (2) set -- "$args0" "$args1" ;; + (3) set -- "$args0" "$args1" "$args2" ;; + (4) set -- "$args0" "$args1" "$args2" "$args3" ;; + (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; + (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; + (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; + (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; + (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; + esac +fi + +# Escape application args +save () { + for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done + echo " " +} +APP_ARGS=$(save "$@") + +# Collect all arguments for the java command, following the shell quoting and substitution rules +eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS" + +# by default we should be in the correct project dir, but when run from Finder on Mac, the cwd is wrong +if [ "$(uname)" = "Darwin" ] && [ "$HOME" = "$PWD" ]; then + cd "$(dirname "$0")" +fi + +exec "$JAVACMD" "$@" diff --git a/gradlew.bat b/gradlew.bat new file mode 100644 index 0000000..9991c50 --- /dev/null +++ b/gradlew.bat @@ -0,0 +1,100 @@ +@rem +@rem Copyright 2015 the original author or authors. +@rem +@rem Licensed under the Apache License, Version 2.0 (the "License"); +@rem you may not use this file except in compliance with the License. +@rem You may obtain a copy of the License at +@rem +@rem http://www.apache.org/licenses/LICENSE-2.0 +@rem +@rem Unless required by applicable law or agreed to in writing, software +@rem distributed under the License is distributed on an "AS IS" BASIS, +@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +@rem See the License for the specific language governing permissions and +@rem limitations under the License. +@rem + +@if "%DEBUG%" == "" @echo off +@rem ########################################################################## +@rem +@rem Gradle startup script for Windows +@rem +@rem ########################################################################## + +@rem Set local scope for the variables with windows NT shell +if "%OS%"=="Windows_NT" setlocal + +set DIRNAME=%~dp0 +if "%DIRNAME%" == "" set DIRNAME=. +set APP_BASE_NAME=%~n0 +set APP_HOME=%DIRNAME% + +@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m" + +@rem Find java.exe +if defined JAVA_HOME goto findJavaFromJavaHome + +set JAVA_EXE=java.exe +%JAVA_EXE% -version >NUL 2>&1 +if "%ERRORLEVEL%" == "0" goto init + +echo. +echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:findJavaFromJavaHome +set JAVA_HOME=%JAVA_HOME:"=% +set JAVA_EXE=%JAVA_HOME%/bin/java.exe + +if exist "%JAVA_EXE%" goto init + +echo. +echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:init +@rem Get command-line arguments, handling Windows variants + +if not "%OS%" == "Windows_NT" goto win9xME_args + +:win9xME_args +@rem Slurp the command line arguments. +set CMD_LINE_ARGS= +set _SKIP=2 + +:win9xME_args_slurp +if "x%~1" == "x" goto execute + +set CMD_LINE_ARGS=%* + +:execute +@rem Setup the command line + +set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar + +@rem Execute Gradle +"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS% + +:end +@rem End local scope for the variables with windows NT shell +if "%ERRORLEVEL%"=="0" goto mainEnd + +:fail +rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of +rem the _cmd.exe /c_ return code! +if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 +exit /b 1 + +:mainEnd +if "%OS%"=="Windows_NT" endlocal + +:omega diff --git a/off.bat b/off.bat new file mode 100644 index 0000000..6b6d231 --- /dev/null +++ b/off.bat @@ -0,0 +1,3 @@ +@echo off +sc stop Tomcat8 +ping 127.0.0.1 > nul \ No newline at end of file diff --git a/off.sh b/off.sh new file mode 100644 index 0000000..04dffa1 --- /dev/null +++ b/off.sh @@ -0,0 +1,3 @@ +#!/bin/bash +source ./setenv.sh +bash ${tc_instance}/bin/catalina.sh stop >> /dev/null 2>&1 \ No newline at end of file diff --git a/on.bat b/on.bat new file mode 100644 index 0000000..579e90c --- /dev/null +++ b/on.bat @@ -0,0 +1,2 @@ +@echo off +sc start Tomcat8 \ No newline at end of file diff --git a/on.sh b/on.sh new file mode 100644 index 0000000..638de19 --- /dev/null +++ b/on.sh @@ -0,0 +1,3 @@ +#!/bin/bash +source ./setenv.sh +bash ${tc_instance}/bin/catalina.sh start >> /dev/null 2>&1 \ No newline at end of file diff --git a/prod.sh b/prod.sh new file mode 100644 index 0000000..1ca39a1 --- /dev/null +++ b/prod.sh @@ -0,0 +1,5 @@ +#!/bin/bash +cp src/main/webapp/WEB-INF/classes/log4j.properties.prod src/main/webapp/WEB-INF/classes/log4j.properties +cp src/main/webapp/WEB-INF/app.properties.prod src/main/webapp/WEB-INF/app.properties +rm -rf src/main/webapp/META-INF/context.xml +bash ./gradlew clean war diff --git a/publish.sh b/publish.sh new file mode 100644 index 0000000..af9a192 --- /dev/null +++ b/publish.sh @@ -0,0 +1,12 @@ +#!/bin/bash +source ./setenv.sh +cp src/main/webapp/WEB-INF/classes/log4j.properties.local.mac src/main/webapp/WEB-INF/classes/log4j.properties +cp src/main/webapp/WEB-INF/app.properties.local.mac src/main/webapp/WEB-INF/app.properties +cp src/main/webapp/META-INF/context.xml.2fi src/main/webapp/META-INF/context.xml + + +#mvn clean package +#cp target/*.war ${tc_instance}/webapps/ + +bash ./gradlew clean war +cp build/libs/*.war ${tc_instance}/webapps/ \ No newline at end of file diff --git a/setenv.bat b/setenv.bat new file mode 100644 index 0000000..e0fb510 --- /dev/null +++ b/setenv.bat @@ -0,0 +1,3 @@ +@echo off +set PROJECT_NAME=tbms +set TC_BASE=C:\Tomcat \ No newline at end of file diff --git a/setenv.sh b/setenv.sh new file mode 100644 index 0000000..eb183ec --- /dev/null +++ b/setenv.sh @@ -0,0 +1,2 @@ +project=tbms +tc_instance=/Users/2fiadmin/tomcat \ No newline at end of file diff --git a/settings.gradle b/settings.gradle new file mode 100644 index 0000000..d2ee3fa --- /dev/null +++ b/settings.gradle @@ -0,0 +1 @@ +rootProject.name = 'TBMS' \ No newline at end of file diff --git a/src/main/java/com/ffii/core/BaseEntity.java b/src/main/java/com/ffii/core/BaseEntity.java new file mode 100644 index 0000000..81d87a4 --- /dev/null +++ b/src/main/java/com/ffii/core/BaseEntity.java @@ -0,0 +1,135 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core; + +import java.io.Serializable; +import java.util.Date; + +import javax.persistence.Column; +import javax.persistence.GeneratedValue; +import javax.persistence.GenerationType; +import javax.persistence.Id; +import javax.persistence.MappedSuperclass; +import javax.persistence.Version; + +@MappedSuperclass +public abstract class BaseEntity implements Serializable, Cloneable { + + private static final long serialVersionUID = -7211267047474252631L; + + @Id + @GeneratedValue(strategy = GenerationType.IDENTITY) + private PK id; + + @Column(columnDefinition = "int(11)") + private Integer sysGroupId; + + @Version + @Column(columnDefinition = "mediumint unsigned", nullable = false) + private int versionId; // hibernate optimistic lock version id + + @Column(columnDefinition = "boolean", nullable = false) + private boolean deleted; // defaults to false + + @Column(updatable = false) + private Integer createdBy; // User ID that created this record + + @Column + private Integer modifiedBy; // User ID that last modified this record + + @Column(updatable = false, nullable = false) + private Date created; // date created + + @Column(nullable = false) + private Date modified; // last modified date + + /** Default constructor */ + public BaseEntity() { + + } + + /* + * implements Cloneable + */ + @Override + protected Object clone() throws CloneNotSupportedException { + BaseEntity clone = (BaseEntity) super.clone(); + clone.id = null; + return clone; + } + + /* + * getters and setters + */ + public PK getId() { + return id; + } + + @SuppressWarnings("unchecked") + public void setId(Serializable id) { + this.id = (PK) id; + } + + public int getVersionId() { + return versionId; + } + + public void setVersionId(int versionId) { + this.versionId = versionId; + } + + public boolean isDeleted() { + return deleted; + } + + public void setDeleted(boolean deleted) { + this.deleted = deleted; + } + + public Integer getCreatedBy() { + return createdBy; + } + + public void setCreatedBy(Integer createdBy) { + this.createdBy = createdBy; + } + + public Integer getModifiedBy() { + return modifiedBy; + } + + public void setModifiedBy(Integer modifiedBy) { + this.modifiedBy = modifiedBy; + } + + public Date getCreated() { + return created; + } + + public void setCreated(Date created) { + this.created = created; + } + + public Date getModified() { + return modified; + } + + public void setModified(Date modified) { + this.modified = modified; + } + + public Integer getSysGroupId() { + return sysGroupId; + } + + public void setSysGroupId(Integer sysGroupId) { + this.sysGroupId = sysGroupId; + } + +} diff --git a/src/main/java/com/ffii/core/IBaseEntity.java b/src/main/java/com/ffii/core/IBaseEntity.java new file mode 100644 index 0000000..47dbfbb --- /dev/null +++ b/src/main/java/com/ffii/core/IBaseEntity.java @@ -0,0 +1,107 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core; + +import java.io.Serializable; +import java.util.Date; + +public interface IBaseEntity extends Serializable, Cloneable { + + /** + * @return the entity id + */ + public PK getId(); + + /** + * Set the entity id + * + * @param id + * the entity id + */ + public void setId(PK id); + + /** + * @return hibernate version id + */ + public int getVersionId(); + + /** + * Set the hibernate version id + * + * @param versionId + * the hibernate version id + */ + public void setVersionId(int versionId); + + /** + * @return entity's deleted flag + */ + public boolean isDeleted(); + + /** + * Set the entity's deleted flag + * + * @param deleted + * the entity's deleted flag + */ + public void setDeleted(boolean deleted); + + /** + * @return created by User ID + */ + public Integer getCreatedBy(); + + /** + * Set the created by User ID + * + * @param createdBy + * the created by User ID + */ + public void setCreatedBy(Integer createdBy); + + /** + * @return the last modified by User ID + */ + public Integer getModifiedBy(); + + /** + * Set the last modified by User ID + * + * @param modifiedBy + * the last modified by User ID + */ + public void setModifiedBy(Integer modifiedBy); + + /** + * @return created date + */ + public Date getCreated(); + + /** + * Set the created date + * + * @param created + * the created date + */ + public void setCreated(Date created); + + /** + * @return the last modified date + */ + public Date getModified(); + + /** + * Set the last modified date + * + * @param modified + * the last modified date + */ + public void setModified(Date modified); + +} diff --git a/src/main/java/com/ffii/core/Session.java b/src/main/java/com/ffii/core/Session.java new file mode 100644 index 0000000..0e034e8 --- /dev/null +++ b/src/main/java/com/ffii/core/Session.java @@ -0,0 +1,36 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core; + +import javax.servlet.http.HttpServletRequest; + +/** + * Get or Set Session Attributes + * + * @author Patrick + */ +public class Session { + + public static final String AVAILABLE_LOCALES = "availableLocales"; + + /** + * Get session attribute + */ + public static Object getAttribute(HttpServletRequest request, String name) { + return request.getSession().getAttribute(name); + } + + /** + * Set session attribute + */ + public static void setAttribute(HttpServletRequest request, String name, Object value) { + request.getSession().setAttribute(name, value); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/Settings.java b/src/main/java/com/ffii/core/Settings.java new file mode 100644 index 0000000..be11ab5 --- /dev/null +++ b/src/main/java/com/ffii/core/Settings.java @@ -0,0 +1,149 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core; + +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.BooleanUtils; + +public abstract class Settings { + + /* + * System-wide settings + */ + + /** Define all available language names as comma separated string */ + public static final String SYS_AVAILABLE_LANGUAGES = "SYS.availableLanguages"; + + /** Define all available locales as comma separated string */ + public static final String SYS_AVAILABLE_LOCALES = "SYS.availableLocales"; + + /** Define the system default locale as string */ + public static final String SYS_DEFAULT_LOCALE = "SYS.defaultLocale"; + + /** Define the system available currencies as comma separated string */ + public static final String SYS_CURRENCIES = "SYS.currencies"; + + /** Define the system modules (authorities.module) */ + public static final String SYS_ROLE_MODULES = "SYS.modules"; + + /* + * Mail settings + */ + + /** Mail - SMTP host */ + public static final String MAIL_SMTP_HOST = "MAIL.smtp.host"; + + /** Mail - SMTP port */ + public static final String MAIL_SMTP_PORT = "MAIL.smtp.port"; + + /** Mail - SMTP username */ + public static final String MAIL_SMTP_USERNAME = "MAIL.smtp.username"; + + /** Mail - SMTP password */ + public static final String MAIL_SMTP_PASSWORD = "MAIL.smtp.password"; + + public static final String SYS_PASSWORD_RULE_MIN = "SYS.password.rule.length.min"; + public static final String SYS_PASSWORD_RULE_MAX = "SYS.password.rule.length.max"; + public static final String SYS_PASSWORD_RULE_NUMBER = "SYS.password.rule.number"; + public static final String SYS_PASSWORD_RULE_UPPER_ENG = "SYS.password.rule.upper.eng"; + public static final String SYS_PASSWORD_RULE_LOWER_ENG = "SYS.password.rule.lower.eng"; + public static final String SYS_PASSWORD_RULE_SPECIAL = "SYS.password.rule.special"; + + public static final String JS_VERSION = "JS.version"; + + public static class MailSMTP { + private String host; + private String port; + private String username; + private String password; + + public MailSMTP(SettingsService settingsService) { + if (settingsService == null) throw new NullPointerException("SettingsService cannot be null"); + + this.host = settingsService.getString(MAIL_SMTP_HOST); + this.port = settingsService.getString(MAIL_SMTP_PORT); + this.username = settingsService.getString(MAIL_SMTP_USERNAME); + this.password = settingsService.getString(MAIL_SMTP_PASSWORD); + } + + public String getHost() { + return host; + } + + public String getPort() { + return port; + } + + public String getUsername() { + return username; + } + + public String getPassword() { + return password; + } + + } + + public static class PasswordRule { + private int min; + private int max; + + private boolean number; + private boolean upperEng; + private boolean lowerEng; + private boolean specialChar; + + public PasswordRule(SettingsService settingsService) { + if (settingsService == null) throw new NullPointerException("SettingsService cannot be null"); + + this.min = settingsService.getInt(SYS_PASSWORD_RULE_MIN); + this.max = settingsService.getInt(SYS_PASSWORD_RULE_MAX); + this.number = BooleanUtils.isTrue(settingsService.getString(SYS_PASSWORD_RULE_NUMBER)); + this.upperEng = BooleanUtils.isTrue(settingsService.getString(SYS_PASSWORD_RULE_UPPER_ENG)); + this.lowerEng = BooleanUtils.isTrue(settingsService.getString(SYS_PASSWORD_RULE_LOWER_ENG)); + this.specialChar = BooleanUtils.isTrue(settingsService.getString(SYS_PASSWORD_RULE_SPECIAL)); + } + + public int getMin() { + return min; + } + + public int getMax() { + return max; + } + + public boolean needNumberChar() { + return number; + } + + public boolean needUpperEngChar() { + return upperEng; + } + + public boolean needLowerEngChar() { + return lowerEng; + } + + public boolean needSpecialChar() { + return specialChar; + } + + public String getWrongMsg() { + StringBuilder msg = new StringBuilder("Please Following Password Rule.\n"); + msg.append("Minimum " + getMin() + " Characters\n"); + msg.append("Maximum " + getMax() + " Characters\n"); + if (needNumberChar()) msg.append("Numbers\n"); + if (needLowerEngChar()) msg.append("Lower-Case Letters\n"); + if (needUpperEngChar()) msg.append("Capital Letters\n"); + if (needSpecialChar()) msg.append("Symbols\n"); + return msg.toString(); + } + + } +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/User.java b/src/main/java/com/ffii/core/User.java new file mode 100644 index 0000000..bc797b9 --- /dev/null +++ b/src/main/java/com/ffii/core/User.java @@ -0,0 +1,264 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core; + +import java.util.List; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; +import javax.persistence.Transient; + +import org.springframework.security.core.GrantedAuthority; +import org.springframework.security.core.userdetails.UserDetails; + +@Entity +@Table(name = "users") +public class User extends BaseEntity implements UserDetails { + + private static final long serialVersionUID = -9036483598847846102L; + + /** Company ID */ + @Column(nullable = false) + private int companyId; + + /** Customer ID, optional, for End User's customers */ + @Column(nullable = true) + private Integer customerId; + + /** username for login */ + @Column(columnDefinition = "varchar(32)", nullable = false) + private String username; + + /** password for login */ + @Column(columnDefinition = "varchar(64)", nullable = false) + private String password; + + /** is user expired? (not implemented) */ + @Column(columnDefinition = "boolean", nullable = false) + private boolean expired; + + /** is user locked? (not implemented) */ + @Column(columnDefinition = "boolean", nullable = false) + private boolean locked; + + /** User default locale (en / zh_TW / zh_CN) */ + @Column(columnDefinition = "varchar(5)") + private String locale; + + /** Full name for display */ + @Column(columnDefinition = "varchar(90)") + private String fullname; + + /* User profile info (optional fields) START */ + + /** First name */ + @Column(columnDefinition = "varchar(45)") + private String firstname; + + /** Last name */ + @Column(columnDefinition = "varchar(30)") + private String lastname; + + /** Department */ + @Column(nullable = true) + private Integer deptId; + + /** Job title */ + @Column(columnDefinition = "varchar(60)") + private String title; + + /** Email */ + @Column(columnDefinition = "varchar(120)") + private String email; + + /** Phone 1 */ + @Column(columnDefinition = "varchar(30)") + private String phone1; + + /** Phone 2 */ + @Column(columnDefinition = "varchar(30)") + private String phone2; + + /** Remarks */ + @Column(columnDefinition = "varchar(600)") + private String remarks; + + /* User profile info (optional fields) END */ + + /** Transient authorities (populated during user authentication) */ + @Transient + private List authorities; + + /* + * getters and setters + */ + + public int getCompanyId() { + return companyId; + } + + public void setCompanyId(int companyId) { + this.companyId = companyId; + } + + public Integer getCustomerId() { + return customerId; + } + + public void setCustomerId(Integer customerId) { + this.customerId = customerId; + } + + public String getUsername() { + return username; + } + + public void setUsername(String username) { + this.username = username; + } + + public String getPassword() { + return password; + } + + public void setPassword(String password) { + this.password = password; + } + + public boolean isExpired() { + return expired; + } + + public void setExpired(boolean expired) { + this.expired = expired; + } + + public boolean isLocked() { + return locked; + } + + public void setLocked(boolean locked) { + this.locked = locked; + } + + public String getLocale() { + return locale; + } + + public void setLocale(String locale) { + this.locale = locale; + } + + public String getFullname() { + return fullname; + } + + public void setFullname(String fullname) { + this.fullname = fullname; + } + + public String getFirstname() { + return firstname; + } + + public void setFirstname(String firstname) { + this.firstname = firstname; + } + + public String getLastname() { + return lastname; + } + + public void setLastname(String lastname) { + this.lastname = lastname; + } + + public Integer getDeptId() { + return deptId; + } + + public void setDeptId(Integer deptId) { + this.deptId = deptId; + } + + public String getTitle() { + return title; + } + + public void setTitle(String title) { + this.title = title; + } + + public String getEmail() { + return email; + } + + public void setEmail(String email) { + this.email = email; + } + + public String getPhone1() { + return phone1; + } + + public void setPhone1(String phone1) { + this.phone1 = phone1; + } + + public String getPhone2() { + return phone2; + } + + public void setPhone2(String phone2) { + this.phone2 = phone2; + } + + public String getRemarks() { + return remarks; + } + + public void setRemarks(String remarks) { + this.remarks = remarks; + } + + public void setAuthorities(List authorities) { + this.authorities = authorities; + } + + /* + * Override + */ + + @Override + public List getAuthorities() { + return authorities; + } + + @Override + public boolean isAccountNonExpired() { + return !expired; + } + + @Override + public boolean isAccountNonLocked() { + return !locked; + } + + @Override + public boolean isCredentialsNonExpired() { + return true; + } + + @Override + public boolean isEnabled() { + return true; + } + +} diff --git a/src/main/java/com/ffii/core/dao/HibernateDao.java b/src/main/java/com/ffii/core/dao/HibernateDao.java new file mode 100644 index 0000000..bc5c209 --- /dev/null +++ b/src/main/java/com/ffii/core/dao/HibernateDao.java @@ -0,0 +1,160 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.dao; + +import java.io.Serializable; +import java.util.Date; +import java.util.List; + +import com.ffii.core.BaseEntity; +import com.ffii.core.User; +import com.ffii.core.utils.SecurityUtils; + +import org.hibernate.query.Query; +import org.springframework.orm.hibernate5.support.HibernateDaoSupport; + +/** + * Implementation of the {@link IHibernateDao} interface. + * + * @author Patrick + */ +public abstract class HibernateDao, PK extends Serializable> extends HibernateDaoSupport + implements IHibernateDao { + + private final Class type; + + public HibernateDao(final Class type) { + this.type = type; + } + + /** + * Automatically set the {@code createdBy}, {@code created}, {@code modifiedBy}, + * and {@code modified} fields of the object instance. + * + * @param instance the object instance + * @param isNew {@code true} if the instance is new, and need to set the + * {@code createdBy} and {@code created} fields + */ + private void autoSetCreateAndLastModifyFields(final T instance, boolean isNew) { + // try to get the authenticated User ID from session (not available in Mapp) + User user = SecurityUtils.getUser(); + Integer userId = null; + Integer sysGroupId = null; + if (user != null){ + userId = user.getId(); + sysGroupId = user.getSysGroupId(); + } + + Date now = new Date(); + + if (isNew) { + if (instance.getCreatedBy() == null && userId != null) + instance.setCreatedBy(userId); + if (userId != null) + instance.setModifiedBy(userId); + if (instance.getCreated() == null) + instance.setCreated(now); + if(instance.getSysGroupId() == null) + instance.setSysGroupId(sysGroupId); + instance.setModified(now); + } else { + if (userId != null) + instance.setModifiedBy(userId); + instance.setModified(now); + } + } + + @SuppressWarnings("unchecked") + @Override + public PK save(final T instance) { + autoSetCreateAndLastModifyFields(instance, true); + return (PK) getHibernateTemplate().save(instance); + } + + @SuppressWarnings("unchecked") + @Override + public PK saveAs(final T instance) { + return (PK) getHibernateTemplate().save(instance); + } + + @Override + public void update(final T instance) { + autoSetCreateAndLastModifyFields(instance, false); + getHibernateTemplate().update(instance); + } + + @Override + public PK saveOrUpdate(final T instance) { + Serializable id = instance.getId(); + if (id instanceof Long) { + if (((Long) id).longValue() < 0L) + id = null; + } else if (id instanceof Integer) { + if (((Integer) id).intValue() < 0) + id = null; + } + if (id == null) + return save(instance); + else { + update(instance); + return (PK) instance.getId(); + } + } + + @Override + public boolean delete(final T instance) { + try { + getHibernateTemplate().delete(instance); + return true; + } catch (Exception e) { + return false; + } + } + + @Override + public void deleteAll(List instances) { + getHibernateTemplate().deleteAll(instances); + } + + @Override + public void flush() { + getHibernateTemplate().flush(); + } + + @Override + public T find(final PK id) { + return getHibernateTemplate().get(type, id); + } + + @Override + @SuppressWarnings("unchecked") + public T findByQuery(final String queryString, final Serializable... args) { + return getHibernateTemplate().execute(session -> { + Query query = session.createQuery(queryString); + for (int i = 0; i < args.length; i++) { + query.setParameter(i, args[i]); + } + query.setMaxResults(1); + return query.uniqueResult(); + }); + } + + @Override + @SuppressWarnings("unchecked") + public List listByQuery(final String queryString, final Serializable... args) { + return getHibernateTemplate().execute(session -> { + Query query = session.createQuery(queryString); + for (int i = 0; i < args.length; i++) { + query.setParameter(i, args[i]); + } + return query.list(); + }); + } + +} diff --git a/src/main/java/com/ffii/core/dao/IHibernateDao.java b/src/main/java/com/ffii/core/dao/IHibernateDao.java new file mode 100644 index 0000000..5fa08f8 --- /dev/null +++ b/src/main/java/com/ffii/core/dao/IHibernateDao.java @@ -0,0 +1,125 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.dao; + +import java.io.Serializable; +import java.util.List; + +import org.springframework.orm.hibernate5.HibernateTemplate; + +/** + * Hibernate DAO interface. For use with business services to perform actual operations. + * + * @param + * The class this DAO is taking care of. + * @param + * The type of the primary key of class instances. + * + * @author Patrick + */ +public interface IHibernateDao { + + /** + * Returns the underlying {@link HibernateTemplate} + */ + public HibernateTemplate getHibernateTemplate(); + + /** + * Saves the instance to the database. + * + * @param instance + * the object instance to save + * + * @return the object instance's primary key in database + */ + public PK save(T instance); + + /** + * Saves the instance to the database without setting the created/updated fields. + * + * @param instance + * the object instance to save + * + * @return the object instance's primary key in database + */ + public PK saveAs(T instance); + + /** + * Updates the record in the database with the given instance. + * + * @param instance + * modified object instance + */ + public void update(T instance); + + /** + * Saves or updates the record in the database with the given instance. + * + * @param instance + * new or modified object instance + * + * @return the object instance's primary key in database + */ + public PK saveOrUpdate(T instance); + + /** + * Deletes the object instance from the database. + * + * @param instance + * the object instance to remove + */ + public boolean delete(T instance); + + /** + * Remove a collection of instances from the database. + * + * @param instances + * The object instances to remove + */ + public void deleteAll(List instances); + + /** + * Finds the object with the specified identity from the database. + * + * @param id + * the object's primary key in database + * + * @return the mapped object instance from the database + */ + public T find(PK id); + + /** + * Finds the object using the specified query (HQL) and arguments from the database. + * + * @param queryString + * the query string using HQL + * @param args + * variable number of arguments to pass to the query. Note you must have the exact number of arguments as specified in the query. + * + * @return the object instance from the database + */ + public T findByQuery(String queryString, Serializable... args); + + /** + * Returns a {@code List} of {@code Object}s using the specified query (HQL) and arguments from the database. + * + * @param queryString + * the query string using HQL + * @param args + * variable number of arguments to pass to the query. Note you must have the exact number of arguments as specified in the query. + * + * @return {@code List} of object instances from the database + */ + public List listByQuery(String queryString, Serializable... args); + + public void flush(); + +} diff --git a/src/main/java/com/ffii/core/dao/JdbcDao.java b/src/main/java/com/ffii/core/dao/JdbcDao.java new file mode 100644 index 0000000..35a5a5d --- /dev/null +++ b/src/main/java/com/ffii/core/dao/JdbcDao.java @@ -0,0 +1,260 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.dao; + +import java.io.Serializable; +import java.util.List; +import java.util.Map; + +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; + +import org.springframework.dao.IncorrectResultSizeDataAccessException; +import org.springframework.jdbc.core.BeanPropertyRowMapper; +import org.springframework.jdbc.core.JdbcOperations; +import org.springframework.jdbc.core.JdbcTemplate; +import org.springframework.jdbc.core.namedparam.NamedParameterJdbcDaoSupport; +import org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate; +import org.springframework.jdbc.core.simple.SimpleJdbcInsert; + +/** + * JDBC DAO implementation which extends Spring {@link NamedParameterJdbcDaoSupport} + * + * @author Patrick + */ +public class JdbcDao extends NamedParameterJdbcDaoSupport { + + /** + * Return an instance of SimpleJdbcInsert with the specified table name + */ + private SimpleJdbcInsert getJdbcInsert(String tableName, String idName) { + SimpleJdbcInsert jdbcInsert = new SimpleJdbcInsert(getJdbcTemplate()); + if (idName != null) + return jdbcInsert.withTableName(tableName).usingGeneratedKeyColumns(idName); + else + return jdbcInsert.withTableName(tableName); + } + + /** + * Query for a {@code List} of {@code Object}s of type {@code T} using the supplied {@code class} to map the query results. Uses SQL with the named + * parameter support provided by the {@code NamedParameterJdbcTemplate}. + * + * @param sql + * the SQL query to run + * @param mappedClass + * the class to use for result mapping + * @param args + * the map containing the arguments for the query + * @param maxRows + * the maximum results to return + */ + public List query(String sql, Class mappedClass, Map args, int maxRows) { + ((JdbcTemplate) getNamedParameterJdbcTemplate().getJdbcOperations()).setMaxRows(maxRows); + return getNamedParameterJdbcTemplate().query(sql, args, BeanPropertyRowMapper.newInstance(mappedClass)); + } + + /** + * Execute the supplied query with the supplied arguments. + *

+ * The query is expected to be a single row query (otherwise, {@code null} will be returned); the result row will be mapped to a Map (one + * entry for each column, using the column name as the key). Uses SQL with the named parameter support provided by the {@link NamedParameterJdbcTemplate} + *

+ * + * @param sql + * the SQL query to run + * @param args + * the map containing the arguments for the query + */ + public Map queryForMap(String sql, Map args) { + try { + return getNamedParameterJdbcTemplate().queryForMap(sql, args); + } catch (IncorrectResultSizeDataAccessException e) { + logger.debug("Unexpected row count for queryForMap()", e); + return null; + } + } + + /** + * Query for a {@code List} of {@code Map}s, each element in the returned {@code List} is constructed as a {@code Map} as described in + * {@link JdbcOperations#queryForMap}. Uses SQL with the named parameter support provided by the {@code NamedParameterJdbcTemplate}. + * + * @param sql + * the SQL query to run + * @param args + * the map containing the arguments for the query + * @param maxRows + * the maximum results to return + */ + public List> queryForList(String sql, Map args, int maxRows) { + ((JdbcTemplate) getNamedParameterJdbcTemplate().getJdbcOperations()).setMaxRows(maxRows); + return getNamedParameterJdbcTemplate().queryForList(sql, args); + } + + /** + * Query for a {@code List} of {@code Map}s, each element in the returned {@code List} is constructed as a {@code Map} as described in + * {@link JdbcOperations#queryForMap}. Uses SQL with the named parameter support provided by the {@code NamedParameterJdbcTemplate}. + * + * @param sql + * the SQL query to run + * @param args + * the map containing the arguments for the query + */ + public List> queryForList(String sql, Map args) { + return queryForList(sql, args, 0); + } + + /** + * Query for an {@code int} passing in a SQL query using the named parameter support provided by the {@code NamedParameterJdbcTemplate} and a map containing + * the arguments. + *

+ * The query is expected to be a single row/single column query; the returned result will be directly mapped to an {@code int}. + * + * @param sql + * the SQL query to run + * @param args + * the map containing the arguments for the query + */ + public int queryForInt(String sql, Map args) { + Integer value = getNamedParameterJdbcTemplate().queryForObject(sql, args, Integer.class); + return (value != null ? value.intValue() : 0); + } + + /** + * Query for a {@code String} passing in a SQL query using the named parameter support provided by the {@code NamedParameterJdbcTemplate} and a map + * containing the arguments. + *

+ * The query is expected to be a single row/single column query; the returned result will be directly mapped to a {@code String}. + * + * @param sql + * the SQL query to run + * @param args + * the map containing the arguments for the query + */ + public String queryForString(String sql, Map args) { + return getNamedParameterJdbcTemplate().queryForObject(sql, args, String.class); + } + + /** + * Executes a batch using the supplied SQL statement with the batch of supplied arguments using the named parameter support provided by the + * {@code NamedParameterJdbcTemplate} + * + * @param sql + * the SQL statement to execute + * @param batchValues + * the array of Maps containing the batch of arguments for the query + * + * @return an array containing the numbers of rows affected by each update in the batch + */ + public int[] executeBatchUpdate(String sql, Map[] batchValues) { + return getNamedParameterJdbcTemplate().batchUpdate(sql, batchValues); + } + + /** + * Execute the supplied SQL statement with (optional) supplied arguments using the named parameter support provided by the + * {@code NamedParameterJdbcTemplate} + * + * @param sql + * the SQL statement to execute + * @param args + * the map containing the arguments for the query + * + * @return the number of rows affected by the update + */ + public int executeUpdate(String sql, Map args) { + return getNamedParameterJdbcTemplate().update(sql, args); + } + + /** + * Execute the supplied SQL statement with no arguments + * + * @param sql + * the SQL statement to execute + * + * @return the number of rows affected by the update + */ + public int executeUpdate(String sql) { + return getJdbcTemplate().update(sql); + } + + /** + * Executes SQL UPDATE statement with the supplied class and its ID and keyValuePairs + * + * @param clazz + * any class that extends BaseEntity + * @param keyValuePairs + * key value pairs, must include the ID field + * + * @return the number of rows affected by the update + */ + public int executeUpdateByTable(String tableName, Map args) { + + StringBuilder sql = new StringBuilder("UPDATE `" + tableName + "` SET "); + int i = 0; + for (String key : args.keySet()) { + if (i > 0) sql.append(", "); + sql.append(key + " = :" + key); + i++; + } + sql.append(" WHERE id = :id"); + + return executeUpdate(sql.toString(), args); + } + + /** + * Execute SQL Insert statement with the supplied arguments + * + * @param tableName + * the database table name + * @param args + * the map containing the arguments for the insert statement in the form of column name and its value + * + * @return the number of rows affected as returned by the JDBC driver + */ + public int executeInsert(String tableName, Map args) { + return getJdbcInsert(tableName, null).execute(args); + } + + /** + * Execute SQL Insert statement with the supplied arguments and return the generated key value + * + * @param tableName + * the database table name + * @param idName + * the name of ID column that has auto generated key + * @param args + * the map containing the arguments for the insert statement in the form of column name and its value + * + * @return the generated key value + */ + public Number executeInsertAndReturnKey(String tableName, String idName, Map args) { + return getJdbcInsert(tableName, idName).executeAndReturnKey(args); + } + + /** + * Executes SQL Delete statement with the supplied class and its ID + * + * @param clazz + * any class that extends BaseEntity + * @param id + * the entity's ID + * + * @return the number of rows affected by the delete + */ + public int executeDelete(Class> clazz, Serializable id) { + Table table = clazz.getAnnotation(Table.class); + + String sql = "DELETE FROM " + table.name() + " WHERE id = :id"; + + return executeUpdate(sql, MapUtils.toHashMap(Params.ID, id)); + } + +} diff --git a/src/main/java/com/ffii/core/engine/FreeMarkerEngine.java b/src/main/java/com/ffii/core/engine/FreeMarkerEngine.java new file mode 100644 index 0000000..c4e9d0b --- /dev/null +++ b/src/main/java/com/ffii/core/engine/FreeMarkerEngine.java @@ -0,0 +1,56 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.engine; + +import java.io.IOException; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Component; +import org.springframework.ui.freemarker.FreeMarkerTemplateUtils; +import org.springframework.web.context.support.WebApplicationObjectSupport; +import org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer; + +import freemarker.template.Template; +import freemarker.template.TemplateException; + +/** + * FreeMarker template engine - a Spring Component Bean + * + * @author Patrick + */ +@Component +public class FreeMarkerEngine extends WebApplicationObjectSupport { + + @Autowired + private FreeMarkerConfigurer freemarkerConfig; + + /** + * Generates content from FreeMarker template + * + * @param template + * the FreeMarker template name (e.g. {@code "example/example.ftl"}) + * @param model + * the model to be applied to the FreeMarker template, may be null + * @return the generated content as a {@code String}, or {@code null} if exceptions occured + */ + public String generateFreeMarkerContent(String template, Object model) { + try { + Template t = freemarkerConfig.getConfiguration().getTemplate(template); + return FreeMarkerTemplateUtils.processTemplateIntoString(t, model); + } catch (TemplateException e) { + logger.error("Error while processing FreeMarker template ", e); + } catch (IOException e) { + logger.error("IOException occured ", e); + } + return null; + } + +} diff --git a/src/main/java/com/ffii/core/engine/MailEngine.java b/src/main/java/com/ffii/core/engine/MailEngine.java new file mode 100644 index 0000000..fdd68f1 --- /dev/null +++ b/src/main/java/com/ffii/core/engine/MailEngine.java @@ -0,0 +1,316 @@ +/******************************************************************************* + * Copyright 2018 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.engine; + +import java.io.File; +import java.util.HashMap; +import java.util.Map; +import java.util.Properties; + +import javax.mail.MessagingException; +import javax.mail.internet.InternetAddress; +import javax.mail.internet.MimeMessage; + +import com.ffii.core.Settings; +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.tbms.user.service.SysGroupService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.core.io.InputStreamSource; +import org.springframework.mail.javamail.JavaMailSender; +import org.springframework.mail.javamail.JavaMailSenderImpl; +import org.springframework.mail.javamail.MimeMessageHelper; +import org.springframework.stereotype.Component; +import org.springframework.web.context.support.WebApplicationObjectSupport; + +/** + * Mail Engine is a Spring Component Bean that handles E-mail operations. + * + * @author Patrick + */ +@Component +public class MailEngine extends WebApplicationObjectSupport { + + @Autowired + private FreeMarkerEngine freeMarkerEngine; + + private JavaMailSender mailSender; + + @Autowired + private SettingsService settingsService; + + @Autowired + private SysGroupService sysGroupService; + + /** + * Send HTML mail message + * + * @param from + * the from address, must not be null + * @param replyTo + * the reply to address, may be null + * @param to + * the to addresses, must not be null + * @param cc + * the cc addresses, may be null + * @param bcc + * the bcc addresses, may be null + * @param subject + * the subject, may be null + * @param html + * the html message body, must not be null + * @param attachmentFilename + * the name of the attachment as it will appear in the mail + * @param file + * the File to attach + */ + + private JavaMailSender getJavaMailSender(int sysGroupId){ + //if(mailSender == null){ + Map sysGroup = sysGroupService.find(sysGroupId); + + String smtp_host = ""; + int smtp_port = 0; + String smtp_username = ""; + String smtp_password = ""; + logger.info(sysGroup); + if(sysGroup != null){ + smtp_host = sysGroup.get("smtp_host")==null?"":sysGroup.get("smtp_host").toString(); + smtp_port = sysGroup.get("smtp_port")==null?0:Integer.parseInt(sysGroup.get("smtp_port").toString()); + smtp_username = sysGroup.get("smtp_username")==null?"":sysGroup.get("smtp_username").toString(); + smtp_password = sysGroup.get("smtp_password")==null?"":sysGroup.get("smtp_password").toString(); + } + + + JavaMailSenderImpl jmsi = new JavaMailSenderImpl(); + jmsi.setHost(smtp_host); + jmsi.setPort(smtp_port); + jmsi.setUsername(smtp_username); + jmsi.setPassword(smtp_password); + + Properties props = jmsi.getJavaMailProperties(); + props.put("mail.transport.protocol", "smtp"); + props.put("mail.smtp.auth", "true"); + props.put("mail.smtp.starttbms.enable", "true"); + props.put("mail.debug", "true"); + mailSender = jmsi; + //} + return mailSender; + } + + public void sendHtmlMail(int sysGroupId, InternetAddress from, InternetAddress replyTo, InternetAddress[] to, InternetAddress[] cc, InternetAddress[] bcc, + String subject, String html, String attachmentFilename, File file) { + + MimeMessage mimeMessage = getJavaMailSender(sysGroupId).createMimeMessage(); + + try { + MimeMessageHelper message = new MimeMessageHelper(mimeMessage, true, "UTF-8"); + message.setFrom(from); + if (replyTo != null) message.setReplyTo(replyTo); + message.setTo(to); + if (cc != null) message.setCc(cc); + if (bcc != null) message.setBcc(bcc); + if (subject != null) message.setSubject(subject); + message.setText(html, true); + if (attachmentFilename != null && file != null) message.addAttachment(attachmentFilename, file); + } catch (MessagingException e) { + logger.error("Failed to send HTML mail", e); + } + + getJavaMailSender(sysGroupId).send(mimeMessage); + } + + + /** + * Send HTML mail message + * + * @param from + * the from address, must not be null + * @param replyTo + * the reply to address, may be null + * @param to + * the to addresses, must not be null + * @param subject + * the subject, may be null + * @param html + * the html message body, must not be null + * @param attachmentFilename + * the name of the attachment as it will appear in the mail + * @param file + * the File to attach + */ + public void sendHtmlMail(int sysGroupId, InternetAddress from, InternetAddress replyTo, InternetAddress[] to, + String subject, String html, String attachmentFilename, File file) { + sendHtmlMail(sysGroupId, from, replyTo, to, null, null, subject, html, attachmentFilename, file); + } + + /** + * Send HTML mail message + * + * @param from + * the from address, must not be null + * @param replyTo + * the reply to address, may be null + * @param to + * the to addresses, must not be null + * @param subject + * the subject, may be null + * @param html + * the html message body, must not be null + */ + public void sendHtmlMail(int sysGroupId,InternetAddress from, InternetAddress replyTo, InternetAddress[] to, String subject, String html) { + sendHtmlMail(sysGroupId, from, replyTo, to, null, null, subject, html, null, null); + } + + /** + * Send HTML mail message generated from FreeMarker template + * + * @param from + * the from address, must not be null + * @param replyTo + * the reply to address, may be null + * @param to + * the to addresses, must not be null + * @param cc + * the cc addresses, may be null + * @param bcc + * the bcc addresses, may be null + * @param subject + * the subject, may be null + * @param template + * the FreeMarker template name, must not be null + * @param model + * the model to be applied to the FreeMarker template, may be null + * @param attachmentFilename + * the name of the attachment as it will appear in the mail + * @param file + * the File to attach + */ + public void sendFreeMarkerHtmlMail(int sysGroupId,InternetAddress from, InternetAddress replyTo, InternetAddress[] to, InternetAddress[] cc, InternetAddress[] bcc, + String subject, String template, Map model, String attachmentFilename, File file) { + + String html = freeMarkerEngine.generateFreeMarkerContent(template, model); + + sendHtmlMail(sysGroupId,from, replyTo, to, cc, bcc, subject, html, attachmentFilename, file); + } + + /** + * Send HTML mail message generated from FreeMarker template + * + * @param from + * the from address, must not be null + * @param replyTo + * the reply to address, may be null + * @param to + * the to addresses, must not be null + * @param subject + * the subject, may be null + * @param template + * the FreeMarker template name, must not be null + * @param model + * the model to be applied to the FreeMarker template, may be null + */ + public void sendFreeMarkerHtmlMail(int sysGroupId, InternetAddress from, InternetAddress replyTo, InternetAddress[] to, InternetAddress[] cc, InternetAddress[] bcc, + String subject, String template, Map model) { + sendFreeMarkerHtmlMail(sysGroupId, from, replyTo, to, cc, bcc, subject, template, model, null, null); + } + + /** + * Send HTML mail message generated from FreeMarker template + * + * @param from + * the from address, must not be null + * @param replyTo + * the reply to address, may be null + * @param to + * the to addresses, must not be null + * @param subject + * the subject, may be null + * @param template + * the FreeMarker template name, must not be null + * @param model + * the model to be applied to the FreeMarker template, may be null + * @param attachmentFilename + * the name of the attachment as it will appear in the mail + * @param file + * the File to attach + */ + public void sendFreeMarkerHtmlMail(int sysGroupId,InternetAddress from, InternetAddress replyTo, InternetAddress[] to, + String subject, String template, Map model, String attachmentFilename, File file) { + sendFreeMarkerHtmlMail(sysGroupId, from, replyTo, to, null, null, subject, template, model, attachmentFilename, file); + } + + /** + * Send HTML mail message generated from FreeMarker template + * + * @param from + * the from address, must not be null + * @param replyTo + * the reply to address, may be null + * @param to + * the to addresses, must not be null + * @param subject + * the subject, may be null + * @param template + * the FreeMarker template name, must not be null + * @param model + * the model to be applied to the FreeMarker template, may be null + * @param attachmentFilename + * the name of the attachment as it will appear in the mail + * @param file + * the File to attach + */ + + public void sendFreeMarkerHtmlMail(int sysGroupId, InternetAddress from, InternetAddress replyTo, InternetAddress[] to, + String subject, String template, Map model, String attachmentFilename, InputStreamSource file) { + + String html = freeMarkerEngine.generateFreeMarkerContent(template, model); + + MimeMessage mimeMessage = getJavaMailSender(sysGroupId).createMimeMessage(); + try { + MimeMessageHelper message = new MimeMessageHelper(mimeMessage, true, "UTF-8"); + message.setFrom(from); + if (replyTo != null) message.setReplyTo(replyTo); + message.setTo(to); + if (subject != null) message.setSubject(subject); + message.setText(html, true); + if (attachmentFilename != null && file != null) message.addAttachment(attachmentFilename, file); + } catch (MessagingException e) { + logger.error("Failed to send HTML mail", e); + } + + getJavaMailSender(sysGroupId).send(mimeMessage); + } + + + /** + * Send HTML mail message generated from FreeMarker template + * + * @param from + * the from address, must not be null + * @param replyTo + * the reply to address, may be null + * @param to + * the to addresses, must not be null + * @param subject + * the subject, may be null + * @param template + * the FreeMarker template name, must not be null + * @param model + * the model to be applied to the FreeMarker template, may be null + */ + public void sendFreeMarkerHtmlMail(int sysGroupId, InternetAddress from, InternetAddress replyTo, InternetAddress[] to, + String subject, String template, Map model) { + sendFreeMarkerHtmlMail(sysGroupId,from, replyTo, to, null, null, subject, template, model, null, null); + } + +} diff --git a/src/main/java/com/ffii/core/i18n/support/JdbcMessageSource.java b/src/main/java/com/ffii/core/i18n/support/JdbcMessageSource.java new file mode 100644 index 0000000..4578055 --- /dev/null +++ b/src/main/java/com/ffii/core/i18n/support/JdbcMessageSource.java @@ -0,0 +1,109 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.i18n.support; + +import java.text.MessageFormat; +import java.util.HashMap; +import java.util.List; +import java.util.Locale; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.support.AbstractMessageSource; + +import com.ffii.core.dao.JdbcDao; + +/** + * Jdbc MessageSource implementation. + * + *

+ * CREATE TABLE `i18n` (
+ * 	`locale` varchar(10) NOT NULL,
+ * 	`code` varchar(100) NOT NULL,
+ * 	`value` varchar(500) DEFAULT NULL,
+ * PRIMARY KEY (`locale`,`code`)
+ * );
+ * 
+ * + * @author Patrick + */ +public class JdbcMessageSource extends AbstractMessageSource { + + @Autowired + private JdbcDao jdbcDao; + + @Override + protected String resolveCodeWithoutArguments(String code, Locale locale) { + return getMessages(locale.toString()).get(code); + } + + @Override + protected MessageFormat resolveCode(String code, Locale locale) { + String msg = getMessages(locale.toString()).get(code); + return createMessageFormat(msg, locale); + } + + /** i18n messages cache */ + private static Map> MESSAGES = new HashMap>(); + + /** + * Load a list of messages from i18n table in database + * + * @param locale + * the locale String (e.g. {@code en_US}) + */ + public List> loadMessages(String locale) { + /* prep args */ + Map args = new HashMap(); + args.put("locale", locale); + + /* build sql */ + String sql = "SELECT locale, code, value FROM i18n WHERE locale = :locale"; + + /* do query and return */ + return jdbcDao.queryForList(sql, args); + } + + /** + * Get i18n messages map + * + * @param locale + * the locale String (e.g. {@code en_US}) + */ + public Map getMessages(String locale) { + Map messages = MESSAGES.get(locale); + + /* if not loaded yet, load it from database */ + if (messages == null) { + messages = new HashMap(); + + /* convert the list to a simple messages map */ + List> rawMessages = loadMessages(locale); + for (Map rm : rawMessages) { + messages.put((String) rm.get("code"), (String) rm.get("value")); + } + + /* cache the messages */ + MESSAGES.put(locale, messages); + } + + return messages; + } + + /** + * Reset the i18n messages cache + */ + public void resetMessagesCache() { + /* simply create a new map */ + MESSAGES = new HashMap>(); + } + +} diff --git a/src/main/java/com/ffii/core/security/authentication/AuthToken.java b/src/main/java/com/ffii/core/security/authentication/AuthToken.java new file mode 100644 index 0000000..c9746d9 --- /dev/null +++ b/src/main/java/com/ffii/core/security/authentication/AuthToken.java @@ -0,0 +1,52 @@ +package com.ffii.core.security.authentication; + +import com.ffii.core.User; + +import org.springframework.security.authentication.AbstractAuthenticationToken; + +/** + * Authentication Token + * + * @author Patrick + */ +public class AuthToken extends AbstractAuthenticationToken { + + private static final long serialVersionUID = 3383254131623375507L; + + private final String token; + private final User user; + + public AuthToken(String token) { + super(null); + + this.token = token; + this.user = null; + setAuthenticated(false); + } + + public AuthToken(String token, User user) { + super(user.getAuthorities()); + + this.token = token; + this.user = user; + setAuthenticated(true); + } + + @Override + public Object getCredentials() { + return getToken(); + } + + @Override + public Object getPrincipal() { + return getUser(); + } + + public String getToken() { + return token; + } + + public User getUser() { + return user; + } +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/security/authentication/TokenAuthenticationProvider.java b/src/main/java/com/ffii/core/security/authentication/TokenAuthenticationProvider.java new file mode 100644 index 0000000..ed12605 --- /dev/null +++ b/src/main/java/com/ffii/core/security/authentication/TokenAuthenticationProvider.java @@ -0,0 +1,49 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.security.authentication; + +import com.ffii.core.User; +import com.ffii.core.security.service.TokenUserDetailsService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.security.authentication.AuthenticationProvider; +import org.springframework.security.authentication.BadCredentialsException; +import org.springframework.security.core.Authentication; +import org.springframework.security.core.AuthenticationException; +import org.springframework.stereotype.Component; + +/** + * Token Authentication Provider + * + * @author Patrick + */ +@Component +public class TokenAuthenticationProvider implements AuthenticationProvider { + + @Autowired + private TokenUserDetailsService tokenUserDetailsService; + + @Override + public Authentication authenticate(Authentication authentication) throws AuthenticationException { + final AuthToken authToken = (AuthToken) authentication; + final String token = authToken.getToken(); + + User user = tokenUserDetailsService.findUserByToken(token); + + if (user == null) + throw new BadCredentialsException("No user found for token - " + token); + + return new AuthToken(token, user); + } + + @Override + public boolean supports(Class authentication) { + return authentication.equals(AuthToken.class); + } +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/security/filter/AuthTokenFilter.java b/src/main/java/com/ffii/core/security/filter/AuthTokenFilter.java new file mode 100644 index 0000000..f0174a1 --- /dev/null +++ b/src/main/java/com/ffii/core/security/filter/AuthTokenFilter.java @@ -0,0 +1,74 @@ +package com.ffii.core.security.filter; + +import java.io.IOException; +import java.util.Collections; + +import javax.servlet.FilterChain; +import javax.servlet.ServletException; +import javax.servlet.ServletRequest; +import javax.servlet.ServletResponse; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import com.ffii.core.security.authentication.AuthToken; +import com.ffii.core.utils.StringUtils; + +import org.springframework.security.core.Authentication; +import org.springframework.security.core.AuthenticationException; +import org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter; +import org.springframework.security.web.util.matcher.RequestMatcher; + +/** + * Authentication Token Filter + * + * @author Patrick + */ +public class AuthTokenFilter extends AbstractAuthenticationProcessingFilter { + + public static final String TOKEN_HEADER = "x-auth-token"; + + public AuthTokenFilter(RequestMatcher requestMatcher) { + super(requestMatcher); + } + + @Override + public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) + throws IOException, ServletException { + final String tokenValue = getTokenValue((HttpServletRequest) request); + + // This filter only applies if the header is present + if (StringUtils.isEmpty(tokenValue)) { + chain.doFilter(request, response); + return; + } + + // On success keep going on the chain + this.setAuthenticationSuccessHandler((request1, response1, authentication) -> { + chain.doFilter(request1, response1); + }); + + super.doFilter(request, response, chain); + } + + @Override + public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) + throws AuthenticationException, IOException, ServletException { + final String tokenValue = getTokenValue(request); + + if (StringUtils.isEmpty(tokenValue)) { + return null; + } + + AuthToken token = new AuthToken(tokenValue); + token.setDetails(authenticationDetailsSource.buildDetails(request)); + + return this.getAuthenticationManager().authenticate(token); + } + + private String getTokenValue(HttpServletRequest request) { + return Collections.list(request.getHeaderNames()).stream() + .filter(header -> TOKEN_HEADER.equalsIgnoreCase(header)).map(header -> request.getHeader(header)) + .findFirst().orElse(null); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/security/service/LoginLogService.java b/src/main/java/com/ffii/core/security/service/LoginLogService.java new file mode 100644 index 0000000..dc54608 --- /dev/null +++ b/src/main/java/com/ffii/core/security/service/LoginLogService.java @@ -0,0 +1,65 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.security.service; + +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.web.AbstractService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * Login Log Service + * + * @author Patrick + */ +@Service +public class LoginLogService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + /** + * Create Login Log record + * + * @param username + * the username + * @param remoteAddr + * request.getRemoteAddr() + * @param success + * true if the login is successful, else false + * + * @return true if the number of rows inserted is 1 + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = false) + public boolean createLoginLog(String username, String remoteAddr, boolean success) { + Map args = new HashMap<>(4); + args.put("username", username); + args.put("loginTime", new Date()); + args.put("ipAddr", remoteAddr); + args.put("success", success); + + return (jdbcDao.executeInsert("user_login_log", args) == 1); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> listLastLog(String username, int limit) { + return jdbcDao.queryForList("SELECT success FROM user_login_log where username = :username ORDER BY loginTime DESC LIMIT " + limit, + MapUtils.toHashMap("username", username)); + } + +} diff --git a/src/main/java/com/ffii/core/security/service/TokenUserDetailsService.java b/src/main/java/com/ffii/core/security/service/TokenUserDetailsService.java new file mode 100644 index 0000000..77ba37d --- /dev/null +++ b/src/main/java/com/ffii/core/security/service/TokenUserDetailsService.java @@ -0,0 +1,143 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.security.service; + +import java.sql.ResultSet; +import java.sql.SQLException; +import java.util.ArrayList; +import java.util.HashSet; +import java.util.List; +import java.util.Set; + +import com.ffii.core.User; +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.web.AbstractService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.support.MessageSourceAccessor; +import org.springframework.jdbc.core.RowMapper; +import org.springframework.security.core.GrantedAuthority; +import org.springframework.security.core.SpringSecurityMessageSource; +import org.springframework.security.core.authority.SimpleGrantedAuthority; +import org.springframework.security.core.userdetails.UserDetails; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * Token User Details Service + * + * @author Patrick + */ +@Service +public class TokenUserDetailsService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + public static final String FIND_USER_BY_DEVICE_TOKEN_SQL = "SELECT u.* FROM users u LEFT JOIN access_token at ON u.id = at.userId" + + " WHERE u.deleted = 0 AND at.token = :token"; + + public static final String LOAD_AUTHORITIES_BY_USERNAME_SQL = "SELECT u.username, ua.authority" + + " FROM `users_authorities` ua" + " LEFT JOIN `users` u ON ua.userId = u.id" + + " WHERE u.deleted = 0 AND u.username = ?"; + + public static final String LOAD_GROUP_AUTHORITIES_BY_USERNAME_SQL = "SELECT g.id, g.name, ga.authority" + + " FROM `groups_authorities` ga" + " LEFT JOIN `groups` g ON ga.groupId = g.id AND g.deleted = 0" + + " LEFT JOIN `groups_users` gu ON ga.groupId = gu.groupId" + " LEFT JOIN `users` u ON gu.userId = u.id" + + " WHERE u.deleted = 0 AND u.username = ?"; + + protected final MessageSourceAccessor messages = SpringSecurityMessageSource.getAccessor(); + + // ~ Constructors + public TokenUserDetailsService() { + } + + // ~ Methods + + /** + * Allows subclasses to add their own granted authorities to the list to be + * returned in the UserDetails. + * + * @param username the username, for use by finder methods + * @param authorities the current granted authorities, as populated from the + * authoritiesByUsername mapping + */ + protected void addCustomAuthorities(String username, List authorities) { + // add ROLE_USER for basic access + authorities.add(new SimpleGrantedAuthority("ROLE_USER")); + } + + public UserDetails loadUserByToken(String token) { + + User user = findUserByToken(token); // contains no GrantedAuthority[] + + // build GrantedAuthority[] + Set authoritiesSet = new HashSet<>(); + + // aadd all user's authorities + authoritiesSet.addAll(loadUserAuthorities(user.getUsername())); + + // add all user's groups' authorities + authoritiesSet.addAll(loadGroupAuthorities(user.getUsername())); + + // convert to List + List authoritiesList = new ArrayList(authoritiesSet); + + addCustomAuthorities(user.getUsername(), authoritiesList); + + user.setAuthorities(authoritiesList); + + return user; + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public User findUserByToken(String token) { + List users = jdbcDao.query(FIND_USER_BY_DEVICE_TOKEN_SQL, User.class, MapUtils.toHashMap("token", token), + 1); + if (users.size() == 1) + return users.get(0); + else + return null; + } + + /** + * Loads user authorities by executing SQL + * + * @return a list of GrantedAuthority objects for the user + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + protected List loadUserAuthorities(String username) { + return jdbcDao.getNamedParameterJdbcTemplate().query(LOAD_AUTHORITIES_BY_USERNAME_SQL, + MapUtils.toHashMap("username", username), new RowMapper() { + @Override + public GrantedAuthority mapRow(ResultSet rs, int rowNum) throws SQLException { + return new SimpleGrantedAuthority(rs.getString("authority")); + } + }); + } + + /** + * Loads group authorities by executing SQL + * + * @return a list of GrantedAuthority objects from the user's groups + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + protected List loadGroupAuthorities(String username) { + return jdbcDao.getNamedParameterJdbcTemplate().query(LOAD_GROUP_AUTHORITIES_BY_USERNAME_SQL, + MapUtils.toHashMap("username", username), new RowMapper() { + @Override + public GrantedAuthority mapRow(ResultSet rs, int rowNum) throws SQLException { + return new SimpleGrantedAuthority(rs.getString("authority")); + } + }); + } + +} diff --git a/src/main/java/com/ffii/core/security/userdetails/UserDetailsServiceImpl.java b/src/main/java/com/ffii/core/security/userdetails/UserDetailsServiceImpl.java new file mode 100644 index 0000000..fd85d56 --- /dev/null +++ b/src/main/java/com/ffii/core/security/userdetails/UserDetailsServiceImpl.java @@ -0,0 +1,239 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.security.userdetails; + +import java.sql.ResultSet; +import java.sql.SQLException; +import java.util.ArrayList; +import java.util.HashSet; +import java.util.List; +import java.util.Set; + +import com.ffii.core.User; + +import org.springframework.context.ApplicationContextException; +import org.springframework.context.support.MessageSourceAccessor; +import org.springframework.jdbc.core.BeanPropertyRowMapper; +import org.springframework.jdbc.core.RowMapper; +import org.springframework.jdbc.core.support.JdbcDaoSupport; +import org.springframework.security.core.GrantedAuthority; +import org.springframework.security.core.SpringSecurityMessageSource; +import org.springframework.security.core.authority.SimpleGrantedAuthority; +import org.springframework.security.core.userdetails.UserDetails; +import org.springframework.security.core.userdetails.UserDetailsService; +import org.springframework.security.core.userdetails.UsernameNotFoundException; +import org.springframework.util.Assert; + + +public class UserDetailsServiceImpl extends JdbcDaoSupport implements UserDetailsService { + + // ~ Static fields/initializers ===================================================================================== + + public static final String DEF_USERS_BY_USERNAME_QUERY = "SELECT *" + + " FROM `users` WHERE deleted = 0 AND username = ?"; + + public static final String DEF_AUTHORITIES_BY_USERNAME_QUERY = "SELECT u.username, ua.authority" + + " FROM `users_authorities` ua" + + " LEFT JOIN `users` u ON ua.userId = u.id" + + " WHERE u.deleted = 0 AND u.username = ?"; + + public static final String DEF_GROUP_AUTHORITIES_BY_USERNAME_QUERY = "SELECT g.id, g.name, ga.authority" + + " FROM `groups_authorities` ga" + + " LEFT JOIN `groups` g ON ga.groupId = g.id AND g.deleted = 0" + + " LEFT JOIN `groups_users` gu ON ga.groupId = gu.groupId" + + " LEFT JOIN `users` u ON gu.userId = u.id" + + " WHERE u.deleted = 0 AND u.username = ?"; + + // ~ Instance fields ================================================================================================ + + protected final MessageSourceAccessor messages = SpringSecurityMessageSource.getAccessor(); + + private String usersByUsernameQuery; + private String authoritiesByUsernameQuery; + private String groupAuthoritiesByUsernameQuery; + + private boolean enableAuthorities = true; + private boolean enableGroups; + + // ~ Constructors =================================================================================================== + + public UserDetailsServiceImpl() { + usersByUsernameQuery = DEF_USERS_BY_USERNAME_QUERY; + authoritiesByUsernameQuery = DEF_AUTHORITIES_BY_USERNAME_QUERY; + groupAuthoritiesByUsernameQuery = DEF_GROUP_AUTHORITIES_BY_USERNAME_QUERY; + } + + // ~ Methods ======================================================================================================== + + /** + * Allows subclasses to add their own granted authorities to the list to be returned in the UserDetails. + * + * @param username + * the username, for use by finder methods + * @param authorities + * the current granted authorities, as populated from the authoritiesByUsername mapping + */ + protected void addCustomAuthorities(String username, List authorities) { + // add ROLE_USER for basic access + authorities.add(new SimpleGrantedAuthority("ROLE_USER")); + } + + public String getUsersByUsernameQuery() { + return usersByUsernameQuery; + } + + @Override + protected void initDao() throws ApplicationContextException { + Assert.isTrue(enableAuthorities || enableGroups, "Use of either authorities or groups must be enabled"); + } + + @Override + public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException { + + List users = loadUsersByUsername(username); + + if (users.size() == 0) { + logger.debug("Query returned no results for user '" + username + "'"); + + throw new UsernameNotFoundException( + messages.getMessage("JdbcDaoImpl.notFound", new Object[] { username }, "Username {0} not found")); + } + + User user = users.get(0); // contains no GrantedAuthority[] + + Set dbAuthsSet = new HashSet(); + + if (enableAuthorities) { + dbAuthsSet.addAll(loadUserAuthorities(user.getUsername())); + } + + if (enableGroups) { + dbAuthsSet.addAll(loadGroupAuthorities(user.getUsername())); + } + + List dbAuths = new ArrayList(dbAuthsSet); + + addCustomAuthorities(user.getUsername(), dbAuths); + + if (dbAuths.size() == 0) { + logger.debug("User '" + username + "' has no authorities and will be treated as 'not found'"); + + throw new UsernameNotFoundException( + messages.getMessage("USER.noAuthority", new Object[] { username }, "User {0} has no GrantedAuthority")); + } + + user.setAuthorities(dbAuths); + return user; + } + + /** + * Executes the SQL usersByUsernameQuery and returns a list of UserDetails objects. There should normally only be one matching user. + */ + protected List loadUsersByUsername(String username) { + return getJdbcTemplate().query(usersByUsernameQuery, new String[] { username }, BeanPropertyRowMapper.newInstance(User.class)); + } + + /** + * Loads authorities by executing the SQL from authoritiesByUsernameQuery. + * + * @return a list of GrantedAuthority objects for the user + */ + protected List loadUserAuthorities(String username) { + return getJdbcTemplate().query(authoritiesByUsernameQuery, new String[] { username }, new RowMapper() { + @Override + public GrantedAuthority mapRow(ResultSet rs, int rowNum) throws SQLException { + return new SimpleGrantedAuthority(rs.getString("authority")); + } + }); + } + + /** + * Loads authorities by executing the SQL from groupAuthoritiesByUsernameQuery. + * + * @return a list of GrantedAuthority objects for the user + */ + protected List loadGroupAuthorities(String username) { + return getJdbcTemplate().query(groupAuthoritiesByUsernameQuery, new String[] { username }, new RowMapper() { + @Override + public GrantedAuthority mapRow(ResultSet rs, int rowNum) throws SQLException { + return new SimpleGrantedAuthority(rs.getString("authority")); + } + }); + } + + /** + * Allows the default query string used to retrieve authorities based on username to be overridden, if default table or column names need to be changed. The + * default query is {@link #DEF_AUTHORITIES_BY_USERNAME_QUERY}; when modifying this query, ensure that all returned columns are mapped back to the same + * column names as in the default query. + * + * @param queryString + * The SQL query string to set + */ + public void setAuthoritiesByUsernameQuery(String queryString) { + authoritiesByUsernameQuery = queryString; + } + + protected String getAuthoritiesByUsernameQuery() { + return authoritiesByUsernameQuery; + } + + /** + * Allows the default query string used to retrieve group authorities based on username to be overridden, if default table or column names need to be + * changed. The default query is {@link #DEF_GROUP_AUTHORITIES_BY_USERNAME_QUERY}; when modifying this query, ensure that all returned columns are mapped + * back to the same column names as in the default query. + * + * @param queryString + * The SQL query string to set + */ + public void setGroupAuthoritiesByUsernameQuery(String queryString) { + groupAuthoritiesByUsernameQuery = queryString; + } + + /** + * Allows the default query string used to retrieve users based on username to be overridden, if default table or column names need to be changed. The + * default query is {@link #DEF_USERS_BY_USERNAME_QUERY}; when modifying this query, ensure that all returned columns are mapped back to the same column + * names as in the default query. If the 'enabled' column does not exist in the source database, a permanent true value for this column may be returned by + * using a query similar to + * + *
+	 * "select username,password,'true' as enabled from users where username = ?"
+	 * 
+ * + * @param usersByUsernameQueryString + * The query string to set + */ + public void setUsersByUsernameQuery(String usersByUsernameQueryString) { + this.usersByUsernameQuery = usersByUsernameQueryString; + } + + protected boolean getEnableAuthorities() { + return enableAuthorities; + } + + /** + * Enables loading of authorities from the authorities table. Defaults to true + */ + public void setEnableAuthorities(boolean enableAuthorities) { + this.enableAuthorities = enableAuthorities; + } + + protected boolean getEnableGroups() { + return enableGroups; + } + + /** + * Enables support for group authorities. Defaults to false + * + * @param enableGroups + */ + public void setEnableGroups(boolean enableGroups) { + this.enableGroups = enableGroups; + } + +} diff --git a/src/main/java/com/ffii/core/security/web/authentication/JsonAuthenticationFailureHandler.java b/src/main/java/com/ffii/core/security/web/authentication/JsonAuthenticationFailureHandler.java new file mode 100644 index 0000000..be29efb --- /dev/null +++ b/src/main/java/com/ffii/core/security/web/authentication/JsonAuthenticationFailureHandler.java @@ -0,0 +1,100 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.security.web.authentication; + +import java.io.IOException; +import java.util.List; +import java.util.Map; + +import javax.servlet.ServletException; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.security.core.AuthenticationException; +import org.springframework.security.web.authentication.SimpleUrlAuthenticationFailureHandler; + +import com.ffii.core.utils.BooleanUtils; +import com.ffii.core.utils.JsonUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.StringUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.utils.web.ServletResponseUtils; +import com.ffii.core.web.view.AbstractView; +import com.ffii.core.security.service.LoginLogService; +import com.ffii.tbms.user.service.UserService; + +/** + * AuthenticationFailureHandler implementation which return a failure JSON String upon failed authentication. + * + * @author Patrick + */ +public class JsonAuthenticationFailureHandler extends SimpleUrlAuthenticationFailureHandler { + + /** Continuous fail 5 time, lock user */ + private final int TIMES = 5; + + protected final Log logger = LogFactory.getLog(getClass()); + + @Autowired + private UserService userService; + + @Autowired + private LoginLogService loginLogService; + + /** + * Returns the failure JSON String to client. + */ + @Override + public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response, AuthenticationException exception) + throws IOException, ServletException { + + logger.info("Authentication Failure: " + exception.getMessage() + " [" + request.getRemoteAddr() + "]"); + + String username = StringUtils.left(ServletRequestUtils.getStringParameter(request, "username"), 32); + + ServletResponseUtils.disableCaching(response); + response.setContentType(AbstractView.CONTENT_TYPE_JSON); + response.setCharacterEncoding("UTF-8"); + response.setStatus(HttpServletResponse.SC_UNAUTHORIZED); // set HTTP status to 401 + + boolean locked = false; + // log failed login + if (username != null) { + loginLogService.createLoginLog(username, request.getRemoteAddr(), false); + + // when failed 5 times, lock account + List> logs = loginLogService.listLastLog(username, TIMES); + if (logs.size() >= TIMES) { + boolean needLock = true; + for (Map log : logs) { + if (BooleanUtils.isTrue(log.get("success"))) { + needLock = false; + break; + } + } + if (needLock) { + locked = true; + userService.lockUser(username, true); + } + } + + } + Map result = MapUtils.toHashMap( + Params.SUCCESS, Boolean.FALSE, + Params.MSG, + locked ? "Account locked (" + TIMES + " Times Failure), please contact your IT administrator." : "Invalid Username or Password."); + + ServletResponseUtils.writeStringToStream(response, AbstractView.CHARSET_UTF8, JsonUtils.toJsonString(result)); + } + +} diff --git a/src/main/java/com/ffii/core/security/web/authentication/JsonAuthenticationSuccessHandler.java b/src/main/java/com/ffii/core/security/web/authentication/JsonAuthenticationSuccessHandler.java new file mode 100644 index 0000000..c00ac19 --- /dev/null +++ b/src/main/java/com/ffii/core/security/web/authentication/JsonAuthenticationSuccessHandler.java @@ -0,0 +1,119 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.security.web.authentication; + +import java.io.IOException; +import java.io.UnsupportedEncodingException; +import java.net.URLEncoder; +import java.util.HashMap; +import java.util.Map; + +import javax.servlet.ServletException; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import com.ffii.core.Session; +import com.ffii.core.Settings; +import com.ffii.core.security.service.LoginLogService; +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.JsonUtils; +import com.ffii.core.utils.LocaleUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.utils.web.ServletResponseUtils; +import com.ffii.core.web.view.AbstractView; + + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.http.MediaType; +import org.springframework.security.core.Authentication; +import org.springframework.security.web.authentication.SimpleUrlAuthenticationSuccessHandler; +import org.springframework.security.web.savedrequest.HttpSessionRequestCache; +import org.springframework.security.web.savedrequest.RequestCache; +import org.springframework.security.web.savedrequest.SavedRequest; +import org.springframework.util.StringUtils; +import org.springframework.web.servlet.i18n.SessionLocaleResolver; +import org.springframework.web.util.WebUtils; + +/** + * AuthenticationSuccessHandler implementation which return a success JSON String upon successful authentication. + * + * @author Patrick + */ +public class JsonAuthenticationSuccessHandler extends SimpleUrlAuthenticationSuccessHandler { + + private RequestCache requestCache = new HttpSessionRequestCache(); + + @Autowired + private LoginLogService loginLogService; + + @Autowired + private SettingsService settingsService; + + /** + * Returns the successful JSON String to client, unless the account is locked. + */ + @Override + public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response, Authentication authentication) + throws IOException, ServletException { + + logger.info("Authentication Success: " + authentication.getName() + " [" + request.getRemoteAddr() + "]"); + + ServletResponseUtils.disableCaching(response); + response.setContentType(MediaType.APPLICATION_JSON_UTF8_VALUE); + response.setCharacterEncoding("UTF-8"); + + // save available locales to session + String[] availableLocales = settingsService.getString(Settings.SYS_AVAILABLE_LOCALES).split(","); + Session.setAttribute(request, Session.AVAILABLE_LOCALES, availableLocales); + + // set user's default locale + String locale = SecurityUtils.getUser().getLocale(); + if (!StringUtils.isEmpty(locale)) + WebUtils.setSessionAttribute(request, SessionLocaleResolver.LOCALE_SESSION_ATTRIBUTE_NAME, LocaleUtils.toLocale(locale)); + + // extra values to be passed to client + Map values = new HashMap(); + + SavedRequest savedRequest = requestCache.getRequest(request, response); + if (savedRequest != null) { + String targetUrlParameter = getTargetUrlParameter(); + if (isAlwaysUseDefaultTargetUrl() || (targetUrlParameter != null && StringUtils.hasText(request.getParameter(targetUrlParameter)))) { + requestCache.removeRequest(request, response); + authenticationSuccess(request, response, null); + return; + } + + // Use the DefaultSavedRequest URL + String targetUrl = savedRequest.getRedirectUrl(); + logger.debug("Sending DefaultSavedRequest Url: " + targetUrl); + + // target URL to redirect to (if any) + values.put("targetUrl", URLEncoder.encode(targetUrl, "UTF-8")); + } + + authenticationSuccess(request, response, values); + } + + protected void authenticationSuccess(HttpServletRequest request, HttpServletResponse response, Map values) + throws UnsupportedEncodingException, IOException { + + Map args = new HashMap(); + args.put(Params.SUCCESS, Boolean.TRUE); + if (values != null) args.putAll(values); + + clearAuthenticationAttributes(request); + ServletResponseUtils.writeStringToStream(response, AbstractView.CHARSET_UTF8, JsonUtils.toJsonString(args)); + + // log successful login + loginLogService.createLoginLog(SecurityUtils.getUser().getUsername(), request.getRemoteAddr(), true); + + } + +} diff --git a/src/main/java/com/ffii/core/setting/Setting.java b/src/main/java/com/ffii/core/setting/Setting.java new file mode 100644 index 0000000..9450546 --- /dev/null +++ b/src/main/java/com/ffii/core/setting/Setting.java @@ -0,0 +1,64 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.setting; + +import java.io.Serializable; + +public class Setting implements Serializable { + + private static final long serialVersionUID = 3925955875238868120L; + + private String category; + + private String type; + + private String name; + + private String value; + + /** default constructor */ + public Setting() { + + } + + public String getCategory() { + return category; + } + + public void setCategory(String category) { + this.category = category; + } + + public String getType() { + return type; + } + + public void setType(String type) { + this.type = type; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getValue() { + return value; + } + + public void setValue(String value) { + this.value = value; + } + +} diff --git a/src/main/java/com/ffii/core/setting/service/SettingsService.java b/src/main/java/com/ffii/core/setting/service/SettingsService.java new file mode 100644 index 0000000..7de097c --- /dev/null +++ b/src/main/java/com/ffii/core/setting/service/SettingsService.java @@ -0,0 +1,169 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.setting.service; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.setting.Setting; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; + +/** + * System Settings Service + * + * @author Patrick + */ +@Service +public class SettingsService { + + private static final String SQL_LOAD_SETTINGS = "SELECT * FROM settings ORDER BY category, name"; + + private static final String SQL_INSERT_OR_UPDATE_SETTING = "INSERT INTO settings (`name`, `value`) VALUES (:name, :value) ON DUPLICATE KEY UPDATE `name` = VALUES(`name`), `value` = VALUES(`value`)"; + + /** + * Settings cache + */ + private static Map SETTINGS = null; + + @Autowired + private JdbcDao jdbcDao; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> searchSettings(Map args) { + + StringBuilder sql = new StringBuilder("SELECT * FROM settings WHERE 1=1"); + + if (args.containsKey("category")) sql.append(" AND category = :category"); + if (args.containsKey("type")) sql.append(" AND type = :type"); + if (args.containsKey("name")) sql.append(" AND name = :name"); + + sql.append(" ORDER BY category, name"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + /** + * Load and return a Map of all system settings from database + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map loadSettingsMap() { + List settings = jdbcDao.query(SQL_LOAD_SETTINGS, Setting.class, null, 0); + Map settingsMap = new HashMap(); + for (Setting setting : settings) { + settingsMap.put(setting.getName(), setting); + } + return settingsMap; + } + + /** + * @param name + * the name of the setting + * @param defaultValue + * the default value to return if setting is not found + * + * @return the String value of the setting, or the default value if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public String getString(String name, String defaultValue) { + if (SETTINGS == null) SETTINGS = loadSettingsMap(); + return SETTINGS.get(name) != null ? SETTINGS.get(name).getValue() : defaultValue; + } + + /** + * @param name + * the name of the setting + * + * @return the String value of the setting, or {@code null} if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public String getString(String name) { + return getString(name, null); + } + + /** + * @param name + * the name of the setting + * @param defaultValue + * the default value to return if setting is not found + * + * @return the int value of the setting, or the default value if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public int getInt(String name, int defaultValue) { + return NumberUtils.toInt(getString(name), defaultValue); + } + + /** + * @param name + * the name of the setting + * + * @return the int value of the setting, or zero (0) if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public int getInt(String name) { + return getInt(name, 0); + } + + /** + * @param name + * the name of the setting + * @param defaultValue + * the default value to return if setting is not found + * + * @return the double value of the setting, or the default value if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public double getDouble(String name, double defaultValue) { + return NumberUtils.toDouble(getString(name), defaultValue); + } + + /** + * @param name + * the name of the setting + * + * @return the double value of the setting, or zero (0.0) if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public double getDouble(String name) { + return getDouble(name, 0.0d); + } + + /** + * @param name + * the name of the setting + * @param value + * the value of the setting + */ + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int saveSetting(String name, String value) { + Map args = new HashMap(2); + args.put(Params.NAME, name); + args.put(Params.VALUE, value); + return jdbcDao.executeUpdate(SQL_INSERT_OR_UPDATE_SETTING, args); + } + + /** + * Reset the settings cache + */ + public void resetSettingsCache() { + // simply set the settings cache to null + SETTINGS = null; + } + +} diff --git a/src/main/java/com/ffii/core/support/SimpleDateEditor.java b/src/main/java/com/ffii/core/support/SimpleDateEditor.java new file mode 100644 index 0000000..fd6b521 --- /dev/null +++ b/src/main/java/com/ffii/core/support/SimpleDateEditor.java @@ -0,0 +1,45 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.support; + +import java.beans.PropertyEditorSupport; +import java.util.Date; + +import org.springframework.util.StringUtils; + +import com.ffii.core.utils.DateUtils; + +/** + * Property Editor for Date in the format defined by {@link DateUtils#PARSE_PATTERNS}
+ *

+ * Defaults to null if cannot be parsed, never throw an Exception + *

+ * + * @see DateUtils#parseDateStrictly(String, String[], Date) + * + * @author Patrick + */ +public class SimpleDateEditor extends PropertyEditorSupport { + + @Override + public void setAsText(String text) throws IllegalArgumentException { + if (StringUtils.hasText(text)) + setValue(DateUtils.parseDateStrictly(text, DateUtils.PARSE_PATTERNS, null)); + else + setValue(null); + } + + @Override + public String getAsText() { + return DateUtils.formatDate((Date) getValue()); + } + +} diff --git a/src/main/java/com/ffii/core/support/SimpleDecimalEditor.java b/src/main/java/com/ffii/core/support/SimpleDecimalEditor.java new file mode 100644 index 0000000..e8e0b03 --- /dev/null +++ b/src/main/java/com/ffii/core/support/SimpleDecimalEditor.java @@ -0,0 +1,38 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.support; + +import java.beans.PropertyEditorSupport; +import java.math.BigDecimal; + +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.StringUtils; + +/** + * Property Editor for BigDecimal (Defaults to null if cannot be parsed, never throw an Exception) + * + * @see NumberUtils#toDecimal(String, BigDecimal) + * + * @author Patrick + */ +public class SimpleDecimalEditor extends PropertyEditorSupport { + + @Override + public void setAsText(String value) throws IllegalArgumentException { + setValue(NumberUtils.toDecimal(value, null)); + } + + @Override + public String getAsText() { + return (getValue() == null ? StringUtils.EMPTY : getValue().toString()); + } + +} diff --git a/src/main/java/com/ffii/core/support/SimpleDoubleEditor.java b/src/main/java/com/ffii/core/support/SimpleDoubleEditor.java new file mode 100644 index 0000000..1140889 --- /dev/null +++ b/src/main/java/com/ffii/core/support/SimpleDoubleEditor.java @@ -0,0 +1,37 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.support; + +import java.beans.PropertyEditorSupport; + +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.StringUtils; + +/** + * Property Editor for Double (Defaults to null if cannot be parsed, never throw an Exception) + * + * @see NumberUtils#toDouble(String, Double) + * + * @author Patrick + */ +public class SimpleDoubleEditor extends PropertyEditorSupport { + + @Override + public void setAsText(String value) throws IllegalArgumentException { + setValue(NumberUtils.toDouble(value, null)); + } + + @Override + public String getAsText() { + return (getValue() == null ? StringUtils.EMPTY : getValue().toString()); + } + +} diff --git a/src/main/java/com/ffii/core/support/SimpleIntegerEditor.java b/src/main/java/com/ffii/core/support/SimpleIntegerEditor.java new file mode 100644 index 0000000..ff8ac74 --- /dev/null +++ b/src/main/java/com/ffii/core/support/SimpleIntegerEditor.java @@ -0,0 +1,37 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.support; + +import java.beans.PropertyEditorSupport; + +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.StringUtils; + +/** + * Property Editor for Integer (Defaults to null if cannot be parsed, never throw an Exception) + * + * @see NumberUtils#toInt(String, Integer) + * + * @author Patrick + */ +public class SimpleIntegerEditor extends PropertyEditorSupport { + + @Override + public void setAsText(String value) throws IllegalArgumentException { + setValue(NumberUtils.toInt(value, null)); + } + + @Override + public String getAsText() { + return (getValue() == null ? StringUtils.EMPTY : getValue().toString()); + } + +} diff --git a/src/main/java/com/ffii/core/support/SimpleLongEditor.java b/src/main/java/com/ffii/core/support/SimpleLongEditor.java new file mode 100644 index 0000000..e1a1c83 --- /dev/null +++ b/src/main/java/com/ffii/core/support/SimpleLongEditor.java @@ -0,0 +1,37 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.support; + +import java.beans.PropertyEditorSupport; + +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.StringUtils; + +/** + * Property Editor for Long (Defaults to null if cannot be parsed, never throw an Exception) + * + * @see NumberUtils#toLong(String, Long) + * + * @author Patrick + */ +public class SimpleLongEditor extends PropertyEditorSupport { + + @Override + public void setAsText(String value) throws IllegalArgumentException { + setValue(NumberUtils.toLong(value, null)); + } + + @Override + public String getAsText() { + return (getValue() == null ? StringUtils.EMPTY : getValue().toString()); + } + +} diff --git a/src/main/java/com/ffii/core/support/SimpleStringTrimToEmptyEditor.java b/src/main/java/com/ffii/core/support/SimpleStringTrimToEmptyEditor.java new file mode 100644 index 0000000..ada9880 --- /dev/null +++ b/src/main/java/com/ffii/core/support/SimpleStringTrimToEmptyEditor.java @@ -0,0 +1,41 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.support; + +import java.beans.PropertyEditorSupport; + +import com.ffii.core.utils.StringUtils; + +/** + *

+ * Property Editor for String + *

+ *

+ * Use {@link StringUtils.trimToEmpty()} when binding the value and getting the value to display + *

+ * + * @see StringUtils#trimToEmpty(String) + * + * @author Patrick + */ +public class SimpleStringTrimToEmptyEditor extends PropertyEditorSupport { + + @Override + public void setAsText(String value) throws IllegalArgumentException { + setValue(StringUtils.trimToEmpty(value)); + } + + @Override + public String getAsText() { + return (getValue() == null ? StringUtils.EMPTY : StringUtils.trimToEmpty((String) getValue())); + } + +} diff --git a/src/main/java/com/ffii/core/support/SimpleStringTrimToNullEditor.java b/src/main/java/com/ffii/core/support/SimpleStringTrimToNullEditor.java new file mode 100644 index 0000000..26703d7 --- /dev/null +++ b/src/main/java/com/ffii/core/support/SimpleStringTrimToNullEditor.java @@ -0,0 +1,42 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.support; + +import java.beans.PropertyEditorSupport; + +import com.ffii.core.utils.StringUtils; + +/** + *

+ * Property Editor for String + *

+ *

+ * Use {@link StringUtils.trimToNull()} when binding the value, but use {@link StringUtils.trimToEmpty()} when getting the value to display + *

+ * + * @see StringUtils#trimToNull(String) + * @see StringUtils#trimToEmpty(String) + * + * @author Patrick + */ +public class SimpleStringTrimToNullEditor extends PropertyEditorSupport { + + @Override + public void setAsText(String value) throws IllegalArgumentException { + setValue(StringUtils.trimToNull(value)); + } + + @Override + public String getAsText() { + return (getValue() == null ? StringUtils.EMPTY : StringUtils.trimToEmpty((String) getValue())); + } + +} diff --git a/src/main/java/com/ffii/core/utils/ArgsBuilder.java b/src/main/java/com/ffii/core/utils/ArgsBuilder.java new file mode 100644 index 0000000..7bafd71 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/ArgsBuilder.java @@ -0,0 +1,17 @@ +package com.ffii.core.utils; + +import java.util.Map; + +/** + * @author fung + */ +public class ArgsBuilder extends MapBuilder { + + public ArgsBuilder() { + } + + public ArgsBuilder(Map args) { + super(args); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/utils/BooleanUtils.java b/src/main/java/com/ffii/core/utils/BooleanUtils.java new file mode 100644 index 0000000..ea4feea --- /dev/null +++ b/src/main/java/com/ffii/core/utils/BooleanUtils.java @@ -0,0 +1,67 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +public class BooleanUtils extends org.apache.commons.lang3.BooleanUtils { + + /** + *

+ * For the case of {@code Number}, only if the value is {@code 1} will return {@code true}. Otherwise, {@code false} is returned. + *

+ *

+ * For the case of {@code String}, {@code 'true'}, {@code 'on'} or {@code 'yes'} (case insensitive) will return {@code true}. Otherwise, {@code false} is + * returned. + *

+ *

+ * For the case of {@code Boolean}, only if the {@code Boolean} value is {@code true} will return {@code true}, handling {@code null} by returning + * {@code false}. + *

+ *

+ * For any other cases including {@code null} will return {@code false}. + *

+ */ + public static boolean isTrue(Object obj) { + if (obj instanceof Number) { + return ((Number) obj).intValue() == 1; + } else if (obj instanceof String) { + return toBoolean((String) obj); + } else { + return Boolean.TRUE.equals(obj); + } + } + + /** + *

+ * For the case of {@code Number}, only if the value is {@code 0} will return {@code true}. Otherwise, {@code false} is returned. + *

+ *

+ * For the case of {@code String}, {@code true} is returned unless the value is {@code 'true'}, {@code 'on'} or {@code 'yes'} (case insensitive) which will + * return {@code false}. + *

+ *

+ * For the case of {@code Boolean}, only if the {@code Boolean} value is {@code false} will return {@code true}, handling {@code null} by returning + * {@code false}. + *

+ *

+ * For any other cases including {@code null} will return {@code false}. + *

+ */ + public static boolean isFalse(Object obj) { + if (obj instanceof Number) { + return ((Number) obj).intValue() == 0; + } else if (obj instanceof String) { + return !toBoolean((String) obj); + } else { + return Boolean.FALSE.equals(obj); + } + } + +} diff --git a/src/main/java/com/ffii/core/utils/CheckDigitUtils.java b/src/main/java/com/ffii/core/utils/CheckDigitUtils.java new file mode 100644 index 0000000..d1880e5 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/CheckDigitUtils.java @@ -0,0 +1,66 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +/** + * CheckDigitUtils + * + * @author Patrick + */ +public abstract class CheckDigitUtils { + + /* + * ISO/IEC 7812-1 Annex B + * Check digit calc method + */ + public static int luhnCalc(String digitsString) { + int sum = 0; + boolean alternate = false; + for (int i = 0; i < digitsString.length(); i++) { + int n = Integer.parseInt(digitsString.substring(i, i + 1)); + if (alternate) { + n *= 2; + if (n > 9) { + n = (n % 10) + 1; + } + } + sum += n; + alternate = !alternate; + } + return ((sum * 9) % 10); + } + + /* + * ISO/IEC 7812-1 Annex B + * Check digit check method + */ + public static boolean luhnCheck(String digitsStringWithCheckDigit) { + int sum = 0; + boolean alternate = false; + for (int i = digitsStringWithCheckDigit.length() - 1; i >= 0; i--) { + try { + int n = Integer.parseInt(digitsStringWithCheckDigit.substring(i, i + 1)); + if (alternate) { + n *= 2; + if (n > 9) { + n = (n % 10) + 1; + } + } + sum += n; + alternate = !alternate; + } catch (NumberFormatException nfe) { + continue; + } + } + return (sum % 10 == 0); + } + +} diff --git a/src/main/java/com/ffii/core/utils/CriteriaArgsBuilder.java b/src/main/java/com/ffii/core/utils/CriteriaArgsBuilder.java new file mode 100644 index 0000000..c5d1651 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/CriteriaArgsBuilder.java @@ -0,0 +1,119 @@ +package com.ffii.core.utils; + +import java.util.HashMap; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.springframework.web.bind.ServletRequestBindingException; + +/** + * ArgsBuilder of Criteria + * + * @see {@link CriteriaUtils} + * @author fung + */ +public class CriteriaArgsBuilder { + + private Map args; + private HttpServletRequest request; + + public CriteriaArgsBuilder(HttpServletRequest request) { + args = new HashMap(); + this.request = request; + } + + public CriteriaArgsBuilder(HttpServletRequest request, Map args) { + this.args = args; + this.request = request; + } + + public CriteriaArgsBuilder addStringExact(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addStringExact(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addStringLike(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addStringLike(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addString(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addString(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addStringContains(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addStringContains(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addStringStartsWith(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addStringStartsWith(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addStringEndsWith(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addStringEndsWith(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addStringList(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addStringList(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addStringCsv(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addStringCsv(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addInteger(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addInteger(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addNonZeroInteger(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addNonZeroInteger(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addIntegerList(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addIntegerList(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addNonZeroIntegerList(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addNonZeroIntegerList(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addLong(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addLong(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addNonZeroLong(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addNonZeroLong(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addDate(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addDate(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addDateTo(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addDateTo(request, args, paramName); + return this; + } + + public CriteriaArgsBuilder addBoolean(String paramName) throws ServletRequestBindingException { + CriteriaUtils.addBoolean(request, args, paramName); + return this; + } + + public Map toMap() { + return this.args; + } +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/utils/CriteriaUtils.java b/src/main/java/com/ffii/core/utils/CriteriaUtils.java new file mode 100644 index 0000000..5d14dce --- /dev/null +++ b/src/main/java/com/ffii/core/utils/CriteriaUtils.java @@ -0,0 +1,191 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.sql.Date; +import java.util.ArrayList; +import java.util.Calendar; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.springframework.web.bind.ServletRequestBindingException; + +import com.ffii.core.utils.web.ServletRequestUtils; + +/** + * Utils for getting parameter values from HTTP Request and put them into a criteria map if found + * + * @author Patrick + */ +public abstract class CriteriaUtils { + + /** + * Alias for {@link #addString(HttpServletRequest, Map, String)} + */ + public static void addStringExact(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + addString(request, args, paramName); + } + + /** + * Alias for {@link #addStringContains(HttpServletRequest, Map, String)} + */ + public static void addStringLike(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + addStringContains(request, args, paramName); + } + + /** + * Add a String (an exact value for using equal sign in SQL) parameter to criteria. Usually used for exact string search. + */ + public static void addString(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + String value = ServletRequestUtils.getTrimmedStringParameter(request, paramName); + if (value != null) args.put(paramName, value); + } + + /** + * Add a String (a substring value for using LIKE in SQL) parameter to criteria. Usually used for substring search for values that contains the + * input value. + */ + public static void addStringContains(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + String value = ServletRequestUtils.getTrimmedStringParameter(request, paramName); + if (value != null) args.put(paramName, StringUtils.PERCENT + value + StringUtils.PERCENT); + } + + /** + * Add a String (a substring value for using LIKE in SQL) parameter to criteria. Usually used for substring search for values that starts with + * the input value. + */ + public static void addStringStartsWith(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + String value = ServletRequestUtils.getTrimmedStringParameter(request, paramName); + if (value != null) args.put(paramName, value + StringUtils.PERCENT); + } + + /** + * Add a String (a substring value for using LIKE in SQL) parameter to criteria. Usually used for substring search for values that ends with + * the input value. + */ + public static void addStringEndsWith(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + String value = ServletRequestUtils.getTrimmedStringParameter(request, paramName); + if (value != null) args.put(paramName, StringUtils.PERCENT + value); + } + + /** + * Add String List parameter to criteria. + */ + public static void addStringList(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + String[] params = ServletRequestUtils.getStringParameters(request, paramName); + if (params.length > 0) { + List value = new ArrayList(); + for (int i = 0; i < params.length; i++) + if (StringUtils.isNotBlank(params[i])) value.add(params[i]); + if (value.size() > 0) args.put(paramName, value); + } + } + + /** + * Add String CSV parameter to criteria. + */ + public static void addStringCsv(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + String text = ServletRequestUtils.getStringParameter(request, paramName); + if (StringUtils.isNotEmpty(text)) { + String[] params = text.split(","); + List values = new ArrayList(); + for (int i = 0; i < params.length; i++) + values.add(params[i]); + args.put(paramName, values); + } + } + + /** + * Add an Integer parameter to criteria. + */ + public static void addInteger(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + Integer value = ServletRequestUtils.getIntParameter(request, paramName, null); + if (value != null) args.put(paramName, value); + } + + /** + * Add a non-zero Integer parameter to criteria. + */ + public static void addNonZeroInteger(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + Integer value = ServletRequestUtils.getIntParameter(request, paramName, null); + if (value != null && value.intValue() != 0) args.put(paramName, value); + } + + /** + * Add Integer List parameter to criteria. + */ + public static void addIntegerList(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + int[] params = ServletRequestUtils.getIntParameters(request, paramName); + if (params.length > 0) { + List values = new ArrayList(); + for (int i = 0; i < params.length; i++) + values.add(params[i]); + args.put(paramName, values); + } + } + + /** + * Add non-zero Integer List parameter to criteria. + */ + public static void addNonZeroIntegerList(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + int[] params = ServletRequestUtils.getIntParameters(request, paramName); + if (params.length > 0) { + List values = new ArrayList(); + for (int i = 0; i < params.length; i++) + if (params[i] != 0) values.add(params[i]); + args.put(paramName, values); + } + } + + /** + * Add a Long parameter to criteria. + */ + public static void addLong(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + Long value = ServletRequestUtils.getLongParameter(request, paramName, null); + if (value != null) args.put(paramName, value); + } + + /** + * Add a non-zero Long parameter to criteria. + */ + public static void addNonZeroLong(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + Long value = ServletRequestUtils.getLongParameter(request, paramName, null); + if (value != null && value.longValue() != 0L) args.put(paramName, value); + } + + /** + * Add a SQL Date parameter to criteria. Usually used for FROM date range search, or exact date search. + */ + public static void addDate(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + Date value = ServletRequestUtils.getSqlDateParameter(request, paramName); + if (value != null) args.put(paramName, value); + } + + /** + * Add a SQL Date (plus 1 day) parameter to criteria. Usually used for {@code TO} date range search. + */ + public static void addDateTo(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + Date value = ServletRequestUtils.getSqlDateParameter(request, paramName); + if (value != null) args.put(paramName, DateUtils.add(value.getClass(), value, Calendar.DAY_OF_MONTH, 1)); + } + + /** + * Add a Boolean parameter to criteria if it's not {@code null}. Accepts "true", "on", "yes" (any case) and "1" as values for true; treats every other + * non-empty value as false (i.e. parses leniently). + */ + public static void addBoolean(HttpServletRequest request, Map args, String paramName) throws ServletRequestBindingException { + Boolean value = ServletRequestUtils.getBooleanParameter(request, paramName); + if (value != null) args.put(paramName, value); + } + +} diff --git a/src/main/java/com/ffii/core/utils/DataBindUtils.java b/src/main/java/com/ffii/core/utils/DataBindUtils.java new file mode 100644 index 0000000..fb76b25 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/DataBindUtils.java @@ -0,0 +1,103 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.util.Map; + +import org.apache.commons.lang3.ArrayUtils; +import org.springframework.beans.MutablePropertyValues; +import org.springframework.web.bind.WebDataBinder; + +import com.ffii.core.support.SimpleDateEditor; +import com.ffii.core.support.SimpleIntegerEditor; +import com.ffii.core.support.SimpleStringTrimToNullEditor; + +/** + * DataBindUtils + * + * @author Patrick + */ +public abstract class DataBindUtils { + /** coreFields */ + public static final String[] coreFields = { Params.ID, "ownerId", "deleted", "createdBy", "modifiedBy", "created", "modified", "password" }; + + /** + * + * @param object + * @return WebDataBinder + */ + private static WebDataBinder createBinder(Object object) { + WebDataBinder binder = new WebDataBinder(object); + binder.registerCustomEditor(String.class, new SimpleStringTrimToNullEditor()); + binder.registerCustomEditor(Integer.class, new SimpleIntegerEditor()); + binder.registerCustomEditor(java.util.Date.class, new SimpleDateEditor()); + return binder; + } + + /** + * Binds data using {@link WebDataBinder} with the following custom editors:- + * + *
    + *
  • {@link SimpleStringTrimToNullEditor}
  • + *
  • {@link SimpleIntegerEditor}
  • + *
  • {@link SimpleDateEditor}
  • + *
+ * + * @param record + * record Map + * @param object + * the target object to bind onto + * @param disallowFields + * optional + */ + public static void bindRecord(Map record, Object object, String... disallowFields) { + WebDataBinder binder = createBinder(object); + binder.setDisallowedFields(disallowFields); + binder.bind(new MutablePropertyValues(record)); + }; + + /** + * Binds data using {@link WebDataBinder} with the following custom editors:- + * + *
    + *
  • {@link SimpleStringTrimToNullEditor}
  • + *
  • {@link SimpleIntegerEditor}
  • + *
  • {@link SimpleDateEditor}
  • + *
+ * + *

+ * Important: The following system fields will NOT be binded for security reasons. + *

    + *
  • id
  • + *
  • ownerId
  • + *
  • deleted
  • + *
  • createdBy
  • + *
  • modifiedBy
  • + *
  • created
  • + *
  • modified
  • + *
  • password
  • + *
+ *

+ * + * @param record + * record Map + * @param object + * the target object to bind onto + * @param disallowFields + * optional + */ + public static void bindRecordWithoutCore(Map record, Object object, String... disallowFields) { + WebDataBinder binder = createBinder(object); + + binder.setDisallowedFields(ArrayUtils.addAll(coreFields, disallowFields)); + binder.bind(new MutablePropertyValues(record)); + }; +} diff --git a/src/main/java/com/ffii/core/utils/DateUtils.java b/src/main/java/com/ffii/core/utils/DateUtils.java new file mode 100644 index 0000000..b87376d --- /dev/null +++ b/src/main/java/com/ffii/core/utils/DateUtils.java @@ -0,0 +1,1021 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.sql.Timestamp; +import java.text.DecimalFormat; +import java.text.ParseException; +import java.text.SimpleDateFormat; +import java.util.Calendar; +import java.util.Date; +import java.util.regex.Pattern; + +import org.apache.commons.lang3.time.FastDateFormat; + +/** + * Utility class for date parsing and formatting. + * + * @see FastDateFormat + * @see ISO 8601 + * @see RFC 822 + * + * @author Patrick + */ +public abstract class DateUtils extends org.apache.commons.lang3.time.DateUtils { + + /** Used to format double digit hours, minutes, and seconds */ + private static final DecimalFormat DF00 = new DecimalFormat("00"); + + /** RegEx pattern to test 24-hour 4-digit time format */ + private static final Pattern PATTERN_24HR_TIME_STRING = Pattern.compile("^(([0-1][0-9])|(2[0-3]))[0-5][0-9]$"); + + /** + * HK date formatter for date without time zone. The format used is dd/MM/yyyy. + */ + public static final FastDateFormat HK_DATE_FORMAT = FastDateFormat.getInstance("dd/MM/yyyy"); + + /** + * HK date formatter for datetime. The format used is dd/MM/yyyy HH:mm:ss. + */ + public static final FastDateFormat HK_DATETIME_FORMAT = FastDateFormat.getInstance("dd/MM/yyyy HH:mm:ss"); + + /** + * SQL date formatter for date without time zone. The format used is yyyy-MM-dd. + */ + public static final FastDateFormat SQL_DATE_FORMAT = FastDateFormat.getInstance("yyyy-MM-dd"); + + /** + * Ext JS ISO8601 formatter for date-time with time zone. The format used is yyyy-MM-dd'T'HH:mm:ssZZ. + */ + public static final FastDateFormat ISO_JS_DATETIME_TIME_ZONE_FORMAT = FastDateFormat.getInstance("yyyy-MM-dd'T'HH:mm:ss.SSSZ"); + + /** + * Default parse patterns + *
    + *
  1. dd/MM/yyyy + *
  2. dd/MM/yyyy HH:mm:ss + *
  3. yyyy-MM-dd + *
  4. yyyy-MM-dd'T'HH:mm:ss + *
  5. yyyy-MM-dd'T'HH:mm:ss.SSS'Z' + *
  6. yyyy-MM-dd'T'HH:mm:ss.SSSZ + *
+ */ + public static final String[] PARSE_PATTERNS = { "dd/MM/yyyy","dd/MM/yyyy HH:mm:ss", "yyyy-MM-dd", "yyyy-MM-dd'T'HH:mm:ss", "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'", "yyyy-MM-dd'T'HH:mm:ss.SSSZ" }; + + /** + * PayPal parse patterns + *
    + *
  1. HH:mm:ss MMM dd, yyyy z + *
+ */ + public static final String[] PARSE_PATTERNS_PAYPAL = { "HH:mm:ss MMM dd, yyyy z" }; + + /** + * Formats a Date as String using the default pattern + * + * @param date + * the date object, may be {@code null} + * + * @return the formatted date string, or "" if date is {@code null} + */ + public static String formatDate(Date date) { + return formatDate(date, StringUtils.EMPTY); + } + + /** + * Formats a Date as String using the default pattern, with a fallback default value if the date is null + * + * @param date + * the date object, may be {@code null} + * @param defaultValue + * the value to return if date is {@code null} + * + * @return the formatted date string, or the default value if date is {@code null} + */ + public static String formatDate(Date date, String defaultValue) { + if (date == null) return defaultValue; + return HK_DATE_FORMAT.format(date); + } + + /** + * Formats a Date as String using the provided pattern, with a fallback default value if the date is null + * + * @param date + * the date object, may be {@code null} + * @param pattern + * {@link java.text.SimpleDateFormat} compatible pattern + * @param defaultValue + * the value to return if date is {@code null} + * + * @return the formatted date string, or the default value if date is {@code null} + * + * @throws IllegalArgumentException + * if pattern is invalid + */ + public static String formatDate(Date date, String pattern, String defaultValue) { + if (date == null) return defaultValue; + if (HK_DATE_FORMAT.getPattern().equals(pattern)) { + return HK_DATE_FORMAT.format(date); + } else if (SQL_DATE_FORMAT.getPattern().equals(pattern)) { + return SQL_DATE_FORMAT.format(date); + } else { + return FastDateFormat.getInstance(pattern).format(date); + } + } + + /** + *

+ * Parses a string representing a date by trying a variety of different parsers. + *

+ *

+ * The parse will try each parse pattern in turn. A parse is only deemed successful if it parses the whole of the input string. If no parse patterns match, + * the default value is returned. + *

+ *

+ * The parser parses strictly - it does not allow for dates such as "February 942, 1996". + *

+ * + * @param str + * the date to parse, not null + * @param parsePatterns + * the date format patterns to use, see {@link SimpleDateFormat}, not null + * @param defaultValue + * the default value to use as fallback + * + * @return the parsed {@link Date} object + * + * @see DateUtils#parseDateStrictly(String, String[]) + */ + public static Date parseDateStrictly(String str, String[] parsePatterns, Date defaultValue) { + if (str == null) return defaultValue; + try { + return parseDateStrictly(str, parsePatterns); + } catch (ParseException e) { + return defaultValue; + } + } + + /** + *

+ * Parses a string representing a date by trying a variety of different parsers. + *

+ *

+ * The parse will try each parse pattern in turn. A parse is only deemed successful if it parses the whole of the input string. If no parse patterns match, + * the default value is returned. + *

+ *

+ * The parser parses strictly - it does not allow for dates such as "February 942, 1996". + *

+ * + * @param str + * the date to parse, not null + * @param defaultValue + * the default value to use as fallback + * + * @return the parsed {@link Date} object + * + * @see DateUtils#parseDateStrictly(String, String[]) + */ + public static Date parseDateStrictly(String str, Date defaultValue) { + return parseDateStrictly(str, PARSE_PATTERNS, defaultValue); + } + + /** + * Clone a date + * + * @return The cloned date, or null if input date is null + */ + @SuppressWarnings("unchecked") + public static T clone(Date date) { + return (date == null) ? null : (T) date.clone(); + } + + /** + * Check if the time is valid 24-hour time + */ + @Deprecated + public static boolean isValid24HourTime(int time) { + int hour = time / 100; + int minute = time - hour * 100; + + // invalid hour + if (hour < 0 || hour > 23) return false; + + // invalid minute + if (minute < 0 || minute > 59) return false; + + return true; + } + + /** + * Check if the time string is valid 24-hour format (4 digit without any symbols) + */ + public static final boolean isValid24HourTime(String timeString) { + if (timeString == null || timeString.length() != 4) { + // if it's null or not 4-digit + return false; + } else { + // else check against RegEx + return PATTERN_24HR_TIME_STRING.matcher(timeString).matches(); + } + } + + /** + * Converts 24-hour time string to a long value in millisecond + * + * @param str + * 24-hour time string in the format of "hh:mm" or "hhmm" + */ + public static long convertTimeStringToMillisecond(String str) { + if (StringUtils.isNotBlank(str)) { + str = StringUtils.remove(str, ':'); + int time = NumberUtils.toInt(str); + int hour = time / 100; + int minute = time - hour * 100; + return hour * 3600000 + minute * 60000; + } + return 0L; + } + + /** + * Returns a new Date object by adding the time value from a 24-hour time string + * + * @param clazz + * the Date class to return + * @param date + * the Date object that the time to add to, will not be changed + * @param str + * 24-hour time string in the format of "hh:mm" or "hhmm" + */ + @SuppressWarnings("unchecked") + public static T addTimeToDate(Class clazz, Date date, String str) { + if (date != null && StringUtils.isNotBlank(str)) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + c.set(Calendar.HOUR_OF_DAY, 0); + c.set(Calendar.MINUTE, 0); + c.set(Calendar.SECOND, 0); + c.set(Calendar.MILLISECOND, 0); + long time = c.getTimeInMillis() + convertTimeStringToMillisecond(str); + if (clazz == Date.class) { + return (T) new Date(time); + } else if (clazz == java.sql.Date.class) { + return (T) new java.sql.Date(time); + } else if (clazz == Timestamp.class) { + return (T) new java.sql.Timestamp(time); + } else { + throw new UnsupportedOperationException(clazz.getName() + " is not supported."); + } + } + return null; + } + + /** + * Returns today with only the date component + */ + public static Date getToday() { + return truncate(new Date(), Calendar.DAY_OF_MONTH); + } + + /** + * Returns the week number within the current year (e.g. if the date is within the first week of the year, it will return 1) + * + * @param date + * non-{@code null} {@code date} object + */ + public static final int getWeekOfYear(Date date) { + Calendar calendar = Calendar.getInstance(); + calendar.setTime(date); + return calendar.get(Calendar.WEEK_OF_YEAR); + } + + /** + * Returns the week number within the current year (e.g. if the date is within the first week of the year, it will return 1), where you can specify the + * first day of the week + * + * @param date + * non-{@code null} {@code date} object + * @param firstDayOfWeek + * the first day of the week (e.g. Calendar.SUNDAY, Calendar.MONDAY, etc) + */ + public static final int getWeekOfYear(Date date, int firstDayOfWeek) { + Calendar calendar = Calendar.getInstance(); + calendar.setTime(date); + calendar.setFirstDayOfWeek(firstDayOfWeek); + return calendar.get(Calendar.WEEK_OF_YEAR); + } + + /** + * Returns {@code true} if the {@code date} is earlier than today (ignoring the time component), returns {@code false} if later than or same as today + */ + public static boolean isEarlierThanToday(Date date) { + return truncate(date, Calendar.DAY_OF_MONTH).getTime() < getToday().getTime(); + } + + /** + * Returns {@code true} if the {@code date} is later than today (ignoring the time component), returns {@code false} if earlier than or same as today + */ + public static boolean isLaterThanToday(Date date) { + return truncate(date, Calendar.DAY_OF_MONTH).getTime() > getToday().getTime(); + } + + /** + * Returns {@code true} if date {@code a} is earlier than date {@code b} (ignoring the time component), returns {@code false} if later than or same day + */ + public static boolean isEarlierThan(Date a, Date b) { + return truncate(a, Calendar.DAY_OF_MONTH).getTime() < truncate(b, Calendar.DAY_OF_MONTH).getTime(); + } + + /** + * Returns {@code true} if date {@code a} is later than date {@code b} (ignoring the time component), returns {@code false} if earlier than or same day + */ + public static boolean isLaterThan(Date a, Date b) { + return truncate(a, Calendar.DAY_OF_MONTH).getTime() > truncate(b, Calendar.DAY_OF_MONTH).getTime(); + } + + /** + * Returns {@code true} if date {@code a} is the same date as date {@code b} (ignoring the time component), else returns {@code false} + */ + public static boolean isSameDate(Date a, Date b) { + return truncate(a, Calendar.DAY_OF_MONTH).getTime() == truncate(b, Calendar.DAY_OF_MONTH).getTime(); + } + + /** + * Calculate the difference in days of (toDate - fromDate), ignoring the time component of both dates. + */ + public static long getDiffInDays(Date fromDate, Date toDate) { + // ignore the time component of both dates + Date fromDateT = truncate(fromDate, Calendar.DAY_OF_MONTH); + Date toDateT = truncate(toDate, Calendar.DAY_OF_MONTH); + + // calculate the difference in ms divided by MILLIS_PER_DAY, thus the difference in days + return (toDateT.getTime() - fromDateT.getTime()) / MILLIS_PER_DAY; + } + + /** + * Calculate the difference in minutes of (toDate - fromDate), by truncating up to the minute of both dates. + */ + public static final long getDiffInMins(Date fromDate, Date toDate) { + // truncate up to the minute of both dates + Date fromDateT = DateUtils.truncate(fromDate, Calendar.MINUTE); + Date toDateT = DateUtils.truncate(toDate, Calendar.MINUTE); + + return (toDateT.getTime() - fromDateT.getTime()) / DateUtils.MILLIS_PER_MINUTE; + } + + /** + * Calculate time diff in mins (same day or within 1 day) + */ + public static final int getDiffInMins(String timeFrom, String timeTo) { + int diffMins = 0; + + // defaults to "0000" if empty + if (StringUtils.isBlank(timeFrom)) timeFrom = "0000"; + if (StringUtils.isBlank(timeTo)) timeTo = "0000"; + + if (!isValid24HourTime(timeFrom) || !isValid24HourTime(timeTo)) { + return diffMins; + } + + try { + int timeFromHour = Integer.parseInt(timeFrom.substring(0, 2)); + int timeFromMin = Integer.parseInt(timeFrom.substring(2)); + int timeToHour = Integer.parseInt(timeTo.substring(0, 2)); + int timeToMin = Integer.parseInt(timeTo.substring(2)); + + diffMins += 60 - timeFromMin; + diffMins += timeToMin; + diffMins += ((timeToHour - 1) - timeFromHour) * 60; + + if (timeToHour < timeFromHour) { + // may be across a 00:00 + diffMins += 24 * 60; + } + } catch (Exception e) { + } + + return diffMins; + } + + public static final String get24HourTimeFromDate(Date date) { + if (date == null) return StringUtils.EMPTY; + Calendar calendar = Calendar.getInstance(); + calendar.setTime(date); + return DF00.format(calendar.get(Calendar.HOUR_OF_DAY)) + DF00.format(calendar.get(Calendar.MINUTE)); + } + + public static final String get24HourTimeFromDateWithColon(Date date) { + if (date == null) return StringUtils.EMPTY; + Calendar calendar = Calendar.getInstance(); + calendar.setTime(date); + return DF00.format(calendar.get(Calendar.HOUR_OF_DAY)) + ":" + DF00.format(calendar.get(Calendar.MINUTE)); + } + + /** + *

+ * Adds or subtracts the specified amount of time to the given calendar field to the {@code date} returning a new object (the original {@code date} object + * is unchanged), based on the calendar's rules. + *

+ *

+ * For example, to subtract 5 days from the {@code date}, you can achieve it by calling:
+ * {@code add(date, Calendar.DAY_OF_MONTH, -5)}. + *

+ * + * @param clazz + * the date class to return (supports {@link java.util.Date}, {@link java.sql.Date}, {@link java.sql.Timestamp}) + * @param date + * the {@code date}, not {@code null} + * @param calendarField + * the calendar field to add to (e.g. {@code Calendar.DAY_OF_MONTH}) + * @param amount + * the amount to add, may be negative + * + * @return the new {@code date} object with the amount added + * + * @throws IllegalArgumentException + * if the {@code date} is {@code null} + * + * @see Calendar#add(int, int) + */ + @SuppressWarnings("unchecked") + public static T add(Class clazz, Date date, int calendarField, int amount) { + if (date == null) { + throw new IllegalArgumentException("The date must not be null"); + } + Calendar c = Calendar.getInstance(); + c.setTime(date); + c.add(calendarField, amount); + if (clazz == Date.class) { + return (T) c.getTime(); + } else if (clazz == java.sql.Date.class) { + return (T) new java.sql.Date(c.getTimeInMillis()); + } else if (clazz == Timestamp.class) { + return (T) new java.sql.Timestamp(c.getTimeInMillis()); + } else { + throw new UnsupportedOperationException(clazz.getName() + " is not supported."); + } + } + + /** + *

+ * Adds or subtracts the specified amount of years to the {@code date} returning a new object (the original {@code date} object is unchanged), based on the + * calendar's rules. + *

+ * + * @param clazz + * the date class to return (supports {@link java.util.Date}, {@link java.sql.Date}, {@link java.sql.Timestamp}) + * @param date + * the {@code date}, not {@code null} + * @param amount + * the amount to add, may be negative + * + * @return the new {@code date} object with the amount added + * + * @throws IllegalArgumentException + * if the {@code date} is {@code null} + * + * @see Calendar#add(int, int) + */ + public static T addYears(Class clazz, Date date, int amount) { + return add(clazz, date, Calendar.YEAR, amount); + } + + /** + *

+ * Adds or subtracts the specified amount of months to the {@code date} returning a new object (the original {@code date} object is unchanged), based on the + * calendar's rules. + *

+ * + * @param clazz + * the date class to return (supports {@link java.util.Date}, {@link java.sql.Date}, {@link java.sql.Timestamp}) + * @param date + * the {@code date}, not {@code null} + * @param amount + * the amount to add, may be negative + * + * @return the new {@code date} object with the amount added + * + * @throws IllegalArgumentException + * if the {@code date} is {@code null} + * + * @see Calendar#add(int, int) + */ + public static T addMonths(Class clazz, Date date, int amount) { + return add(clazz, date, Calendar.MONTH, amount); + } + + /** + *

+ * Adds or subtracts the specified amount of days to the {@code date} returning a new object (the original {@code date} object is unchanged), based on the + * calendar's rules. + *

+ * + * @param clazz + * the date class to return (supports {@link java.util.Date}, {@link java.sql.Date}, {@link java.sql.Timestamp}) + * @param date + * the {@code date}, not {@code null} + * @param amount + * the amount to add, may be negative + * + * @return the new {@code date} object with the amount added + * + * @throws IllegalArgumentException + * if the {@code date} is {@code null} + * + * @see Calendar#add(int, int) + */ + public static T addDays(Class clazz, Date date, int amount) { + return add(clazz, date, Calendar.DAY_OF_MONTH, amount); + } + + /** + *

+ * Adds or subtracts the specified amount of hours to the {@code date} returning a new object (the original {@code date} object is unchanged), based on the + * calendar's rules. + *

+ * + * @param clazz + * the date class to return (supports {@link java.util.Date}, {@link java.sql.Date}, {@link java.sql.Timestamp}) + * @param date + * the {@code date}, not {@code null} + * @param amount + * the amount to add, may be negative + * + * @return the new {@code date} object with the amount added + * + * @throws IllegalArgumentException + * if the {@code date} is {@code null} + * + * @see Calendar#add(int, int) + */ + public static T addHours(Class clazz, Date date, int amount) { + return add(clazz, date, Calendar.HOUR_OF_DAY, amount); + } + + /** + *

+ * Adds or subtracts the specified amount of minutes to the {@code date} returning a new object (the original {@code date} object is unchanged), based on + * the calendar's rules. + *

+ * + * @param clazz + * the date class to return (supports {@link java.util.Date}, {@link java.sql.Date}, {@link java.sql.Timestamp}) + * @param date + * the {@code date}, not {@code null} + * @param amount + * the amount to add, may be negative + * + * @return the new {@code date} object with the amount added + * + * @throws IllegalArgumentException + * if the {@code date} is {@code null} + * + * @see Calendar#add(int, int) + */ + public static T addMinutes(Class clazz, Date date, int amount) { + return add(clazz, date, Calendar.MINUTE, amount); + } + + /** + *

+ * Adds or subtracts the specified amount of seconds to the {@code date} returning a new object (the original {@code date} object is unchanged), based on + * the calendar's rules. + *

+ * + * @param clazz + * the date class to return (supports {@link java.util.Date}, {@link java.sql.Date}, {@link java.sql.Timestamp}) + * @param date + * the {@code date}, not {@code null} + * @param amount + * the amount to add, may be negative + * + * @return the new {@code date} object with the amount added + * + * @throws IllegalArgumentException + * if the {@code date} is {@code null} + * + * @see Calendar#add(int, int) + */ + public static T addSeconds(Class clazz, Date date, int amount) { + return add(clazz, date, Calendar.SECOND, amount); + } + + /** + * Returns the day of the month represented by this Date object. + * + * @return a value between {@code 1} and {@code 31} representing the day of the month + * + * @see Calendar#get(Calendar.DAY_OF_MONTH) + */ + public static int getDay(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + return c.get(Calendar.DAY_OF_MONTH); + } + + /** + * Returns the day of the week represented by this Date object. + * + * @return a value from {@code 1} (Sunday) to {@code 7} (Saturday) representing the day of the week + * + * @see Calendar#get(Calendar.DAY_OF_WEEK) + */ + public static int getDayOfWeek(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + return c.get(Calendar.DAY_OF_WEEK); + } + + /** + * Returns a number representing the month represented by this Date object + * + * @return a value between {@code 0} and {@code 11} representing the month, with the value {@code 0} representing January + * + * @see Calendar#get(Calendar.MONTH) + */ + public static int getMonth(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + return c.get(Calendar.MONTH); + } + + /** + * Returns the year represented by this Date object + * + * @see Calendar#get(Calendar.YEAR) + */ + public static int getYear(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + return c.get(Calendar.YEAR); + } + + /** + * Returns the number of days of the month represented by this Date object + * + * @param date + * non-{@code null} {@code date} object + */ + public static int getNumberOfDaysOfMonth(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + return c.getActualMaximum(Calendar.DAY_OF_MONTH); + } + + /** + * Returns the number of days by range represented by this Date object + * + * @param dateFrom + * Date Start From + * @param dateTo + * Date End To + */ + public static int getNumberOfDaysByRange(Date dateFrom, Date dateTo) { + dateFrom = DateUtils.truncate(dateFrom, Calendar.DAY_OF_MONTH); + dateTo = DateUtils.truncate(dateTo, Calendar.DAY_OF_MONTH); + + Calendar fromCal = Calendar.getInstance(); + fromCal.setTime(dateFrom); + + Calendar toCal = Calendar.getInstance(); + toCal.setTime(dateTo); + int count = 0; + while (DateUtils.isEarlierThan(fromCal.getTime(), toCal.getTime())) { + count++; + fromCal.add(Calendar.DAY_OF_MONTH, 1); + } + return count; + } + + /** + * Returns the first date of the month represented by this Date object + * + * @param date + * non-{@code null} {@code date} object + */ + public static Date getFirstDateOfMonth(Date date) { + Calendar calendar = Calendar.getInstance(); + calendar.setTime(date); + calendar.set(Calendar.DAY_OF_MONTH, 1); + return calendar.getTime(); + } + + /** + * Returns the last date of the month represented by this Date object + * + * @param date + * non-{@code null} {@code date} object + */ + public static Date getLastDateOfMonth(Date date) { + Calendar calendar = Calendar.getInstance(); + calendar.setTime(date); + calendar.set(Calendar.DAY_OF_MONTH, calendar.getActualMaximum(Calendar.DAY_OF_MONTH)); + return calendar.getTime(); + } + + /** + * Returns the first date of the last month represented by this Date object + * + * @param date + * non-{@code null} {@code date} object + */ + public static Date getFirstDateOfLastMonth(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + c.add(Calendar.MONTH, -1); + c.set(Calendar.DAY_OF_MONTH, 1); + return c.getTime(); + } + + /** + * Returns the last date of the last month represented by this Date object + * + * @param date + * non-{@code null} {@code date} object + */ + public static Date getLastDateOfLastMonth(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + c.add(Calendar.MONTH, -1); + c.set(Calendar.DAY_OF_MONTH, c.getActualMaximum(Calendar.DAY_OF_MONTH)); + return c.getTime(); + } + + /** + * Returns the first date of the year + * + * @param year + * the year + */ + public static Date getFirstDateOfYear(int year) { + Calendar calendar = Calendar.getInstance(); + calendar.set(year, Calendar.JANUARY, 1, 0, 0, 0); + return calendar.getTime(); + } + + /** + * Returns the last date of the year + * + * @param year + * the year + */ + public static Date getLastDateOfYear(int year) { + Calendar calendar = Calendar.getInstance(); + calendar.set(year, Calendar.DECEMBER, 31, 0, 0, 0); + return calendar.getTime(); + } + + /** + * Returns the first date of the week represented by this Date object + * + * @param date + * non-{@code null} {@code date} object + */ + public static Date getFirstDateOfWeek(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + c.add(Calendar.DAY_OF_MONTH, -c.get(Calendar.DAY_OF_WEEK) + 1); + return c.getTime(); + } + + /** + * Returns the first date of the week represented by this Date object, where you can specify the first day of the week + * + * @param date + * non-{@code null} {@code date} object + * @param firstDayOfWeek + * the first day of the week (e.g. Calendar.SUNDAY, Calendar.MONDAY, etc) + */ + public static Date getFirstDateOfWeek(Date date, int firstDayOfWeek) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + int diff = c.get(Calendar.DAY_OF_WEEK) - firstDayOfWeek; + if (diff < 0) diff += 7; + c.add(Calendar.DAY_OF_MONTH, -diff); + return c.getTime(); + } + + /** + * Returns the last date of the week represented by this Date object + * + * @param date + * non-{@code null} {@code date} object + */ + public static Date getLastDateOfWeek(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + c.add(Calendar.DAY_OF_MONTH, 7 - c.get(Calendar.DAY_OF_WEEK)); + return c.getTime(); + } + + /** + * Returns the last date of the week represented by this Date object, where you can specify the first day of the week + * + * @param date + * non-{@code null} {@code date} object + * @param firstDayOfWeek + * the first day of the week (e.g. Calendar.SUNDAY, Calendar.MONDAY, etc) + */ + public static Date getLastDateOfWeek(Date date, int firstDayOfWeek) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + int diff = c.get(Calendar.DAY_OF_WEEK) - firstDayOfWeek; + if (diff < 0) diff += 7; + c.add(Calendar.DAY_OF_MONTH, 6 - diff); + return c.getTime(); + } + + /** + * Returns the first date of month by year and month + * + * @param year + * the year + * @param month + * a value between {@code 1} and {@code 12} representing January to December + */ + public static Date getFirstDateOfMonthByYearAndMonth(int year, int month) { + Calendar c = Calendar.getInstance(); + c.set(year, month - 1, 1, 0, 0, 0); + return c.getTime(); + } + + /** + * Returns the last date of month by year and month + * + * @param year + * the year + * @param month + * a value between {@code 1} and {@code 12} representing January to December + */ + public static Date getLastDateOfMonthByYearAndMonth(int year, int month) { + Calendar c = Calendar.getInstance(); + c.set(year, month - 1, 1, 0, 0, 0); + c.set(Calendar.DAY_OF_MONTH, c.getActualMaximum(Calendar.DAY_OF_MONTH)); + return c.getTime(); + } + + /** + * Returns a new {@link java.sql.Date} object from the value of the {@link java.util.Date} object, returns {@code null} if {@code date} is null + * + * @param date + * {@code date} object, may be {@code null} + */ + public static java.sql.Date toSqlDate(Date date) { + if (date == null) return null; + return new java.sql.Date(date.getTime()); + } + + /** + * Returns a new {@link java.sql.Timestamp} object from the value of the {@link java.util.Date} object, returns {@code null} if {@code date} is null + * + * @param date + * {@code date} object, may be {@code null} + */ + public static java.sql.Timestamp toTimestamp(Date date) { + if (date == null) return null; + return new java.sql.Timestamp(date.getTime()); + } + + /** + * Returns the number of days in a month count by the Day of Week (Sunday to Saturday) + * + * @param year + * 4-digit year + * @param month + * 1 to 12 (Jan to Dec) + * @param weekDays + * Calendar.SUNDAY to Calendar.SATURDAY + * + * @return the number of days in a month count by the Day of Week + */ + public static int countDaysByDayOfWeek(int year, int month, int... dayOfWeeks) { + Calendar c = Calendar.getInstance(); + c.clear(); + c.set(year, month - 1, 1); // first day of month + + int dayOfWeek = c.get(Calendar.DAY_OF_WEEK); + int daysInMonth = c.getActualMaximum(Calendar.DAY_OF_MONTH); + + int count = 0; + for (int day = 1; day <= daysInMonth; day++) { + for (int dow : dayOfWeeks) { + if (dayOfWeek == dow) count++; + } + dayOfWeek++; + if (dayOfWeek > Calendar.SATURDAY) dayOfWeek = Calendar.SUNDAY; + } + return count; + } + + /** + * Returns the number of days in a month count by the Day of Week (Sunday to Saturday) + * + * @param dateFrom + * Date Start From + * @param dateTo + * Date End To + * @param weekDays + * Calendar.SUNDAY to Calendar.SATURDAY + * + * @return the number of days in a month count by the Day of Week + */ + public static int countDaysByDayOfWeek(Date dateFrom, Date dateTo, int... dayOfWeeks) { + dateFrom = DateUtils.truncate(dateFrom, Calendar.DAY_OF_MONTH); + dateTo = DateUtils.truncate(dateTo, Calendar.DAY_OF_MONTH); + + Calendar fromCal = Calendar.getInstance(); + fromCal.setTime(dateFrom); + + Calendar toCal = Calendar.getInstance(); + toCal.setTime(dateTo); + + int count = 0; + while (DateUtils.isEarlierThan(fromCal.getTime(), toCal.getTime())) { + int dayOfWeek = fromCal.get(Calendar.DAY_OF_WEEK); + for (int dow : dayOfWeeks) { + if (dayOfWeek == dow) { + count++; + break; + } + } + fromCal.add(Calendar.DAY_OF_MONTH, 1); + } + return count; + } + + /** + * Returns {@code true} if date {@code a} is the same month and year as date {@code b} (ignoring the time component), else returns {@code false} + */ + public static boolean isSameMonthYear(Date a, Date b) { + return getYear(a) == getYear(b) && getMonth(a) == getMonth(b); + } + + /** + * Returns {@code true} if date {@code a} is the same week and year as date {@code b} (ignoring the time component), else returns {@code false} + */ + public static boolean isSameWeekYear(Date a, Date b) { + return getYear(a) == getYear(b) && getWeekOfYear(a) == getWeekOfYear(b); + } + + /** + * new Date() is deprecated + * + * @param year + * full year + * @param month + * 0-based + * @param date + * 1-based + * @return java.util.Date + */ + public static Date newDate(int year, int month, int date) { + Calendar instance = Calendar.getInstance(); + instance.clear(); + instance.set(year, month, date); + return instance.getTime(); + } + + /** + * new Date() is deprecated + * + * @param year + * full year + * @param month + * 0-based + * @param date + * 1-based + * @return java.util.Date + */ + public static Date newDate(int year, int month, int date, int hourOfDay, int minute) { + Calendar instance = Calendar.getInstance(); + instance.clear(); + instance.set(year, month, date, hourOfDay, minute); + return instance.getTime(); + } + + /** + * new Date() is deprecated + * + * @param year + * full year + * @param month + * 0-based + * @param date + * 1-based + * @return java.util.Date + */ + public static Date newDate(int year, int month, int date, int hourOfDay, int minute, int second) { + Calendar instance = Calendar.getInstance(); + instance.clear(); + instance.set(year, month, date, hourOfDay, minute, second); + return instance.getTime(); + } +} diff --git a/src/main/java/com/ffii/core/utils/Encoding.java b/src/main/java/com/ffii/core/utils/Encoding.java new file mode 100644 index 0000000..c1b00ea --- /dev/null +++ b/src/main/java/com/ffii/core/utils/Encoding.java @@ -0,0 +1,139 @@ +/******************************************************************************* + * Copyright 2012 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +public class Encoding { + + // Supported Encoding Types + public static final int GB2312 = 0; + public static final int GBK = 1; + public static final int GB18030 = 2; + + public static final int HZ = 3; + public static final int BIG5 = 4; + public static final int CNS11643 = 5; + + public static final int UTF8 = 6; + public static final int UTF8T = 7; + public static final int UTF8S = 8; + + public static final int UNICODE = 9; + public static final int UNICODET = 10; + public static final int UNICODES = 11; + + public static final int ISO2022CN = 12; + public static final int ISO2022CN_CNS = 13; + public static final int ISO2022CN_GB = 14; + + public static final int EUC_KR = 15; + public static final int CP949 = 16; + public static final int ISO2022KR = 17; + public static final int JOHAB = 18; + public static final int SJIS = 19; + public static final int EUC_JP = 20; + public static final int ISO2022JP = 21; + public static final int ASCII = 22; + public static final int OTHER = 23; + public static final int TOTALTYPES = 24; + + // Names of the encodings as understood by Java + public static String[] javaname; + + // Names of the encodings for human viewing + public static String[] nicename; + + // Names of charsets as used in charset parameter of HTML Meta tag + public static String[] htmlname; + + static { + javaname = new String[TOTALTYPES]; + nicename = new String[TOTALTYPES]; + htmlname = new String[TOTALTYPES]; + + // Assign encoding names + javaname[GB2312] = "GB2312"; + javaname[GBK] = "GBK"; + javaname[GB18030] = "GB18030"; + javaname[HZ] = "ASCII"; // What to put here? Sun doesn't support HZ + javaname[ISO2022CN_GB] = "ISO2022CN_GB"; + javaname[BIG5] = "BIG5"; + javaname[CNS11643] = "EUC-TW"; + javaname[ISO2022CN_CNS] = "ISO2022CN_CNS"; + javaname[ISO2022CN] = "ISO2022CN"; + javaname[UTF8] = "UTF8"; + javaname[UTF8T] = "UTF8"; + javaname[UTF8S] = "UTF8"; + javaname[UNICODE] = "Unicode"; + javaname[UNICODET] = "Unicode"; + javaname[UNICODES] = "Unicode"; + javaname[EUC_KR] = "EUC_KR"; + javaname[CP949] = "MS949"; + javaname[ISO2022KR] = "ISO2022KR"; + javaname[JOHAB] = "Johab"; + javaname[SJIS] = "SJIS"; + javaname[EUC_JP] = "EUC_JP"; + javaname[ISO2022JP] = "ISO2022JP"; + javaname[ASCII] = "ASCII"; + javaname[OTHER] = "ISO8859_1"; + + // Assign encoding names + htmlname[GB2312] = "GB2312"; + htmlname[GBK] = "GBK"; + htmlname[GB18030] = "GB18030"; + htmlname[HZ] = "HZ-GB-2312"; + htmlname[ISO2022CN_GB] = "ISO-2022-CN-EXT"; + htmlname[BIG5] = "BIG5"; + htmlname[CNS11643] = "EUC-TW"; + htmlname[ISO2022CN_CNS] = "ISO-2022-CN-EXT"; + htmlname[ISO2022CN] = "ISO-2022-CN"; + htmlname[UTF8] = "UTF-8"; + htmlname[UTF8T] = "UTF-8"; + htmlname[UTF8S] = "UTF-8"; + htmlname[UNICODE] = "UTF-16"; + htmlname[UNICODET] = "UTF-16"; + htmlname[UNICODES] = "UTF-16"; + htmlname[EUC_KR] = "EUC-KR"; + htmlname[CP949] = "x-windows-949"; + htmlname[ISO2022KR] = "ISO-2022-KR"; + htmlname[JOHAB] = "x-Johab"; + htmlname[SJIS] = "Shift_JIS"; + htmlname[EUC_JP] = "EUC-JP"; + htmlname[ISO2022JP] = "ISO-2022-JP"; + htmlname[ASCII] = "ASCII"; + htmlname[OTHER] = "ISO8859-1"; + + // Assign Human readable names + nicename[GB2312] = "GB-2312"; + nicename[GBK] = "GBK"; + nicename[GB18030] = "GB18030"; + nicename[HZ] = "HZ"; + nicename[ISO2022CN_GB] = "ISO2022CN-GB"; + nicename[BIG5] = "Big5"; + nicename[CNS11643] = "CNS11643"; + nicename[ISO2022CN_CNS] = "ISO2022CN-CNS"; + nicename[ISO2022CN] = "ISO2022 CN"; + nicename[UTF8] = "UTF-8"; + nicename[UTF8T] = "UTF-8 (Trad)"; + nicename[UTF8S] = "UTF-8 (Simp)"; + nicename[UNICODE] = "Unicode"; + nicename[UNICODET] = "Unicode (Trad)"; + nicename[UNICODES] = "Unicode (Simp)"; + nicename[EUC_KR] = "EUC-KR"; + nicename[CP949] = "CP949"; + nicename[ISO2022KR] = "ISO 2022 KR"; + nicename[JOHAB] = "Johab"; + nicename[SJIS] = "Shift-JIS"; + nicename[EUC_JP] = "EUC-JP"; + nicename[ISO2022JP] = "ISO 2022 JP"; + nicename[ASCII] = "ASCII"; + nicename[OTHER] = "OTHER"; + } +} diff --git a/src/main/java/com/ffii/core/utils/ExcelUtils.java b/src/main/java/com/ffii/core/utils/ExcelUtils.java new file mode 100644 index 0000000..77f493f --- /dev/null +++ b/src/main/java/com/ffii/core/utils/ExcelUtils.java @@ -0,0 +1,675 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.io.OutputStream; +import java.math.BigDecimal; +import java.security.GeneralSecurityException; +import java.util.Calendar; +import java.util.Date; +import java.util.HashMap; +import java.util.Map; + +import org.apache.poi.openxml4j.exceptions.InvalidFormatException; +import org.apache.poi.openxml4j.opc.OPCPackage; +import org.apache.poi.poifs.crypt.EncryptionInfo; +import org.apache.poi.poifs.crypt.EncryptionMode; +import org.apache.poi.poifs.crypt.Encryptor; +import org.apache.poi.poifs.filesystem.POIFSFileSystem; +import org.apache.poi.ss.usermodel.Cell; +import org.apache.poi.ss.usermodel.CellType; +import org.apache.poi.ss.usermodel.DataFormatter; +import org.apache.poi.ss.usermodel.DateUtil; +import org.apache.poi.ss.usermodel.RichTextString; +import org.apache.poi.ss.usermodel.Row; +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; +import org.apache.poi.ss.util.CellRangeAddress; +import org.apache.poi.xssf.usermodel.XSSFWorkbook; +import org.springframework.core.io.Resource; +import org.springframework.core.io.ResourceLoader; + +/** + * Excel Utils (for Apache POI 3.15 to 3.17) + * + * @author Patrick + * @version 2018-04-06 + */ +public abstract class ExcelUtils { + + /** + * static A to Z char array + */ + private static final char[] A2Z = { 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', + 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z' }; + + private static final DataFormatter DATA_FORMATTER = new DataFormatter(); + + /** max rows limit of .xls **/ + public static final int MAX_ROWS = 65536; + /** max columns limit of .xls **/ + public static final int MAX_COLS = 256; + + /** + * Column reference to index (0-based) map, support up to 256 columns + * (compatible with .xls format) + */ + public static final Map COL_IDX = new HashMap(MAX_COLS, 1.0f); + + static { + for (int columnIndex = 0; columnIndex < MAX_COLS; columnIndex++) { + int tempColumnCount = columnIndex; + StringBuilder sb = new StringBuilder(2); + do { + sb.insert(0, A2Z[tempColumnCount % 26]); + tempColumnCount = (tempColumnCount / 26) - 1; + } while (tempColumnCount >= 0); + COL_IDX.put(sb.toString(), Integer.valueOf(columnIndex)); + } + } + + /** + * Load XSSF workbook (xlsx file) from template source. + * + * @param url the relative path to the template source, e.g. + * "WEB-INF/excel/exampleReportTemplate.xlsx" + * + * @return the workbook, or null if the template file cannot be loaded + */ + public static final Workbook loadXSSFWorkbookFromTemplateSource(ResourceLoader resourceLoader, String url) { + Resource resource = resourceLoader.getResource(url); + try { + return new XSSFWorkbook(resource.getInputStream()); + } catch (IOException e) { + return null; + } + } + + /** + * Write the workbook to byte array. + * + * @param workbook The Excel workbook (cannot be null) + * + * @return the byte[], or null if IO exception occurred + */ + public static final byte[] toByteArray(Workbook workbook) { + ByteArrayOutputStream baos = new ByteArrayOutputStream(); + try { + workbook.write(baos); + } catch (IOException e) { + return null; + } + return baos.toByteArray(); + } + + /** + * Check if the cell exists in the given sheet, row and column. + * + * @param sheet the Sheet (cannot be null) + * @param rowIndex 0-based row index + * @param colIndex 0-based column index + * + * @return {@code true} if cell exists, else {@code false} + */ + public static final boolean isCellExists(Sheet sheet, int rowIndex, int colIndex) { + Row row = sheet.getRow(rowIndex); + if (row != null) { + Cell cell = row.getCell(colIndex); + return cell != null; + } + return false; + } + + /** + * Convenient method to obtain the cell in the given sheet, row and column. + *

+ * Creates the row and the cell if not already exist. + * + * @param sheet the Sheet (cannot be null) + * @param rowIndex 0-based row index + * @param colIndex 0-based column index + * + * @return the Cell (never null) + */ + public static final Cell getCell(Sheet sheet, int rowIndex, int colIndex) { + Row row = sheet.getRow(rowIndex); + if (row == null) { + row = sheet.createRow(rowIndex); + } + Cell cell = row.getCell(colIndex); + if (cell == null) { + cell = row.createCell(colIndex); + } + return cell; + } + + /** + * Get column index by column reference (support up to 256 columns) + * + * @param columnRef column reference such as "A", "B", "AA", "AB"... + * + * @return the column index + * + * @throws NullPointerException if column reference is invalid or the index + * exceeds 256 + */ + public static final int getColumnIndex(String columnRef) { + return COL_IDX.get(columnRef); + } + + /** + * Get column reference by column index + * + * @param columnIndex 0-based column index + * + * @return the column reference such as "A", "B", "AA", "AB"... + */ + public static final String getColumnRef(int columnIndex) { + StringBuilder sb = new StringBuilder(); + int tempColumnCount = columnIndex; + do { + sb.insert(0, A2Z[tempColumnCount % 26]); + tempColumnCount = (tempColumnCount / 26) - 1; + } while (tempColumnCount >= 0); + return sb.toString(); + } + + /** + * Get the Excel Cell Ref String by columnIndex and rowIndex + * + * @param columnIndex 0-based column index + * @param rowIndex 0-based row index + */ + public static final String getCellRefString(int columnIndex, int rowIndex) { + StringBuilder sb = new StringBuilder(); + int tempColumnCount = columnIndex; + do { + sb.insert(0, A2Z[tempColumnCount % 26]); + tempColumnCount = (tempColumnCount / 26) - 1; + } while (tempColumnCount >= 0); + sb.append(rowIndex + 1); + return sb.toString(); + } + + /** + * Get Cell value as String + */ + public static String getStringValue(Cell cell) { + if (cell != null && cell.getCellTypeEnum() == CellType.FORMULA) { + try { + return cell.getStringCellValue(); + } catch (Exception e) { + return ""; + } + } + return DATA_FORMATTER.formatCellValue(cell); + } + + /** + * Get Cell value as BigDecimal, with a fallback value + *

+ * Only support {@link Cell#CELL_TYPE_NUMERIC} and {@link Cell#CELL_TYPE_STRING} + * + * @return the BigDecimal value, or the default value if cell is + * null or cell type is {@link Cell#CELL_TYPE_BLANK} + */ + public static BigDecimal getDecimalValue(Cell cell, BigDecimal defaultValue) { + if (cell == null || cell.getCellTypeEnum() == CellType.BLANK) + return defaultValue; + if (cell.getCellTypeEnum() == CellType.STRING) { + return NumberUtils.toDecimal(cell.getStringCellValue()); + } else { + return BigDecimal.valueOf(cell.getNumericCellValue()); + } + } + + /** + * Get Cell value as BigDecimal + *

+ * Only support {@link Cell#CELL_TYPE_NUMERIC} and {@link Cell#CELL_TYPE_STRING} + * + * @return the BigDecimal value, or BigDecimal.ZERO if + * cell is null or cell type is + * {@link Cell#CELL_TYPE_BLANK} + */ + public static BigDecimal getDecimalValue(Cell cell) { + return getDecimalValue(cell, BigDecimal.ZERO); + } + + /** + * Get Cell value as double + *

+ * Only support {@link Cell#CELL_TYPE_NUMERIC} and {@link Cell#CELL_TYPE_STRING} + */ + public static double getDoubleValue(Cell cell) { + if (cell == null) + return 0.0; + if (cell.getCellTypeEnum() == CellType.STRING) { + return NumberUtils.toDouble(cell.getStringCellValue()); + } else { + return cell.getNumericCellValue(); + } + } + + /** + * Get Cell value as int (rounded half-up to the nearest integer) + *

+ * Only support {@link Cell#CELL_TYPE_NUMERIC} and {@link Cell#CELL_TYPE_STRING} + */ + public static int getIntValue(Cell cell) { + return (int) NumberUtils.round(getDoubleValue(cell), 0); + } + + /** + * Get Cell Integer value (truncated) + */ + public static Integer getIntValue(Cell cell, Integer defaultValue) { + if (cell == null) + return defaultValue; + if (cell.getCellTypeEnum() == CellType.STRING) { + return NumberUtils.toInt(cell.getStringCellValue(), defaultValue); + } else { + return (int) cell.getNumericCellValue(); + } + } + + /** + * Get Cell Date value + */ + public static Date getDateValue(Cell cell) { + if (cell == null) + return null; + if (cell.getCellTypeEnum() == CellType.STRING) { + return DateUtils.parseDateStrictly(cell.getStringCellValue(), DateUtils.PARSE_PATTERNS, null); + } + if (DateUtil.isCellDateFormatted(cell)) { + try { + return DateUtil.getJavaDate(cell.getNumericCellValue()); + } catch (NumberFormatException e) { + return null; + } + } else { + return null; + } + } + + /** + * Convenient method to set Cell value + * + * @param cell the Cell (cannot be null) + * @param value the value to set + */ + public static void setCellValue(Cell cell, Object value) { + if (value instanceof String) + cell.setCellValue((String) value); + else if (value instanceof RichTextString) + cell.setCellValue((RichTextString) value); + else if (value instanceof Number) + cell.setCellValue(((Number) value).doubleValue()); + else if (value instanceof Boolean) + cell.setCellValue(((Boolean) value).booleanValue()); + else if (value instanceof Calendar) + cell.setCellValue((Calendar) value); + else if (value instanceof Date) + cell.setCellValue((Date) value); + else if (value == null) + cell.setCellValue(""); + else + throw new IllegalArgumentException(value.getClass().toString() + " is not supported"); + } + + /** + * Convenient method to set Cell value by Sheet, row index, and column index + * + * @param sheet the Sheet (cannot be null) + * @param rowIndex 0-based row index + * @param colIndex 0-based column index + * @param value the value to set + */ + public static void setCellValue(Sheet sheet, int rowIndex, int colIndex, Object value) { + setCellValue(getCell(sheet, rowIndex, colIndex), value); + } + + /** + * Increase Row Height (if necessary, but never decrease it) by counting the no. + * of lines in a String value + * + * @param sheet The Excel worksheet + * @param row The row index (0-based) + * @param value The (multi-line) String value to count for the no. of + * lines + * @param heightInPoints The height (in points) for 1 line of text + */ + public static void increaseRowHeight(Sheet sheet, int row, String value, int heightInPoints) { + int lines = StringUtils.countMatches(value, "\n") + 1; // count no. of lines + float newHeight = heightInPoints * lines; + + Row r = sheet.getRow(row); + if (r == null) + r = sheet.createRow(row); + + // increase the row height if necessary, but never decrease it + if (r.getHeightInPoints() < newHeight) { + r.setHeightInPoints(newHeight); + } + } + + /** + * Add merged region (i.e. merge cells) + * + * @param sheet The Excel worksheet + * @param firstRowIdx The first row index (0-based) + * @param lastRowIdx The last row index (0-based) + * @param firstColIdx The first column index (0-based) + * @param lastColIdx The last column index (0-based) + */ + public static void addMergedRegion(Sheet sheet, int firstRowIdx, int lastRowIdx, int firstColIdx, int lastColIdx) { + CellRangeAddress cellRangeAddress = new CellRangeAddress(firstRowIdx, lastRowIdx, firstColIdx, lastColIdx); + sheet.addMergedRegion(cellRangeAddress); + } + + /** + * Copy and Insert Row + * + * @param workbook The Excel workbook + * @param sourceSheet The source Excel worksheet + * @param destinationSheet The destination Excel worksheet + * @param sourceRowNum The source row index (0-based) to copy from + * @param destinationRowNum The destination row index (0-based) to insert into + * (from the copied row) + */ + public static void copyAndInsertRow(Workbook workbook, Sheet sourceSheet, Sheet destinationSheet, int sourceRowNum, + int destinationRowNum) { + // get the source / destination row + Row sourceRow = sourceSheet.getRow(sourceRowNum); + Row destRow = destinationSheet.getRow(destinationRowNum); + + // if the row exist in destination, push down all rows by 1 + if (destRow != null) { + destinationSheet.shiftRows(destinationRowNum, destinationSheet.getLastRowNum(), 1, true, false); + } + // create a new row + destRow = destinationSheet.createRow(destinationRowNum); + + // loop through source columns to add to new row + for (int i = 0; i < sourceRow.getLastCellNum(); i++) { + // grab a copy of the old cell + Cell oldCell = sourceRow.getCell(i); + + // if the old cell is null jump to next cell + if (oldCell == null) + continue; + + // create a new cell in destination row + Cell newCell = destRow.createCell(i); + + // apply cell style to new cell from old cell + newCell.setCellStyle(oldCell.getCellStyle()); + + // if there is a cell comment, copy + if (oldCell.getCellComment() != null) { + newCell.setCellComment(oldCell.getCellComment()); + } + + // if there is a cell hyperlink, copy + if (oldCell.getHyperlink() != null) { + newCell.setHyperlink(oldCell.getHyperlink()); + } + + // copy the cell data type + newCell.setCellType(oldCell.getCellTypeEnum()); + + // copy the cell data value + switch (oldCell.getCellTypeEnum()) { + case NUMERIC: + newCell.setCellValue(oldCell.getNumericCellValue()); + break; + case STRING: + newCell.setCellValue(oldCell.getRichStringCellValue()); + break; + case FORMULA: + newCell.setCellFormula(oldCell.getCellFormula()); + break; + case BLANK: + newCell.setCellValue(oldCell.getStringCellValue()); + break; + case BOOLEAN: + newCell.setCellValue(oldCell.getBooleanCellValue()); + break; + case ERROR: + newCell.setCellErrorValue(oldCell.getErrorCellValue()); + break; + default: + break; + } + } + + // if there are any merged regions in the source row, copy to new row + for (int i = 0; i < sourceSheet.getNumMergedRegions(); i++) { + CellRangeAddress cellRangeAddress = sourceSheet.getMergedRegion(i); + if (cellRangeAddress.getFirstRow() == sourceRow.getRowNum()) { + addMergedRegion(destinationSheet, destRow.getRowNum(), + (destRow.getRowNum() + (cellRangeAddress.getLastRow() - cellRangeAddress.getFirstRow())), + cellRangeAddress.getFirstColumn(), cellRangeAddress.getLastColumn()); + } + } + + // copy row height + destRow.setHeight(sourceRow.getHeight()); + } + + /** + * Copy and Insert Row + * + * @param workbook The Excel workbook + * @param sheet The Excel worksheet + * @param sourceRowNum The source row index (0-based) to copy from + * @param destinationRowNum The destination row index (0-based) to insert into + * (from the copied row) + */ + public static void copyAndInsertRow(Workbook workbook, Sheet sheet, int sourceRowNum, int destinationRowNum) { + copyAndInsertRow(workbook, sheet, sheet, sourceRowNum, destinationRowNum); + } + + /** + * Copy Column + * + * @param workbook The Excel workbook + * @param sourceSheet The source Excel worksheet + * @param destinationSheet The destination Excel worksheet + * @param rowStart The source row start index (0-based) to copy from + * @param rowEnd The source row end index (0-based) to copy from + * @param sourceColumnNum The source column index (0-based) to copy from + * @param destinationColumnNum The destination column index (0-based) to copy + * into (from the copied row) + */ + public static void copyColumn(Workbook workbook, Sheet sourceSheet, Sheet destinationSheet, int rowStart, + int rowEnd, int sourceColumnNum, int destinationColumnNum) { + for (int i = rowStart; i <= rowEnd; i++) { + Row sourceRow = sourceSheet.getRow(i); + if (sourceRow == null) + continue; + + Row destinationRow = destinationSheet.getRow(i); + if (destinationRow == null) + destinationRow = destinationSheet.createRow(i); + + Cell oldCell = sourceRow.getCell(sourceColumnNum); + if (oldCell == null) + continue; + + Cell newCell = destinationRow.createCell(destinationColumnNum); + + newCell.setCellStyle(oldCell.getCellStyle()); + + if (oldCell.getCellComment() != null) { + newCell.setCellComment(oldCell.getCellComment()); + } + + if (oldCell.getHyperlink() != null) { + newCell.setHyperlink(oldCell.getHyperlink()); + } + + newCell.setCellType(oldCell.getCellTypeEnum()); + + switch (oldCell.getCellTypeEnum()) { + case NUMERIC: + newCell.setCellValue(oldCell.getNumericCellValue()); + break; + case STRING: + newCell.setCellValue(oldCell.getRichStringCellValue()); + break; + case FORMULA: + newCell.setCellFormula(oldCell.getCellFormula()); + break; + case BLANK: + newCell.setCellValue(oldCell.getStringCellValue()); + break; + case BOOLEAN: + newCell.setCellValue(oldCell.getBooleanCellValue()); + break; + case ERROR: + newCell.setCellErrorValue(oldCell.getErrorCellValue()); + break; + default: + break; + } + + for (int ii = 0; ii < sourceSheet.getNumMergedRegions(); ii++) { + CellRangeAddress cellRangeAddress = sourceSheet.getMergedRegion(ii); + if (cellRangeAddress.getFirstRow() == sourceRow.getRowNum()) { + addMergedRegion(destinationSheet, cellRangeAddress.getFirstRow(), cellRangeAddress.getLastRow(), + destinationColumnNum, (destinationColumnNum + + (cellRangeAddress.getLastColumn() - cellRangeAddress.getFirstColumn()))); + } + } + } + + destinationSheet.setColumnWidth(destinationColumnNum, sourceSheet.getColumnWidth(sourceColumnNum)); + } + + /** + * Copy Column + * + * @param workbook The Excel workbook + * @param sheet The Excel worksheet + * @param rowStart The source row start index (0-based) to copy from + * @param rowEnd The source row end index (0-based) to copy from + * @param sourceColumnNum The source column index (0-based) to copy from + * @param destinationColumnNum The destination column index (0-based) to copy + * into (from the copied row) + */ + public static void copyColumn(Workbook workbook, Sheet sheet, int rowStart, int rowEnd, int sourceColumnNum, + int destinationColumnNum) { + copyColumn(workbook, sheet, sheet, rowStart, rowEnd, sourceColumnNum, destinationColumnNum); + } + + public static void shiftColumns(Row row, int startingIndex, int shiftCount) { + for (int i = row.getPhysicalNumberOfCells() - 1; i >= startingIndex; i--) { + Cell oldCell = row.getCell(i); + Cell newCell = row.createCell(i + shiftCount); + + // apply cell style to new cell from old cell + newCell.setCellStyle(oldCell.getCellStyle()); + + // if there is a cell comment, copy + if (oldCell.getCellComment() != null) { + newCell.setCellComment(oldCell.getCellComment()); + } + + // if there is a cell hyperlink, copy + if (oldCell.getHyperlink() != null) { + newCell.setHyperlink(oldCell.getHyperlink()); + } + + // copy the cell data type + newCell.setCellType(oldCell.getCellTypeEnum()); + + // copy the cell data value + switch (oldCell.getCellTypeEnum()) { + case NUMERIC: + newCell.setCellValue(oldCell.getNumericCellValue()); + break; + case STRING: + newCell.setCellValue(oldCell.getRichStringCellValue()); + break; + case FORMULA: + newCell.setCellFormula(oldCell.getCellFormula()); + break; + case BLANK: + newCell.setCellValue(oldCell.getStringCellValue()); + break; + case BOOLEAN: + newCell.setCellValue(oldCell.getBooleanCellValue()); + break; + case ERROR: + newCell.setCellErrorValue(oldCell.getErrorCellValue()); + break; + default: + break; + } + } + } + + /** handle some invalid char included ( /\*[]:? ) */ + public static void setSheetName(Workbook workbook, Sheet sheet, String name) { + if (workbook != null && sheet != null && StringUtils.isNotBlank(name)) + workbook.setSheetName(workbook.getSheetIndex(sheet), name.replaceAll("[/\\\\*\\[\\]:\\?]", "_")); + } + + /** delete row */ + public static void deleteRow(Sheet sheet, int rowIndex) { + if (sheet != null) { + sheet.removeRow(sheet.getRow(rowIndex)); + if (rowIndex < sheet.getLastRowNum()) + sheet.shiftRows(rowIndex, sheet.getLastRowNum(), -1); + } + } + + public static byte[] encrypt(Workbook workbook, String password) { + return encrypt(toByteArray(workbook), password); + } + + public static byte[] encrypt(byte[] bytes, String password) { + + POIFSFileSystem fs = new POIFSFileSystem(); + EncryptionInfo info = new EncryptionInfo(EncryptionMode.agile); + // EncryptionInfo info = new EncryptionInfo(EncryptionMode.agile, + // CipherAlgorithm.aes192, HashAlgorithm.sha384, -1, -1, null); + + Encryptor enc = info.getEncryptor(); + enc.confirmPassword(password); + + // Read in an existing OOXML file and write to encrypted output stream + // don't forget to close the output stream otherwise the padding bytes aren't + // added + try { + OPCPackage opc = OPCPackage.open(new ByteArrayInputStream(bytes)); + OutputStream os = enc.getDataStream(fs); + opc.save(os); + + ByteArrayOutputStream bos = new ByteArrayOutputStream(); + fs.writeFilesystem(bos); + + return bos.toByteArray(); + } catch (InvalidFormatException e) { + e.printStackTrace(); + } catch (IOException e) { + e.printStackTrace(); + } catch (GeneralSecurityException e) { + e.printStackTrace(); + } + + return bytes; + } + +} diff --git a/src/main/java/com/ffii/core/utils/FileUtils.java b/src/main/java/com/ffii/core/utils/FileUtils.java new file mode 100644 index 0000000..fceeab5 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/FileUtils.java @@ -0,0 +1,122 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.util.HashMap; +import java.util.Map; + +/** + * File Utils + * + * @author Patrick + */ +public abstract class FileUtils { + + private static final Map MIMETYPES = new HashMap<>(); + + static { + MIMETYPES.put("pdf", "application/pdf"); + + MIMETYPES.put("doc", "application/msword"); + MIMETYPES.put("dot", "application/msword"); + MIMETYPES.put("docx", "application/vnd.openxmlformats-officedocument.wordprocessingml.document"); + + MIMETYPES.put("xls", "application/vnd.ms-excel"); + MIMETYPES.put("xlm", "application/vnd.ms-excel"); + MIMETYPES.put("xla", "application/vnd.ms-excel"); + MIMETYPES.put("xlc", "application/vnd.ms-excel"); + MIMETYPES.put("xlt", "application/vnd.ms-excel"); + MIMETYPES.put("xlw", "application/vnd.ms-excel"); + MIMETYPES.put("xlsx", "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"); + + MIMETYPES.put("ppt", "application/vnd.ms-powerpoint"); + MIMETYPES.put("pps", "application/vnd.ms-powerpoint"); + MIMETYPES.put("pot", "application/vnd.ms-powerpoint"); + MIMETYPES.put("pptx", "application/vnd.openxmlformats-officedocument.presentationml.presentation"); + + MIMETYPES.put("bat", "application/x-msdownload"); + MIMETYPES.put("com", "application/x-msdownload"); + MIMETYPES.put("dll", "application/x-msdownload"); + MIMETYPES.put("exe", "application/x-msdownload"); + MIMETYPES.put("msi", "application/x-msdownload"); + + MIMETYPES.put("swf", "application/x-shockwave-flash"); + + MIMETYPES.put("7z", "application/x-7z-compressed"); + MIMETYPES.put("rar", "application/x-rar-compressed"); + MIMETYPES.put("zip", "application/zip"); + + MIMETYPES.put("js", "application/javascript"); + MIMETYPES.put("json", "application/json"); + + MIMETYPES.put("mpga", "audio/mpeg"); + MIMETYPES.put("mp2", "audio/mpeg"); + MIMETYPES.put("mp2a", "audio/mpeg"); + MIMETYPES.put("mp3", "audio/mpeg"); + MIMETYPES.put("m2a", "audio/mpeg"); + MIMETYPES.put("m3a", "audio/mpeg"); + + MIMETYPES.put("bmp", "image/bmp"); + MIMETYPES.put("gif", "image/gif"); + MIMETYPES.put("jpeg", "image/jpeg"); + MIMETYPES.put("jpg", "image/jpeg"); + MIMETYPES.put("jpe", "image/jpeg"); + MIMETYPES.put("JPG", "image/jpeg"); + MIMETYPES.put("png", "image/png"); + MIMETYPES.put("PNG", "image/png"); + MIMETYPES.put("tiff", "image/tiff"); + MIMETYPES.put("tif", "image/tiff"); + + MIMETYPES.put("css", "text/css"); + + MIMETYPES.put("csv", "text/csv"); + + MIMETYPES.put("html", "text/html"); + MIMETYPES.put("htm", "text/html"); + + MIMETYPES.put("txt", "text/plain"); + MIMETYPES.put("text", "text/plain"); + MIMETYPES.put("conf", "text/plain"); + MIMETYPES.put("log", "text/plain"); + + MIMETYPES.put("mp4", "video/mp4"); + MIMETYPES.put("mp4v", "video/mp4"); + MIMETYPES.put("mpg4", "video/mp4"); + + MIMETYPES.put("mpeg", "video/mpeg"); + MIMETYPES.put("mpg", "video/mpeg"); + MIMETYPES.put("mpe", "video/mpeg"); + MIMETYPES.put("m1v", "video/mpeg"); + MIMETYPES.put("m2v", "video/mpeg"); + + MIMETYPES.put("qt", "video/quicktime"); + MIMETYPES.put("mov", "video/quicktime"); + + MIMETYPES.put("wmv", "video/x-ms-wmv"); + MIMETYPES.put("wmx", "video/x-ms-wmx"); + MIMETYPES.put("wvx", "video/x-ms-wvx"); + MIMETYPES.put("avi", "video/x-msvideo"); + + // MIMETYPES.put("xxxxx", "xxxxx"); + } + + /** + * Guess the mimetype from the file name extension + * + * @return The mimetype guessed from the file name extension, or {@code null} if the mimetype cannot be determined + */ + public static String guessMimetype(String filename) { + String extension = StringUtils.substringAfterLast(filename, "."); + String mimetype = MIMETYPES.get(extension); + return mimetype != null ? mimetype : "application/octet-stream"; + } + +} diff --git a/src/main/java/com/ffii/core/utils/ImageUtils.java b/src/main/java/com/ffii/core/utils/ImageUtils.java new file mode 100644 index 0000000..6baa18c --- /dev/null +++ b/src/main/java/com/ffii/core/utils/ImageUtils.java @@ -0,0 +1,26 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.awt.image.BufferedImage; + +import org.imgscalr.Scalr; + +/** + * Image Utils + * + * @author Patrick + */ +public class ImageUtils { + + public BufferedImage resize(BufferedImage srcImage, int targetSize) { + return Scalr.resize(srcImage, targetSize); + } + +} diff --git a/src/main/java/com/ffii/core/utils/JsonUtils.java b/src/main/java/com/ffii/core/utils/JsonUtils.java new file mode 100644 index 0000000..dd7d8fc --- /dev/null +++ b/src/main/java/com/ffii/core/utils/JsonUtils.java @@ -0,0 +1,68 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.io.IOException; +import java.util.List; +import java.util.Map; + +import com.fasterxml.jackson.core.JsonParseException; +import com.fasterxml.jackson.core.JsonProcessingException; +import com.fasterxml.jackson.core.type.TypeReference; +import com.fasterxml.jackson.databind.JsonMappingException; +import com.fasterxml.jackson.databind.ObjectMapper; + +/** + * JSON Utils + * + * @author Patrick + */ +public abstract class JsonUtils { + + // Default mapper instance + private static final ObjectMapper mapper = new ObjectMapper(); + + /** + * Method that can be used to serialize any Java value as a JSON String. + */ + public static String toJsonString(Object obj) { + try { + return mapper.writeValueAsString(obj); + } catch (JsonProcessingException e) { + return null; + } + } + + /** + * Read from JSON String. + * + * @param content JSON String content + * @param valueType the return type + */ + public static T fromJsonString(String content, Class valueType) + throws JsonParseException, JsonMappingException, IOException { + return mapper.readValue(content, valueType); + + } + + public static Map fromJsonStringAsMap(String content) + throws JsonParseException, JsonMappingException, IOException { + return mapper.readValue(content, new TypeReference>() { + }); + } + + public static List> fromJsonStringAsListOfMap(String content) + throws JsonParseException, JsonMappingException, IOException { + return mapper.readValue(content, new TypeReference>>() { + }); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/utils/ListUtils.java b/src/main/java/com/ffii/core/utils/ListUtils.java new file mode 100644 index 0000000..0926c41 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/ListUtils.java @@ -0,0 +1,26 @@ +package com.ffii.core.utils; + +import java.util.ArrayList; +import java.util.List; + +/** + * ListUtils + * + */ +public class ListUtils { + + /** + * Convert values to ArrayList + * + * @param values + * + * @return List + */ + @SuppressWarnings("unchecked") + public static List toArrayList(V... values) { + List list = new ArrayList(values.length); + for (int i = 0; i < values.length; i++) + list.add(values[i]); + return list; + } +} diff --git a/src/main/java/com/ffii/core/utils/LocaleUtils.java b/src/main/java/com/ffii/core/utils/LocaleUtils.java new file mode 100644 index 0000000..124cc76 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/LocaleUtils.java @@ -0,0 +1,47 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.util.Locale; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.util.StringUtils; +import org.springframework.web.servlet.LocaleResolver; +import org.springframework.web.servlet.i18n.SessionLocaleResolver; + +/** + * Utility class for performing translation between Locale and String representations. + */ +public abstract class LocaleUtils { + + private static final LocaleResolver localeResolver = new SessionLocaleResolver(); + + public static final String toString(Locale locale) { + return locale.toString(); + } + + public static final Locale toLocale(String localeString) { + return StringUtils.parseLocaleString(localeString); + } + + public static final Locale resolveLocale(HttpServletRequest request) { + return localeResolver.resolveLocale(request); + } + + public static final String resolveLocaleString(HttpServletRequest request) { + return resolveLocale(request).toString(); + } + + public static final void setLocale(HttpServletRequest request, HttpServletResponse response, Locale locale) { + localeResolver.setLocale(request, response, locale); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/utils/MapBuilder.java b/src/main/java/com/ffii/core/utils/MapBuilder.java new file mode 100644 index 0000000..89cda94 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/MapBuilder.java @@ -0,0 +1,34 @@ +package com.ffii.core.utils; + +import java.util.HashMap; +import java.util.Map; + +/** + * @author fung + */ +public class MapBuilder { + + private Map args; + + public MapBuilder() { + args = new HashMap(); + } + + public MapBuilder(Map args) { + this.args = args; + } + + public MapBuilder add(K key, V value) { + args.put(key, value); + return this; + } + + public Map toMap() { + return args; + } + + @Override + public String toString() { + return args.toString(); + } +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/utils/MapUtils.java b/src/main/java/com/ffii/core/utils/MapUtils.java new file mode 100644 index 0000000..7928c1e --- /dev/null +++ b/src/main/java/com/ffii/core/utils/MapUtils.java @@ -0,0 +1,45 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.util.HashMap; +import java.util.Map; + +/** + * MapUtils + * + * @author Patrick + */ +public class MapUtils { + + /** + * Convert key-value pairs to HashMap + * + * @param keyValuePairs + * Keys and values must be in pairs + * + * @return Map + */ + @SuppressWarnings("unchecked") + public static Map toHashMap(Object... keyValuePairs) { + if (keyValuePairs.length % 2 != 0) + throw new IllegalArgumentException("Keys and values must be in pairs"); + + Map map = new HashMap(keyValuePairs.length / 2); + + for (int i = 0; i < keyValuePairs.length; i += 2) { + map.put((K) keyValuePairs[i], (V) keyValuePairs[i + 1]); + } + + return map; + } + +} diff --git a/src/main/java/com/ffii/core/utils/NumberUtils.java b/src/main/java/com/ffii/core/utils/NumberUtils.java new file mode 100644 index 0000000..278f6fc --- /dev/null +++ b/src/main/java/com/ffii/core/utils/NumberUtils.java @@ -0,0 +1,471 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.math.BigDecimal; +import java.math.RoundingMode; + +import org.apache.commons.lang3.ArrayUtils; + +/** + * NumberUtils extends from Apache Commons, and incl some methods from MathUtils + * + * @author Patrick + */ +public abstract class NumberUtils extends org.apache.commons.lang3.math.NumberUtils { + + /** + * Round the given value to the specified number of decimal places. The value is rounded using the given method which is any method defined in + * {@link BigDecimal}. + * + * @param x + * the value to round + * @param scale + * the number of digits to the right of the decimal point + * @param roundingMethod + * the rounding method as defined in {@link RoundingMode} + * @return the rounded value + */ + public static double round(double x, int scale, RoundingMode roundingMethod) { + try { + return BigDecimal.valueOf(x).setScale(scale, roundingMethod).doubleValue(); + } catch (NumberFormatException ex) { + if (Double.isInfinite(x)) { + return x; + } else { + return Double.NaN; + } + } + } + + /** + * Round the given value to the specified number of decimal places. The value is rounded using the {@link RoundingMode#HALF_UP} method. + * + * @param x + * the value to round + * @param scale + * the number of digits to the right of the decimal point + * @return the rounded value + * @see org.apache.commons.math.util.MathUtils#round(double, int) + */ + public static double round(double x, int scale) { + return round(x, scale, RoundingMode.HALF_UP); + } + + /** + * Round up the given value to the specified number of decimal places. The value is rounded up using the {@link RoundingMode#UP} method. + * + * @param x + * the value to round up + * @param scale + * the number of digits to the right of the decimal point + * @return the rounded up value + */ + public static double roundUp(double x, int scale) { + return round(x, scale, RoundingMode.UP); + } + + /** + * Round down the given value to the specified number of decimal places. The value is rounded down using the {@link RoundingMode#DOWN} method. + * + * @param x + * the value to round down + * @param scale + * the number of digits to the right of the decimal point + * @return the rounded down value + */ + public static double roundDown(double x, int scale) { + return round(x, scale, RoundingMode.DOWN); + } + + /** + * Return the {@code int} value of an {@code Object}, or the default value if the object is either {@code null} or not an instance of {@code Number}. + * + * @param obj + * the {@code Object} + * @param defaultValue + * the default value + * @return the {@code int} value of the {@code Object}, or the default if the object is either {@code null} or not an instance of {@code Number} + * @see Number#intValue() + */ + public static int intValue(Object obj, int defaultValue) { + if (obj instanceof Number) { + return ((Number) obj).intValue(); + } else if (obj instanceof String) { + try { + return Integer.parseInt((String) obj); + } catch (NumberFormatException nfe) { + } + } + return defaultValue; + } + + /** + * Return the {@code int} value of an {@code Object}, or {@code zero} if the object is either {@code null} or not an instance of {@code Number}. + * + * @param obj + * the {@code Object} + * @return the {@code int} value of the {@code Object}, or {@code zero} if the object is either {@code null} or not an instance of {@code Number} + * @see Number#intValue() + */ + public static int intValue(Object obj) { + return intValue(obj, 0); + } + + /** + * Convert an {@code Object} to an {@code Integer} (only if the object is an instance of {@code Number} or {@code String}), returning a default value if the + * conversion fails. + *

+ * If the object is {@code null}, the default value is returned. + * + * @param obj + * the object to convert, may be {@code null} + * @param defaultValue + * the default value, may be {@code null} + * @return the Integer represented by the object, or the default if conversion fails + */ + public static Integer toInt(Object obj, Integer defaultValue) { + if (obj instanceof Number) + return Integer.valueOf(((Number) obj).intValue()); + else if (obj instanceof String) + try { + return Integer.valueOf((String) obj); + } catch (NumberFormatException nfe) { + return defaultValue; + } + else + return defaultValue; + } + + /** + * Return the {@code long} value of a {@code Long} object, or a default value if the object is {@code null}. + * + * @param obj + * the object (can be {@code null}) + * @param defaultValue + * the default value + * @return the {@code long} value of the object if it's a number, or the default value if the object is {@code null} or {@code NaN} + * @see Long#longValue() + */ + public static long longValue(Object obj, long defaultValue) { + return (obj instanceof Number) ? ((Number) obj).longValue() : defaultValue; + } + + /** + * Return the {@code long} value of a {@code Long} object, or {@code zero} if the object is {@code null}. + * + * @param obj + * the object (can be {@code null}) + * @return the {@code long} value of the object if it's a number, or {@code zero} if the object is {@code null} or {@code NaN} + * @see Long#longValue() + */ + public static long longValue(Object obj) { + return longValue(obj, 0l); + } + + /** + * Convert an {@code Object} to a {@code Long} (only if the object is an instance of {@code Number} or {@code String}), returning a default value if the + * conversion fails. + *

+ * If the object is {@code null}, the default value is returned. + * + * @param obj + * the object to convert, may be {@code null} + * @param defaultValue + * the default value, may be {@code null} + * @return the Long represented by the object, or the default if conversion fails + */ + public static Long toLong(Object obj, Long defaultValue) { + if (obj instanceof Number) + return Long.valueOf(((Number) obj).longValue()); + else if (obj instanceof String) + try { + return Long.valueOf((String) obj); + } catch (NumberFormatException nfe) { + return defaultValue; + } + else + return defaultValue; + } + + /** + * @param obj + * the object (can be {@code null}) + * @param defaultValue + * the default value + * @return the {@code double} value of the object if it's a number, or the default value if the object is {@code null} or {@code NaN} + * @see Double#doubleValue() + */ + public static double doubleValue(Object obj, double defaultValue) { + return (obj instanceof Number) ? ((Number) obj).doubleValue() : defaultValue; + } + + /** + * @param obj + * the object (can be {@code null}) + * @param defaultValue + * the default value + * @return the {@code double} value of the object if it's a number, or {@code zero} if the object is {@code null} or {@code NaN} + * @see Double#doubleValue() + */ + public static double doubleValue(Object obj) { + return doubleValue(obj, 0.0d); + } + + /** + * Convert an {@code Object} to a {@code Double} (only if the object is an instance of {@code Number} or {@code String}), returning a default value if the + * conversion fails. + *

+ * If the object is {@code null}, the default value is returned. + * + * @param obj + * the object to convert, may be {@code null} + * @param defaultValue + * the default value, may be {@code null} + * @return the Double represented by the object, or the default if conversion fails + */ + public static Double toDouble(Object obj, Double defaultValue) { + if (obj instanceof Number) + return Double.valueOf(((Number) obj).doubleValue()); + else if (obj instanceof String) + try { + return Double.valueOf((String) obj); + } catch (NumberFormatException nfe) { + return defaultValue; + } + else + return defaultValue; + } + + /** + * Return the {@code BigDecimal} object, or {@code zero} if the object is {@code null}. + * + * @param obj + * the {@code BigDecimal} object + * @return the {@code BigDecimal} object, or {@code zero} if the object is {@code null} + */ + public static BigDecimal decimalValue(BigDecimal obj) { + return decimalValue(obj, BigDecimal.ZERO); + } + + /** + * Return the {@code BigDecimal} object, or a default value if the object is {@code null}. + * + * @param obj + * the {@code BigDecimal} object + * @param defaultValue + * the default value + * @return the {@code BigDecimal} object, or the default if the object is {@code null} + */ + public static BigDecimal decimalValue(BigDecimal obj, BigDecimal defaultValue) { + return obj == null ? defaultValue : obj; + } + + /** + * Convert an {@code Object} to a {@code BigDecimal}, returning {@code BigDecimal.ZERO} if the conversion fails (e.g. the object is not an instance of + * {@code Number} nor {@code String}). + *

+ * If the object is {@code null}, {@code BigDecimal.ZERO} is returned. + * + * @param obj + * the object to convert, may be {@code null} + * @return the BigDecimal represented by the object, or {@code BigDecimal.ZERO} if conversion fails + */ + public static BigDecimal toDecimal(Object obj) { + return toDecimal(obj, BigDecimal.ZERO); + } + + /** + * Convert an {@code Object} to a {@code BigDecimal}, returning a default value if the conversion fails (e.g. the object is not an instance of + * {@code Number} nor {@code String}). + *

+ * If the object is {@code null}, the default value is returned. + * + * @param obj + * the object to convert, may be {@code null} + * @param defaultValue + * the default value, may be {@code null} + * @return the BigDecimal represented by the object, or the default if conversion fails + */ + public static BigDecimal toDecimal(Object obj, BigDecimal defaultValue) { + if (obj instanceof BigDecimal) + return (BigDecimal) obj; + else if (obj instanceof Number) + return BigDecimal.valueOf(((Number) obj).doubleValue()); + else if (obj instanceof String) + try { + return new BigDecimal((String) obj); + } catch (NumberFormatException nfe) { + return defaultValue; + } + else + return defaultValue; + } + + /** + * Null-safe method to check if the two {@code Integer} objects have the same value. + * + *

    + *
  1. Returns {@code true} if {@code a} and {@code b} are both {@code null}. + *
  2. Returns {@code false} if only one of them is {@code null}. + *
  3. Returns {@code true} if {@code a} and {@code b} are not {@code null} and have the same {@code int} value, else returns {@code false}. + *
+ * + * @param a + * Integer obj, may be {@code null} + * @param b + * Integer obj, may be {@code null} + */ + public static boolean isEqual(Integer a, Integer b) { + return a == null ? (b == null ? true : false) : (b == null ? false : a.equals(b)); + } + + /** + * Null-safe method to check if the two {@code Integer} objects have different values. + * + *
    + *
  1. Returns {@code false} if {@code a} and {@code b} are both {@code null}. + *
  2. Returns {@code true} if only one of them is {@code null}. + *
  3. Returns {@code true} if {@code a} and {@code b} are not {@code null} and have different {@code int} values, else returns {@code false}. + *
+ * + * @param a + * Integer obj, may be {@code null} + * @param b + * Integer obj, may be {@code null} + */ + public static boolean isNotEqual(Integer a, Integer b) { + return !isEqual(a, b); + } + + /** + * Null-safe method to check if the two {@code BigDecimal} objects have the same value. + *

+ * Two {@code BigDecimal} objects that are equal in value but have a different scale (like 2.0 and 2.00) are considered equal by this method. + * + *

    + *
  1. Returns {@code true} if {@code a} and {@code b} are both {@code null}. + *
  2. Returns {@code false} if only one of them is {@code null}. + *
  3. Returns {@code true} if {@code a} and {@code b} are not {@code null} and have the same {@code decimal} value, else returns {@code false}. + *
+ * + * @param a + * BigDecimal obj, may be {@code null} + * @param b + * BigDecimal obj, may be {@code null} + */ + public static boolean isEqual(BigDecimal a, BigDecimal b) { + return a == null ? (b == null ? true : false) : (b == null ? false : a.compareTo(b) == 0); + } + + /** + * Null-safe method to check if the two {@code BigDecimal} objects have different values. + *

+ * Two {@code BigDecimal} objects that are equal in value but have a different scale (like 2.0 and 2.00) are considered equal by this method. + * + *

    + *
  1. Returns {@code false} if {@code a} and {@code b} are both {@code null}. + *
  2. Returns {@code true} if only one of them is {@code null}. + *
  3. Returns {@code true} if {@code a} and {@code b} are not {@code null} and have different {@code decimal} values, else returns {@code false}. + *
+ * + * @param a + * BigDecimal obj, may be {@code null} + * @param b + * BigDecimal obj, may be {@code null} + */ + public static boolean isNotEqual(BigDecimal a, BigDecimal b) { + return !isEqual(a, b); + } + + /** + * Check if {@code BigDecimal} object {@code a} is greater than {@code BigDecimal} object {@code b}. + * + * @param a + * non-{@code null} BigDecimal obj + * @param b + * non-{@code null} BigDecimal obj + */ + public static boolean isGreaterThan(BigDecimal a, BigDecimal b) { + return a.compareTo(b) > 0; + } + + /** + * Check if {@code BigDecimal} object {@code a} is greater than or equals to {@code BigDecimal} object {@code b}. + * + * @param a + * non-{@code null} BigDecimal obj + * @param b + * non-{@code null} BigDecimal obj + */ + public static boolean isGreaterThanOrEqual(BigDecimal a, BigDecimal b) { + return a.compareTo(b) >= 0; + } + + /** + * Check if {@code BigDecimal} object {@code a} is less than {@code BigDecimal} object {@code b}. + * + * @param a + * non-{@code null} BigDecimal obj + * @param b + * non-{@code null} BigDecimal obj + */ + public static boolean isLessThan(BigDecimal a, BigDecimal b) { + return a.compareTo(b) < 0; + } + + /** + * Check if {@code BigDecimal} object {@code a} is less than or equals to {@code BigDecimal} object {@code b}. + * + * @param a + * non-{@code null} BigDecimal obj + * @param b + * non-{@code null} BigDecimal obj + */ + public static boolean isLessThanOrEqual(BigDecimal a, BigDecimal b) { + return a.compareTo(b) <= 0; + } + + /** + * + *
+	 * NumberUtils.equalsAny(null, (Integer[]) null) = false
+	 * NumberUtils.equalsAny(null, null, null)       = true
+	 * NumberUtils.equalsAny(null, 1, 2)             = false
+	 * NumberUtils.equalsAny(1, null, 2)             = false
+	 * NumberUtils.equalsAny(1, 1, 2)                = true
+	 * 
+ * + * @param int + * to compare, may be {@code null}. + * @param searchInts + * a int, may be {@code null}. + * @return {@code true} if the num is equal to any other element of searchInts; {@code false} if searchInts is null or contains no + * matches. + */ + public static boolean equalsAny(final int num, int... searchInts) { + if (ArrayUtils.isNotEmpty(searchInts)) { + for (int next : searchInts) { + if (num == next) { + return true; + } + } + } + return false; + } + + public static double sum(double... nums) { + BigDecimal rs = BigDecimal.ZERO; + for (double num : nums) + rs = rs.add(BigDecimal.valueOf(num)); + return rs.doubleValue(); + } +} diff --git a/src/main/java/com/ffii/core/utils/Params.java b/src/main/java/com/ffii/core/utils/Params.java new file mode 100644 index 0000000..508d890 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/Params.java @@ -0,0 +1,81 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +/** + * Static strings for standard params + * + * @author Patrick + */ +public abstract class Params { + + public static final String ID = "id"; + + public static final String TYPE = "type"; + + public static final String QUERY = "query"; + + public static final String CODE = "code"; + public static final String NAME = "name"; + public static final String TITLE = "title"; + + public static final String KEY = "key"; + public static final String VALUE = "value"; + + public static final String SUCCESS = "success"; + + public static final String AUTH = "auth"; + + /** Short for "message" */ + public static final String MSG = "msg"; + + public static final String DETAILS = "details"; + + public static final String DATA = "data"; + public static final String RECORDS = "records"; + public static final String ROOT = "root"; + public static final String NODE = "node"; + public static final String EXPANDED = "expanded"; + + public static final String FROM = "from"; + public static final String TO = "to"; + + public static final String START = "start"; + public static final String LIMIT = "limit"; + + public static final String PREFIX = "prefix"; + public static final String SUFFIX = "suffix"; + + public static final String LENGTH = "length"; + + public static final String MODE = "mode"; + + public static final String COUNT = "count"; + + public static final String TOTAL = "total"; + + public static final String STATUS = "status"; + + public static final String VERSION_ID = "versionId"; + + public static final String REF_ID = "refId"; + public static final String REF_TYPE = "refType"; + public static final String REF_CODE = "refCode"; + + public static final String FROM_DATE = "fromDate"; + public static final String TO_DATE = "toDate"; + + public static final String MAX_ROWS = "maxRows"; + + public static final String METHOD_GET = "GET"; + public static final String METHOD_POST = "POST"; + +} diff --git a/src/main/java/com/ffii/core/utils/SecurityUtils.java b/src/main/java/com/ffii/core/utils/SecurityUtils.java new file mode 100644 index 0000000..add01f5 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/SecurityUtils.java @@ -0,0 +1,225 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.Random; +import java.util.regex.Pattern; + +import com.ffii.core.User; +import com.ffii.tbms.user.service.UserService; + +import org.springframework.dao.DataAccessException; +import org.springframework.security.authentication.UsernamePasswordAuthenticationToken; +import org.springframework.security.core.Authentication; +import org.springframework.security.core.GrantedAuthority; +import org.springframework.security.core.context.SecurityContext; +import org.springframework.security.core.context.SecurityContextHolder; +import org.springframework.security.core.userdetails.UserDetails; +import org.springframework.security.core.userdetails.UserDetailsService; +import org.springframework.security.core.userdetails.UsernameNotFoundException; + +/** + * Security Utils - for Spring Security + * + * @author Patrick + */ +public class SecurityUtils { + + private static final Pattern PATTERN_DIGITS = Pattern.compile("[0-9]"); + private static final Pattern PATTERN_A2Z_LOWER = Pattern.compile("[a-z]"); + private static final Pattern PATTERN_A2Z_UPPER = Pattern.compile("[A-Z]"); + + private static final String A2Z_LOWER = "abcdefghijklmnopqrstuvwxyz"; + private static final String A2Z_UPPER = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; + private static final String DIGITS = "0123456789"; + + /* + * Ref: https://www.owasp.org/index.php/Password_special_characters + * without space character + */ + private static final String SPECIAL_CHARS = "!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~"; + private static Pattern PATTERN_SPECIAL_CHARS = Pattern.compile("[!\"#$%&'()*+,-./:;<=>?@\\[\\\\\\]^_`{|}~]"); + + /** + * Obtains the current {@code SecurityContext}. + * + * @return the security context (never {@code null}) + */ + public static final SecurityContext getSecurityContext() { + return SecurityContextHolder.getContext(); + } + + /** + * @return the authenticated {@code Principal} ({@code User}) + * @see Authentication#getPrincipal() + */ + public static final User getUser() { + try { + return (User) getSecurityContext().getAuthentication().getPrincipal(); + } catch (ClassCastException e) { + // no authenticated principal + return null; + } catch (NullPointerException e) { + // no authentication information is available + return null; + } + } + + /** + * Updates the Authentication Token with the user (e.g. user changed the password) + * + * @see SecurityContext#setAuthentication(Authentication) + */ + public static final void updateUserAuthentication(final User user) { + getSecurityContext().setAuthentication(new UsernamePasswordAuthenticationToken(user, user.getPassword(), user.getAuthorities())); + } + + /** + * Checks if the current user is GRANTED the {@code role} + * + * @param role + * the {@code role} to check for + * @return {@code true} if the current user is GRANTED the {@code role}, else {@code false} + */ + public static final boolean isGranted(String role) { + Authentication authentication = getSecurityContext().getAuthentication(); + if (authentication == null) return false; + for (GrantedAuthority auth : authentication.getAuthorities()) { + if (auth.getAuthority().equals("SUPERUSER")) return true; + if (role.equals(auth.getAuthority())) return true; + } + return false; + } + + public static final boolean isGrantedOnly(String role) { + Authentication authentication = getSecurityContext().getAuthentication(); + if (authentication == null) return false; + for (GrantedAuthority auth : authentication.getAuthorities()) { + if (role.equals(auth.getAuthority())) return true; + } + return false; + } + + /** + * Checks if the current user is NOT GRANTED the {@code role} + * + * @param role + * the {@code role} to check for + * @return {@code true} if the current user is NOT GRANTED the {@code role}, else {@code false} + */ + public static final boolean isNotGranted(String role) { + return !isGranted(role); + } + + /** + * Checks if the current user is GRANTED ANY of the {@code role}s + * + * @param roles + * the {@code role}s to check for + * @return {@code true} if the current user is GRANTED ANY of the {@code role}s, else {@code false} + */ + public static final boolean isGrantedAny(String... roles) { + for (int i = 0; i < roles.length; i++) { + if (isGranted(roles[i])) return true; + } + return false; + } + + /** + * Checks if the current user is NOT GRANTED ANY of the {@code role}s + * + * @param roles + * the {@code role}s to check for + * @return {@code true} if the current user is NOT GRANTED ANY of the {@code role}s, else {@code false} + */ + public static final boolean isNotGrantedAny(String... roles) { + return !isGrantedAny(roles); + } + + /** + * Checks if the current user is GRANTED ALL of the {@code role}s + * + * @param roles + * the {@code role}s to check for + * @return {@code true} if the current user is GRANTED ALL of the {@code role}s, else {@code false} + */ + public static final boolean isGrantedAll(String... roles) { + for (int i = 0; i < roles.length; i++) { + if (isNotGranted(roles[i])) return false; + } + return true; + } + + /** + * Login a user non-interactively + * + * @param userService + * any implementation of {@link UserDetailsService} + * @param username + * the username + * + * @throws UsernameNotFoundException + * if the user could not be found or the user has no GrantedAuthority + * @throws DataAccessException + * if user could not be found for a repository-specific reason + */ + public static final void loginUser(UserDetailsService userService, String username) { + /* load the user, throw exception if user not found */ + UserDetails userDetails = userService.loadUserByUsername(username); + + /* create authentication token for the specified user */ + Authentication authentication = new UsernamePasswordAuthenticationToken(userDetails, userDetails.getPassword(), userDetails.getAuthorities()); + getSecurityContext().setAuthentication(authentication); + } + + public static final boolean checkPwd(String pwd, int min, int max, boolean num, boolean upperEng, boolean lowerEng, boolean special) { + if (pwd == null) return false; + if (pwd.length() < min) return false; + if (pwd.length() > max) return false; + + if (num && !PATTERN_DIGITS.matcher(pwd).find()) return false; + if (upperEng && !PATTERN_A2Z_UPPER.matcher(pwd).find()) return false; + if (lowerEng && !PATTERN_A2Z_LOWER.matcher(pwd).find()) return false; + if (special && !PATTERN_SPECIAL_CHARS.matcher(pwd).find()) return false; + + return true; + } + + public static String genPwd(int length, boolean num, boolean upperEng, boolean lowerEng, boolean special) { + if (length <= 0) return ""; + + StringBuilder password = new StringBuilder(length); + Random random = new Random(System.nanoTime()); + + List charCategories = new ArrayList<>(4); + if (lowerEng) charCategories.add(A2Z_LOWER); + if (upperEng) charCategories.add(A2Z_UPPER); + if (num) charCategories.add(DIGITS); + if (special) charCategories.add(SPECIAL_CHARS); + + for (int i = 0; i < length; i++) { + String charCategory = charCategories.get(i % charCategories.size()); + char randomChar = charCategory.charAt(random.nextInt(charCategory.length())); + if (password.length() > 0) + password.insert(random.nextInt(password.length()), randomChar); + else + password.append(randomChar); + } + + return password.toString(); + } + + public static void authArgs(Map args){ + args.put("sysGroupId", getUser().getSysGroupId()); + } + +} diff --git a/src/main/java/com/ffii/core/utils/SqlUtils.java b/src/main/java/com/ffii/core/utils/SqlUtils.java new file mode 100644 index 0000000..8e04ca5 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/SqlUtils.java @@ -0,0 +1,20 @@ +package com.ffii.core.utils; + +public class SqlUtils { + + /** + * for IN() of SQL. if no parameter, it will return "''" + * + * @return 'obj1','obj2','obj3','obj4'... + */ + public static String toInString(Object... objs) { + String rs = ""; + for (int i = 0; i < objs.length; i++) { + if (i != 0) rs += ","; + rs += "'" + objs[i] + "'"; + } + if (StringUtils.isBlank(rs)) + rs += "''"; + return rs; + } +} diff --git a/src/main/java/com/ffii/core/utils/StringUtils.java b/src/main/java/com/ffii/core/utils/StringUtils.java new file mode 100644 index 0000000..7c95bf8 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/StringUtils.java @@ -0,0 +1,71 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +/** + * String Utils based on Apache Commons StringUtils. + * + * @author Patrick + */ +public abstract class StringUtils extends org.apache.commons.lang3.StringUtils { + + /** + * The String {@code "0"}. + */ + public static final String ZERO = "0"; + + /** + * The String {@code "1"}. + */ + public static final String ONE = "1"; + + /** + * The String {@code "%"}. + */ + public static final String PERCENT = "%"; + + /** + * The String {@code ","}. + */ + public static final String COMMA = ","; + + /** + * The String {@code "\r\n"} for line break on Windows + */ + public static final String LINE_BREAK_WINDOWS = "\r\n"; + + /** + * The String {@code "\n"} for line break on Unix/Linux + */ + public static final String LINE_BREAK_LINUX = "\n"; + + public static final String[] A2Z_LOWWER = { "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", + "w", "x", "y", "z" }; + public static final String[] A2Z_UPPER = { "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", + "W", "X", "Y", "Z" }; + + public static final String concat(String segregator, final String... chars) { + if (segregator == null) segregator = ""; + String rs = ""; + for (String c : chars) { + if (c == null) + continue; + else { + if (StringUtils.isBlank(rs)) { + rs = c; + } else { + rs += segregator + c; + } + } + } + return rs; + } +} diff --git a/src/main/java/com/ffii/core/utils/ZXingUtils.java b/src/main/java/com/ffii/core/utils/ZXingUtils.java new file mode 100644 index 0000000..740fa8e --- /dev/null +++ b/src/main/java/com/ffii/core/utils/ZXingUtils.java @@ -0,0 +1,54 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core2 project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils; + +import java.awt.Image; + +import com.google.zxing.BarcodeFormat; +import com.google.zxing.Writer; +import com.google.zxing.WriterException; +import com.google.zxing.client.j2se.MatrixToImageWriter; +import com.google.zxing.common.BitMatrix; +import com.google.zxing.oned.Code128Writer; +import com.google.zxing.qrcode.QRCodeWriter; + +/** + * ZXing Utils + * + * @author Patrick + */ +public abstract class ZXingUtils { + + private static final Writer CODE128_WRITER = new Code128Writer(); + + private static final Writer QR_CODE_WRITER = new QRCodeWriter(); + + /** + * Encode contents (String) to Code 128 image + * + * @throws WriterException + */ + public static Image encodeToImageCode128(String contents, int width, int height) throws WriterException { + BitMatrix matrix = CODE128_WRITER.encode(contents, BarcodeFormat.CODE_128, width, height); + return MatrixToImageWriter.toBufferedImage(matrix); + } + + /** + * Encode contents (String) to QR Code image + * + * @throws WriterException + */ + public static Image encodeToImageQRCode(String contents, int width, int height) throws WriterException { + BitMatrix matrix = QR_CODE_WRITER.encode(contents, BarcodeFormat.QR_CODE, width, height); + return MatrixToImageWriter.toBufferedImage(matrix); + } + +} diff --git a/src/main/java/com/ffii/core/utils/sql/QueryBuilder.java b/src/main/java/com/ffii/core/utils/sql/QueryBuilder.java new file mode 100644 index 0000000..df3a992 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/sql/QueryBuilder.java @@ -0,0 +1,114 @@ +package com.ffii.core.utils.sql; + +import java.util.Map; + +import com.ffii.core.utils.StringUtils; + +/** + *

a query builder for handling paging

+ *

suffix cannot blank

+ *

+ * paging arguments key: + * "start": integer (base at 0), + * "limit": integer + *

+ * + * @see #setPaging(boolean) + * @see #setPrefix(String) + * @see #setSuffix(String) + * + * @@author Fung + */ +public class QueryBuilder implements java.io.Serializable { + private static final long serialVersionUID = 4433680400177304974L; + + // setting + private boolean paging = false; + private Map args; + + /** "SELECT *" */ + private String prefix; + + /** "FROM xxxxxxx WHERE true" */ + private String suffix; + + /** default disable paging */ + public QueryBuilder(){} + public QueryBuilder(boolean paging){ + this.paging = paging; + } + + @Override + public String toString() { + return getSearchSql(); + } + + public String getSearchSql() { + parameterCheck(); + return getPrefix() + " " + getSuffix() + (this.paging ? limitQuery() : ""); + } + + /** column name "count" */ + public String getTotalSql() { + parameterCheck(); + return "SELECT COUNT(1) 'count'" + " " + getSuffix(); + } + + private void parameterCheck() { + if (StringUtils.isBlank(suffix)) + throw new IllegalArgumentException("suffix of sql cannot blank"); + } + + private String limitQuery() { + if (args == null) + return StringUtils.EMPTY; + else if (args.containsKey("start") && args.containsKey("limit")) + return " LIMIT :start,:limit"; + else if (args.containsKey("limit")) + return " LIMIT :limit"; + else + return StringUtils.EMPTY; + } + + // setter and getter + + public boolean isPaging() { + return this.paging; + } + + public boolean getPaging() { + return this.paging; + } + + /** true for paging query, default false*/ + public void setPaging(boolean paging) { + this.paging = paging; + } + + public Map getArgs() { + return this.args; + } + + public void setArgs(Map args) { + this.args = args; + } + + public String getPrefix() { + return StringUtils.isNotBlank(this.prefix) ? this.prefix : "SELECT *"; + } + + /** "SELECT *" */ + public void setPrefix(String prefix) { + this.prefix = prefix; + } + + public String getSuffix() { + return this.suffix; + } + + /**

"FROM xxxxxxxx WHERE true"

suffix cannot blank*/ + public void setSuffix(String suffix) { + this.suffix = suffix; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/utils/web/ServletRequestUtils.java b/src/main/java/com/ffii/core/utils/web/ServletRequestUtils.java new file mode 100644 index 0000000..48b7522 --- /dev/null +++ b/src/main/java/com/ffii/core/utils/web/ServletRequestUtils.java @@ -0,0 +1,336 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils.web; + +import java.io.IOException; +import java.util.Collections; +import java.util.Date; +import java.util.Enumeration; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.ServletRequest; +import javax.servlet.http.HttpServletRequest; + +import com.ffii.core.support.SimpleDateEditor; +import com.ffii.core.support.SimpleIntegerEditor; +import com.ffii.core.support.SimpleStringTrimToNullEditor; +import com.ffii.core.utils.DateUtils; +import com.ffii.core.utils.JsonUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.StringUtils; + +import org.apache.commons.lang3.ArrayUtils; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.ServletRequestDataBinder; + +/** + * ServletRequestUtils (extends from Spring Framework) + * + * @author Patrick + */ +public abstract class ServletRequestUtils extends org.springframework.web.bind.ServletRequestUtils { + + /** + * Mobile User-Agent Signatures + */ + private static final String[] MOBILE_USER_AGENTS = { "Android", "iPhone", "iPad" }; + + /** + * Get the User-Agent from the request header + * + * @param request + * HttpServletRequest + * + * @return the User-Agent from the request header, or null if not found + */ + public static String getUserAgent(HttpServletRequest request) { + return request.getHeader("User-Agent"); + } + + /** + * Check if the User-Agent is mobile device + * + * @param request + * HttpServletRequest + * + * @return true if the User-Agent is mobile device + */ + public static boolean isMobileUserAgent(HttpServletRequest request) { + for (String MOBILE_USER_AGENT : MOBILE_USER_AGENTS) { + if (StringUtils.containsIgnoreCase(getUserAgent(request), MOBILE_USER_AGENT)) + return true; + } + return false; + } + + /** + * Get a Map of request parameters + * + * @param request + * current HTTP request + * + * @return a Map containing all of the request parameters + */ + public static Map getParameters(ServletRequest request) { + Enumeration params = request.getParameterNames(); + Map paramsMap = new HashMap(); + while (params.hasMoreElements()) { + String paramName = (String) params.nextElement(); + String paramValue = request.getParameter(paramName); + paramsMap.put(paramName, paramValue); + } + return paramsMap; + } + + /** + * Get an Integer parameter, with a fallback value. Never throws an exception. Can pass a distinguished value as default to enable checks of whether it was + * supplied. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * @param defaultVal + * the default value to use as fallback + * + * @return the Integer value, or defaultVal if not present OR if the value cannot be parsed + */ + public static Integer getIntParameter(ServletRequest request, String name, Integer defaultVal) { + try { + return getIntParameter(request, name); + } catch (ServletRequestBindingException e) { + return defaultVal; + } + } + + /** + * Get a Long parameter, with a fallback value. Never throws an exception. Can pass a distinguished value as default to enable checks of whether it was + * supplied. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * @param defaultVal + * the default value to use as fallback + * + * @return the Long value, or defaultVal if not present OR if the value cannot be parsed + */ + public static Long getLongParameter(ServletRequest request, String name, Long defaultVal) { + try { + return getLongParameter(request, name); + } catch (ServletRequestBindingException e) { + return defaultVal; + } + } + + /** + * Get a Double parameter, with a fallback value. Never throws an exception. Can pass a distinguished value as default to enable checks of whether it was + * supplied. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * @param defaultVal + * the default value to use as fallback + * + * @return the Double value, or defaultVal if not present OR if the value cannot be parsed + */ + public static Double getDoubleParameter(ServletRequest request, String name, Double defaultVal) { + try { + return getDoubleParameter(request, name); + } catch (ServletRequestBindingException e) { + return defaultVal; + } + } + + /** + * Get a trimmed (to null if blank) String parameter, or null if not present. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * + * @return the trimmed (to null if blank) String value, or null if not present + * + * @throws ServletRequestBindingException + * a subclass of ServletException, so it doesn't need to be caught + */ + public static String getTrimmedStringParameter(ServletRequest request, String name) throws ServletRequestBindingException { + return StringUtils.trimToNull(org.springframework.web.bind.ServletRequestUtils.getStringParameter(request, name)); + } + + /** + * Get a trimmed (to null if blank) String parameter, with a fallback value. Never throws an exception. Can pass a distinguished value to + * default to enable checks of whether it was supplied. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * @param defaultVal + * the default value to use as fallback + * + * @return the trimmed (to null if blank) String value, or defaultVal (will be trimmed to null if blank) if not + * present + */ + public static String getTrimmedStringParameter(ServletRequest request, String name, String defaultVal) { + return StringUtils.trimToNull(org.springframework.web.bind.ServletRequestUtils.getStringParameter(request, name, defaultVal)); + } + + /** + * Get a SQL Date parameter, or null if not present or cannot be parsed. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * @param defaultVal + * the default value to use as fallback + * + * @return the SQL Date value, or null if not present or cannot be parsed + */ + public static java.sql.Date getSqlDateParameter(ServletRequest request, String name) throws ServletRequestBindingException { + return getSqlDateParameter(request, name, null); + } + + /** + * Get a SQL Date parameter, with a fallback value. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * @param defaultVal + * the default value to use as fallback + * + * @return the SQL Date value, or default value if not present or cannot be parsed + */ + public static java.sql.Date getSqlDateParameter(ServletRequest request, String name, java.sql.Date defaultVal) throws ServletRequestBindingException { + return DateUtils.toSqlDate(DateUtils.parseDateStrictly((getTrimmedStringParameter(request, name)), DateUtils.PARSE_PATTERNS, defaultVal)); + } + + /** + * Get a Date parameter, or null if not present or cannot be parsed. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * @param defaultVal + * the default value to use as fallback + * + * @return the Date value, or null if not present or cannot be parsed + */ + public static Date getDateParameter(ServletRequest request, String name) throws ServletRequestBindingException { + return getDateParameter(request, name, null); + } + + /** + * Get a Date parameter, with a fallback value. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * @param defaultVal + * the default value to use as fallback + * + * @return the Date value, or default value if not present or cannot be parsed + */ + public static Date getDateParameter(ServletRequest request, String name, Date defaultVal) throws ServletRequestBindingException { + return DateUtils.parseDateStrictly((getTrimmedStringParameter(request, name)), DateUtils.PARSE_PATTERNS, defaultVal); + } + + /** + * Get a List of Map from JSON string parameter. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * + * @return a List of Map, or an empty List if the parameter is not present + */ + public static List getJsonListParameter(ServletRequest request, String name) throws ServletRequestBindingException, IOException { + String content = getStringParameter(request, name); + if (content != null) + return JsonUtils.fromJsonString(content, List.class); + else + return Collections.EMPTY_LIST; + } + + /** + * Get a Map from JSON string parameter. + * + * @param request + * current HTTP request + * @param name + * the name of the parameter + * + * @return a Map, or an empty Map if the parameter is not present + */ + public static Map getJsonMapParameter(ServletRequest request, String name) throws ServletRequestBindingException, IOException { + String content = getStringParameter(request, name); + if (content != null) + return JsonUtils.fromJsonString(content, Map.class); + else + return Collections.EMPTY_MAP; + } + + /** + * Binds data using {@link ServletRequestDataBinder} with the following custom editors:- + * + *
    + *
  • {@link SimpleStringTrimToNullEditor}
  • + *
  • {@link SimpleIntegerEditor}
  • + *
  • {@link SimpleDateEditor}
  • + *
+ * + *

+ * Important: The following system fields will NOT be binded for security reasons. + *

    + *
  • id
  • + *
  • ownerId
  • + *
  • deleted
  • + *
  • createdBy
  • + *
  • modifiedBy
  • + *
  • created
  • + *
  • modified
  • + *
  • password
  • + *
+ *

+ * + * @param request + * current HTTP request + * @param object + * the target object to bind onto + * @param objectName + * the name of the target object + * @param disallowFields + * optional + */ + public static Object doBind(ServletRequest request, Object object, String objectName, String... disallowFields) { + ServletRequestDataBinder binder = new ServletRequestDataBinder(object, objectName); + binder.registerCustomEditor(String.class, new SimpleStringTrimToNullEditor()); + binder.registerCustomEditor(Integer.class, new SimpleIntegerEditor()); + binder.registerCustomEditor(java.util.Date.class, new SimpleDateEditor()); + String[] coreFields = { Params.ID, "ownerId", "deleted", "createdBy", "modifiedBy", "created", "modified", "password" }; + binder.setDisallowedFields(ArrayUtils.addAll(coreFields, disallowFields)); + binder.bind(request); + return object; + }; + +} diff --git a/src/main/java/com/ffii/core/utils/web/ServletResponseUtils.java b/src/main/java/com/ffii/core/utils/web/ServletResponseUtils.java new file mode 100644 index 0000000..1fd6fec --- /dev/null +++ b/src/main/java/com/ffii/core/utils/web/ServletResponseUtils.java @@ -0,0 +1,72 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.utils.web; + +import java.io.IOException; +import java.io.OutputStreamWriter; +import java.io.UnsupportedEncodingException; + +import javax.servlet.ServletOutputStream; +import javax.servlet.http.HttpServletResponse; + +/** + * ServletResponseUtils + * + * @author Patrick + */ +public abstract class ServletResponseUtils { + + /** + * Writes a String to HttpServletResponse encoded with the specified charsetName, and then flush and close it. + * + * @param response + * HttpServletResponse + * @param charsetName + * The name of a supported {@link java.nio.charset.Charset
charset} + * @param str + * String to be written + */ + public static void writeStringToStream(HttpServletResponse response, String charsetName, String str) throws UnsupportedEncodingException, IOException { + OutputStreamWriter out = new OutputStreamWriter(response.getOutputStream(), charsetName); + out.write(str); + out.flush(); + out.close(); + } + + /** + * Writes bytes to HttpServletResponse, and then flush and close it. + * + * @param response + * HttpServletResponse + * @param bytes + * The bytes array to be written + * @throws IOException + */ + public static void writeBytesToStream(HttpServletResponse response, byte[] bytes) throws IOException { + ServletOutputStream out = response.getOutputStream(); + out.write(bytes); + out.flush(); + out.close(); + } + + /** + * Disables caching by modifying the response header. + * + * @param response + * HttpServletResponse + */ + public static void disableCaching(HttpServletResponse response) { + response.addHeader("Pragma", "no-cache"); + response.addHeader("Cache-Control", "no-cache, no-store, max-age=0"); + response.addDateHeader("Expires", 1L); + } + +} diff --git a/src/main/java/com/ffii/core/web/AbstractController.java b/src/main/java/com/ffii/core/web/AbstractController.java new file mode 100644 index 0000000..a63db7a --- /dev/null +++ b/src/main/java/com/ffii/core/web/AbstractController.java @@ -0,0 +1,17 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web; + +import org.springframework.web.context.support.WebApplicationObjectSupport; + +public abstract class AbstractController extends WebApplicationObjectSupport { + +} diff --git a/src/main/java/com/ffii/core/web/AbstractService.java b/src/main/java/com/ffii/core/web/AbstractService.java new file mode 100644 index 0000000..91a3ff2 --- /dev/null +++ b/src/main/java/com/ffii/core/web/AbstractService.java @@ -0,0 +1,17 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web; + +import org.springframework.web.context.support.WebApplicationObjectSupport; + +public abstract class AbstractService extends WebApplicationObjectSupport { + +} diff --git a/src/main/java/com/ffii/core/web/AppConfig.java b/src/main/java/com/ffii/core/web/AppConfig.java new file mode 100644 index 0000000..4b9b5ba --- /dev/null +++ b/src/main/java/com/ffii/core/web/AppConfig.java @@ -0,0 +1,10 @@ +package com.ffii.core.web; + +import org.springframework.context.annotation.Configuration; +import org.springframework.transaction.annotation.EnableTransactionManagement; + +@Configuration +@EnableTransactionManagement +public class AppConfig { + +} diff --git a/src/main/java/com/ffii/core/web/ControllerAdvice.java b/src/main/java/com/ffii/core/web/ControllerAdvice.java new file mode 100644 index 0000000..14d3513 --- /dev/null +++ b/src/main/java/com/ffii/core/web/ControllerAdvice.java @@ -0,0 +1,35 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web; + +import org.springframework.web.bind.WebDataBinder; +import org.springframework.web.bind.annotation.InitBinder; + +import com.ffii.core.support.SimpleDateEditor; +import com.ffii.core.support.SimpleIntegerEditor; +import com.ffii.core.support.SimpleStringTrimToNullEditor; + +/** + * ControllerAdvice is used to define @ExceptionHandler, @InitBinder, and @ModelAttribute methods that apply to all @RequestMapping methods. + * + * @author Patrick + */ +@org.springframework.web.bind.annotation.ControllerAdvice +public class ControllerAdvice { + + @InitBinder + public void initBinder(WebDataBinder binder) { + binder.registerCustomEditor(String.class, new SimpleStringTrimToNullEditor()); + binder.registerCustomEditor(Integer.class, new SimpleIntegerEditor()); + binder.registerCustomEditor(java.util.Date.class, new SimpleDateEditor()); + } + +} diff --git a/src/main/java/com/ffii/core/web/RestResponseEntityExceptionHandler.java b/src/main/java/com/ffii/core/web/RestResponseEntityExceptionHandler.java new file mode 100644 index 0000000..ffc40dd --- /dev/null +++ b/src/main/java/com/ffii/core/web/RestResponseEntityExceptionHandler.java @@ -0,0 +1,37 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web; + +import org.apache.commons.lang3.exception.ExceptionUtils; +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; +import org.springframework.dao.DataIntegrityViolationException; +import org.springframework.http.HttpStatus; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.ExceptionHandler; +import org.springframework.web.context.request.WebRequest; +import org.springframework.web.servlet.mvc.method.annotation.ResponseEntityExceptionHandler; + +/** + * @author Patrick + */ +@org.springframework.web.bind.annotation.ControllerAdvice +public class RestResponseEntityExceptionHandler extends ResponseEntityExceptionHandler { + + protected final Log logger = LogFactory.getLog(getClass()); + + @ExceptionHandler(value = { DataIntegrityViolationException.class }) + protected ResponseEntity handleDataIntegrityViolationException(RuntimeException ex, WebRequest request) { + logger.error(ex.getMessage()); + return handleExceptionInternal(ex, ExceptionUtils.getRootCauseMessage(ex), null, HttpStatus.INTERNAL_SERVER_ERROR, request); + } + +} diff --git a/src/main/java/com/ffii/core/web/filter/AjaxSessionExpirationFilter.java b/src/main/java/com/ffii/core/web/filter/AjaxSessionExpirationFilter.java new file mode 100644 index 0000000..84a9851 --- /dev/null +++ b/src/main/java/com/ffii/core/web/filter/AjaxSessionExpirationFilter.java @@ -0,0 +1,52 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web.filter; + +import java.io.IOException; + +import javax.servlet.Filter; +import javax.servlet.FilterChain; +import javax.servlet.FilterConfig; +import javax.servlet.ServletException; +import javax.servlet.ServletRequest; +import javax.servlet.ServletResponse; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; +import javax.servlet.http.HttpSession; + +public class AjaxSessionExpirationFilter implements Filter { + + private int customSessionExpiredErrorCode = 403; + + @Override + public void init(FilterConfig cfg) throws ServletException { + } + + @Override + public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { + HttpSession currentSession = ((HttpServletRequest) request).getSession(false); + if (currentSession == null) { + String requestedWithHeader = ((HttpServletRequest) request).getHeader("X-Requested-With"); + if ("XMLHttpRequest".equals(requestedWithHeader)) { + ((HttpServletResponse) response).sendError(this.customSessionExpiredErrorCode); + } else { + chain.doFilter(request, response); + } + } else { + chain.doFilter(request, response); + } + } + + @Override + public void destroy() { + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/web/view/AbstractView.java b/src/main/java/com/ffii/core/web/view/AbstractView.java new file mode 100644 index 0000000..ed7fbb4 --- /dev/null +++ b/src/main/java/com/ffii/core/web/view/AbstractView.java @@ -0,0 +1,46 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web.view; + +import org.springframework.web.servlet.View; + +/** + * Abstract base class extending Spring {@link AbstractView} for {@link View} implementations. + * + * @see View + * @author Patrick + */ +public abstract class AbstractView extends org.springframework.web.servlet.view.AbstractView { + + public static final String CONTENT_TYPE_JSON = "application/json"; + + public static final String CONTENT_TYPE_JAVASCRIPT = "text/javascript"; + + public static final String CONTENT_TYPE_TEXT_HTML = "text/html"; + public static final String CONTENT_TYPE_TEXT_PLAIN = "text/plain"; + public static final String CONTENT_TYPE_XML = "text/xml"; + + public static final String CONTENT_TYPE_JPEG = "image/jpeg"; + public static final String CONTENT_TYPE_PNG = "image/png"; + + public static final String CHARSET_UTF8 = "UTF-8"; + + protected boolean disableCaching = true; + + /** + * Disables caching of the generated JSON.
+ * Default is {@code true}, which will prevent the client from caching the generated JSON. + */ + public void setDisableCaching(boolean disableCaching) { + this.disableCaching = disableCaching; + } + +} diff --git a/src/main/java/com/ffii/core/web/view/document/AbstractExcelView.java b/src/main/java/com/ffii/core/web/view/document/AbstractExcelView.java new file mode 100644 index 0000000..70fd9c5 --- /dev/null +++ b/src/main/java/com/ffii/core/web/view/document/AbstractExcelView.java @@ -0,0 +1,82 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web.view.document; + +import java.io.IOException; +import java.util.Locale; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.apache.poi.ss.usermodel.Workbook; +import org.apache.poi.xssf.usermodel.XSSFWorkbook; +import org.springframework.core.io.Resource; +import org.springframework.core.io.support.LocalizedResourceHelper; +import org.springframework.web.servlet.support.RequestContextUtils; + +public abstract class AbstractExcelView extends org.springframework.web.servlet.view.document.AbstractXlsxView { + + private String url; + + /** + * Set the URL of the Excel Workbook source, without localization part nor .xlsx extension. + */ + public void setUrl(String url) { + this.url = url; + } + + /** + * Creates the Excel Workbook from an existing XLSX document. + * + * @param url + * the URL of the Excel template without localization part nor extension + * @param request + * current HTTP request + * @return the Workbook + * + * @throws IOException + * in case of failure + */ + private Workbook getTemplateSource(String url, HttpServletRequest request) throws IOException { + LocalizedResourceHelper helper = new LocalizedResourceHelper(getApplicationContext()); + Locale userLocale = RequestContextUtils.getLocale(request); + Resource inputFile = helper.findLocalizedResource(url, ".xlsx", userLocale); + + // Create the Excel Workbook from the source. + if (logger.isDebugEnabled()) { + logger.debug("Loading Excel workbook from " + inputFile); + } + return new XSSFWorkbook(inputFile.getInputStream()); + } + + /** + * This implementation creates an {@link XSSFWorkbook} for the XLSX format either from URL (if provided) or from scratch. + */ + @Override + protected Workbook createWorkbook(Map model, HttpServletRequest request) { + Workbook workbook; + + if (this.url != null) { + try { + workbook = getTemplateSource(this.url, request); + } catch (IOException e) { + logger.error("Failed to load Excel Workbook from URL!", e); + workbook = new XSSFWorkbook(); + } + } else { + workbook = new XSSFWorkbook(); + logger.debug("Created Excel Workbook from scratch"); + } + + return workbook; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/web/view/freemarker/FreeMarkerView.java b/src/main/java/com/ffii/core/web/view/freemarker/FreeMarkerView.java new file mode 100644 index 0000000..6a5a63f --- /dev/null +++ b/src/main/java/com/ffii/core/web/view/freemarker/FreeMarkerView.java @@ -0,0 +1,83 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web.view.freemarker; + +import java.io.IOException; +import java.util.Map; + +import javax.servlet.ServletResponse; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.security.web.csrf.CsrfToken; + +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.SecurityUtils; + +import freemarker.template.SimpleHash; +import freemarker.template.Template; +import freemarker.template.TemplateException; + + +/** + * FreeMarker view which extends Spring's {@link org.springframework.web.servlet.view.freemarker.FreeMarkerView}. + *

+ * Enforce response's character encoding using {@link ServletResponse#setCharacterEncoding(String)}. + *

+ * Expose {@link SettingsService} and {@link SecurityUtils} for use in FreeMarker template. + *

+ * Use with {@link FreeMarkerViewResolver}. + * + * @author Patrick + */ +public class FreeMarkerView extends org.springframework.web.servlet.view.freemarker.FreeMarkerView { + + private String responseEncoding; + + private SettingsService settingsService; + + /** SecurityUtils for use in FreeMarker template */ + private static final SecurityUtils SECURITY_UTILS = new SecurityUtils(); + + public String getResponseEncoding() { + return responseEncoding; + } + + public void setResponseEncoding(String responseEncoding) { + this.responseEncoding = responseEncoding; + } + + public SettingsService getSettingsService() { + return settingsService; + } + + public void setSettingsService(SettingsService settingsService) { + this.settingsService = settingsService; + } + + @Override + protected void processTemplate(Template template, SimpleHash model, HttpServletResponse response) throws IOException, TemplateException { + response.setCharacterEncoding(getResponseEncoding()); + super.processTemplate(template, model, response); + } + + @Override + protected void exposeHelpers(Map model, HttpServletRequest request) throws Exception { + CsrfToken csrf = (CsrfToken) request.getAttribute(CsrfToken.class.getName()); + if (csrf != null) + model.put("_csrf", csrf.getToken()); + else + model.put("_csrf", ""); + model.put("SecurityUtils", SECURITY_UTILS); + model.put("SettingsService", settingsService); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/core/web/view/freemarker/FreeMarkerViewResolver.java b/src/main/java/com/ffii/core/web/view/freemarker/FreeMarkerViewResolver.java new file mode 100644 index 0000000..c785a25 --- /dev/null +++ b/src/main/java/com/ffii/core/web/view/freemarker/FreeMarkerViewResolver.java @@ -0,0 +1,83 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web.view.freemarker; + + +import com.ffii.core.setting.service.SettingsService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.servlet.view.AbstractTemplateViewResolver; +import org.springframework.web.servlet.view.AbstractUrlBasedView; + +/** + * FreeMarker view resolver which extends Spring's {@link AbstractTemplateViewResolver}. + *

+ * Allows response's character encoding to be explicitly set (default to UTF-8 if not set), so that it is not necessary to set it together at the + * {@link #setContentType(String)} method. + *

+ * The default suffix is set to .ftl + * + * @see FreeMarkerView + * + * @author Patrick + */ +public class FreeMarkerViewResolver extends AbstractTemplateViewResolver { + + /** Default response's character encoding is UTF-8 */ + private static final String DEFAULT_RESPONSE_ENCODING = "UTF-8"; + + /** Default suffix for FreeMarker template is .ftl */ + private static final String DEFAULT_SUFFIX = ".ftl"; + + private String responseEncoding = DEFAULT_RESPONSE_ENCODING; + + @Autowired + private SettingsService settingsService; + + public String getResponseEncoding() { + return responseEncoding; + } + + public void setResponseEncoding(String responseEncoding) { + this.responseEncoding = responseEncoding; + } + + /** + * Default constructor + *

+ * 1. Sets default viewClass to {@link #requiredViewClass}.
+ * 2. Sets default suffix to {@link #DEFAULT_SUFFIX} + * + * @see #setViewClass + * @see #setSuffix + */ + public FreeMarkerViewResolver() { + setViewClass(requiredViewClass()); + setSuffix(DEFAULT_SUFFIX); + } + + /** + * Requires {@link FreeMarkerView}. + */ + @Override + protected Class requiredViewClass() { + return FreeMarkerView.class; + } + + @Override + protected AbstractUrlBasedView buildView(String viewName) throws Exception { + FreeMarkerView view = (FreeMarkerView) super.buildView(viewName); + view.setResponseEncoding(getResponseEncoding()); + view.setSettingsService(settingsService); + return view; + } + +} diff --git a/src/main/java/com/ffii/core/web/view/jasperreports/JasperReportsMultiFormatView.java b/src/main/java/com/ffii/core/web/view/jasperreports/JasperReportsMultiFormatView.java new file mode 100644 index 0000000..80cad1d --- /dev/null +++ b/src/main/java/com/ffii/core/web/view/jasperreports/JasperReportsMultiFormatView.java @@ -0,0 +1,39 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web.view.jasperreports; + +import java.util.HashMap; +import java.util.Map; + +import org.springframework.web.servlet.view.jasperreports.AbstractJasperReportsView; +import org.springframework.web.servlet.view.jasperreports.JasperReportsPdfView; + +/** + * + *

+ * The default mappings for the format lookup are: + * + *

+ *

    + *
  • {@code pdf} - {@code JasperReportsPdfView}
  • + *
  • {@code docx} - {@code JasperReportsDocxView}
  • + *
+ * + */ +public class JasperReportsMultiFormatView extends org.springframework.web.servlet.view.jasperreports.JasperReportsMultiFormatView { + + public JasperReportsMultiFormatView() { + Map> formatMappings = new HashMap>(1); + formatMappings.put("pdf", JasperReportsPdfView.class); + // formatMappings.put("docx", JasperReportsDocxView.class); + setFormatMappings(formatMappings); + } +} diff --git a/src/main/java/com/ffii/core/web/view/json/JsonView.java b/src/main/java/com/ffii/core/web/view/json/JsonView.java new file mode 100644 index 0000000..0fff2f1 --- /dev/null +++ b/src/main/java/com/ffii/core/web/view/json/JsonView.java @@ -0,0 +1,60 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.core.web.view.json; + +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.web.servlet.View; + +import com.ffii.core.utils.JsonUtils; +import com.ffii.core.utils.StringUtils; +import com.ffii.core.utils.web.ServletResponseUtils; +import com.ffii.core.web.view.AbstractView; + +/** + * {@link View} implementation to render the specified view data model as a JSON response. + * + * @see View + * @author Patrick + */ +public class JsonView extends AbstractView { + + /** + * Default view name of JsonView bean + */ + public static final String NAME = "jsonView"; + + @Override + protected void prepareResponse(HttpServletRequest request, HttpServletResponse response) { + // set response content type and encoding + if (StringUtils.contains(request.getHeader("Content-Type"), "multipart/form-data")) + response.setContentType(CONTENT_TYPE_TEXT_HTML); + else + response.setContentType(CONTENT_TYPE_JSON); + response.setCharacterEncoding(CHARSET_UTF8); + if (disableCaching) { + ServletResponseUtils.disableCaching(response); + } + } + + @Override + protected void renderMergedOutputModel(Map model, HttpServletRequest request, HttpServletResponse response) throws Exception { + // create json string from model + String jsonString = JsonUtils.toJsonString(model); + + // encode json string and write to stream + ServletResponseUtils.writeStringToStream(response, CHARSET_UTF8, jsonString); + } + +} diff --git a/src/main/java/com/ffii/tls/api/service/AuthenticationService.java b/src/main/java/com/ffii/tls/api/service/AuthenticationService.java new file mode 100644 index 0000000..25c9d9d --- /dev/null +++ b/src/main/java/com/ffii/tls/api/service/AuthenticationService.java @@ -0,0 +1,141 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.api.service; + +import java.security.SecureRandom; +import java.util.HashMap; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractService; + +import org.apache.commons.lang3.RandomStringUtils; +import org.jfree.util.Log; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * Authentication API Service + * + * @author Patrick + */ +@Service +public class AuthenticationService extends AbstractService { + + private static SecureRandom SECURE_RANDOM = new SecureRandom(); + + @Autowired + private JdbcDao jdbcDao; + + /** + * Generate random token + * + * @return 32 characters random String with letters and numbers + */ + private String generateToken() { + return RandomStringUtils.random(32, 0, 0, true, true, null, SECURE_RANDOM); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public String createAccessToken(int userId, String deviceId) { + + String sql = "INSERT INTO"; + sql += " access_token"; + sql += " (userId, deviceId, token, created)"; + sql += " VALUES"; + sql += " (:userId, :deviceId, :token, NOW())"; + sql += " ON DUPLICATE KEY"; + sql += " UPDATE"; + sql += " created = NOW(),"; + sql += " token = :token"; + + String token = generateToken(); + + Map args = MapUtils.toHashMap("userId", userId, "deviceId", deviceId, "token", token); + jdbcDao.executeUpdate(sql, args); + + return token; + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map findUserByAccessToken(String deviceId, String token) { + + String sql = "SELECT"; + sql += " u.id,"; + sql += " u.sysGroupId,"; + sql += " u.expired,"; + sql += " u.locked,"; + sql += " u.companyId,"; + sql += " u.username,"; + sql += " u.firstname,"; + sql += " u.lastname,"; + sql += " u.fullname"; + sql += " FROM access_token at"; + sql += " LEFT JOIN users u ON at.userId = u.id"; + sql += " WHERE u.deleted = 0"; + sql += " AND u.locked = 0"; + sql += " AND at.deviceId = :deviceId"; + sql += " AND at.token = :token"; + + Map args = MapUtils.toHashMap("deviceId", deviceId, "token", token); + Map data = jdbcDao.queryForMap(sql, args); + if (data == null){ + logger.info("userData : null, deviceId: "+deviceId+", token: "+token); + } + return data; + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map findUserAuth(Map args) { + + String sql = " SELECT * " + + " FROM users_authorities ua " + + " WHERE ua.userId = :userId " + + " AND ua.authority = :auth ; "; + + return jdbcDao.queryForMap(sql, args); + } + + public boolean haveAuth(Object userId, String... auths){ + boolean haveAuth = false; + + Map authMap = findUserAuth(MapUtils.toHashMap("userId", userId, "auth", "SUPERUSER")); + haveAuth = authMap != null && authMap.get("userId") == userId; + if(haveAuth) return haveAuth; + + for(String auth:auths){ + authMap = findUserAuth(MapUtils.toHashMap("userId", userId, "auth", auth)); + haveAuth = authMap != null && authMap.get("userId") == userId; + if(haveAuth) return haveAuth; + } + return haveAuth; + } + + public Map getNoUserFoundMap(){ + logger.info("NoUserFound"); + Map map = new HashMap<>(); + map.put(Params.AUTH, Boolean.FALSE); + map.put(Params.SUCCESS, Boolean.FALSE); + map.put(Params.MSG, "pleaseReLogin"); + return map; + } + + public Map getNoAuthFoundMap(){ + logger.info("NoAuth"); + Map map = new HashMap<>(); + map.put(Params.AUTH, Boolean.FALSE); + map.put(Params.SUCCESS, Boolean.FALSE); + return map; + } + +} diff --git a/src/main/java/com/ffii/tls/api/service/CustomerApiService.java b/src/main/java/com/ffii/tls/api/service/CustomerApiService.java new file mode 100644 index 0000000..0b5f945 --- /dev/null +++ b/src/main/java/com/ffii/tls/api/service/CustomerApiService.java @@ -0,0 +1,214 @@ +package com.ffii.tbms.api.service; + +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.customer.Customer; +import com.ffii.tbms.customer.dao.CustomerDao; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * OrderApiService + */ +@Service +public class CustomerApiService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private CustomerDao customerDao; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(Customer instance) { + return customerDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Customer find(Integer id) { + return customerDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchCustomerList(Map args) { + + StringBuilder sql = new StringBuilder( + " SELECT " + +" c.id," + +" c.surname, " + +" c.firstName, " + +" c.nameCh, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" c.phone1, " + +" c.phone2, " + +" c.companyPhone, " + +" c.companyEmail, " + +" c.companyAddress, " + +" c.email, " + +" c.address, " + +" c.remarks, " + +" c.tag " + +" " + +" FROM " + +" customer c " + + +" WHERE" + +" c.deleted = 0 "); + + if(args != null){ + if (args.containsKey("_searchStr")){ + sql.append(getCustomerNameSearch(args.get("searchStr").toString())); + /* + sql.append(" AND ( c.surname LIKE '"+args.get("_searchStr")+"' "); + sql.append(" OR c.firstName LIKE '"+args.get("_searchStr")+"' "); + sql.append(" OR c.nameCh LIKE '"+args.get("_searchStr")+"' "); + sql.append(" OR c.phone1 LIKE '"+args.get("_searchStr")+"' "); + sql.append(" OR c.phone2 LIKE '"+args.get("_searchStr")+"' ) "); + */ + } + + if (args.containsKey("sysGroupId")){ + sql.append(" AND c.sysGroupId = :sysGroupId "); + } + } + + sql.append(" ORDER BY ( 0 "); + + if (args != null) { + if (args.containsKey("searchStr")){ + sql.append(getCustomerNameOrderBy(args.get("searchStr").toString())); + /* + sql.append(" + IF( c.surname = :searchStr,1,0) + IF( c.surname LIKE '"+args.get("searchStr")+"%',1,0) "); + sql.append(" + IF( c.firstName = :searchStr,1,0) + IF( c.firstName LIKE '"+args.get("searchStr")+"%',1,0) "); + sql.append(" + IF( c.nameCh = :searchStr,1,0) + IF( c.nameCh LIKE '"+args.get("searchStr")+"%',1,0) "); + sql.append(" + IF( c.phone1 = :searchStr,1,0) + IF( c.phone1 LIKE '"+args.get("searchStr")+"%',1,0) "); + sql.append(" + IF( c.phone2 = :searchStr,1,0) + IF( c.phone2 LIKE '"+args.get("searchStr")+"%',1,0) "); + sql.append(" + IF( c.companyPhone = :searchStr,1,0) + IF( c.companyPhone LIKE '"+args.get("searchStr")+"%',1,0) "); + */ + } + } + sql.append(" ) DESC, "); + sql.append(" TRIM(c.firstName), TRIM(c.surname), TRIM(c.nameCh), c.id "); + + logger.info("search cust: "+sql); + + return jdbcDao.queryForList(sql.toString(), args); + } + + private String getCustomerNameSearch(String searchStr){ + String str = ""; + + String[] array = searchStr.split(" "); + for(int i = 0; i loadCustomer(Map args) { + + StringBuilder sql = new StringBuilder( + " SELECT " + +" c.id," + +" c.surname, " + +" c.firstName, " + +" c.nameCh, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName, " + +" c.phone1, " + +" c.phone2, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" c.companyPhone, " + +" c.companyEmail, " + +" c.companyAddress, " + +" c.email, " + +" c.address, " + +" c.remarks, " + +" c.tag, " + +" lastMeetingDate.date As lastMeetingDate, " + +" nextMeetingDate.date AS nextMeetingDate " + +" FROM " + +" customer c " + + +" LEFT JOIN " + +" ( SELECT Max(m.date) AS date, m.custId " + +" FROM meeting m " + +" WHERE m.deleted = 0 " + +" AND DATE(m.date) < DATE(current_date()) " + +" GROUP BY m.custId ) lastMeetingDate ON lastMeetingDate.custId = c.id " + + +" LEFT JOIN " + +" ( SELECT MIN(m.date) AS date, m.custId " + +" FROM meeting m " + +" WHERE m.deleted = 0 " + +" AND DATE(m.date) >= DATE(current_date()) " + +" GROUP BY m.custId ) nextMeetingDate ON nextMeetingDate.custId = c.id " + + +" WHERE" + +" c.deleted = 0 AND c.id = :custId "); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchForCombo(Map args) { + + StringBuilder sql = new StringBuilder(" SELECT " + +" c.id, " + +" c.phone1, " + +" c.phone2, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName " + +" FROM customer c WHERE deleted = 0 "); + + if (args.containsKey(Params.QUERY)) + sql.append(" AND ( concat_ws(' ', c.firstName ,c.surname, c.nameCh, c.phone1, c.phone2) LIKE :query " + +" OR concat_ws(' ', c.surname, c.firstName, c.nameCh, phone1, phone2) LIKE :query ) "); + + if (args.containsKey(Params.ID)) + sql.append(" AND c.id = :id"); + + if(args.containsKey("sysGroupId")){ + sql.append(" AND c.sysGroupId = :sysGroupId "); + } + + sql.append(" ORDER BY c.surname, c.firstName "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/api/service/MeetingApiService.java b/src/main/java/com/ffii/tls/api/service/MeetingApiService.java new file mode 100644 index 0000000..4026449 --- /dev/null +++ b/src/main/java/com/ffii/tls/api/service/MeetingApiService.java @@ -0,0 +1,108 @@ +package com.ffii.tbms.api.service; + +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * OrderApiService + */ +@Service +public class MeetingApiService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchMeeting(String dateStr) { + + StringBuilder sql = new StringBuilder("SELECT" + + " m.date AS meetingDate," + + " m.id AS meetingId," + + " m.type AS meetingType," + + " cu.id AS custId," + + " CONCAT(IF(cu.firstName IS NULL, '', CONCAT(cu.firstName, ' ')), " + + " IF(cu.surname IS NULL, '', CONCAT(cu.surname, ' ')), " + + " IF(cu.nameCh IS NULL, '', cu.nameCh)) AS customerName, " + + " m.orderId," + + " CONCAT(o.type, o.code) as orderCode," + + " m.type," + + " m.remarks" + + " FROM meeting m" + + " LEFT JOIN customer cu ON cu.id = m.custId" + + " LEFT JOIN orders o ON o.id = m.orderId" + + " WHERE m.deleted =0 "); + + if (dateStr != null) { + sql.append(" AND DATE(m.date) = :dateStr"); + } + + sql.append(" ORDER BY m.date ASC, m.id ASC "); + + return jdbcDao.queryForList(sql.toString(), MapUtils.toHashMap("dateStr", dateStr)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map loadMeeting(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " m.date AS meetingDate," + + " m.id AS meetingId," + + " m.type AS meetingType," + + " cu.id AS custId," + + " CONCAT(IF(cu.firstName IS NULL, '', CONCAT(cu.firstName, ' ')), " + + " IF(cu.surname IS NULL, '', CONCAT(cu.surname, ' ')), " + + " IF(cu.nameCh IS NULL, '', cu.nameCh)) AS customerName, " + + " m.orderId," + + " CONCAT(o.type, o.code) as orderCode," + + " m.type," + + " m.staffName," + + " m.remarks" + + " FROM meeting m" + + " LEFT JOIN customer cu ON cu.id = m.custId" + + " LEFT JOIN orders o ON o.id = m.orderId" + + " WHERE m.deleted =0 AND m.id = :id "); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchMeetingByDate(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " m.date AS meetingDate," + + " m.id AS meetingId," + + " m.type AS meetingType," + + " cu.id AS custId," + + " CONCAT(IF(cu.firstName IS NULL, '', CONCAT(cu.firstName, ' ')), " + + " IF(cu.surname IS NULL, '', CONCAT(cu.surname, ' ')), " + + " IF(cu.nameCh IS NULL, '', cu.nameCh)) AS customerName, " + + " m.orderId," + + " CONCAT(o.type, o.code) as orderCode," + + " m.type," + + " m.remarks" + + " FROM meeting m" + + " LEFT JOIN customer cu ON cu.id = m.custId" + + " LEFT JOIN orders o ON o.id = m.orderId" + + " WHERE m.deleted =0"); + + if (args.containsKey("selectedDate")) { + sql.append(" AND DATE(m.date) = :selectedDate"); + } + + sql.append(" ORDER BY m.date ASC, m.id ASC "); + + return jdbcDao.queryForList(sql.toString(), args); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/api/service/OrderApiService.java b/src/main/java/com/ffii/tls/api/service/OrderApiService.java new file mode 100644 index 0000000..06146da --- /dev/null +++ b/src/main/java/com/ffii/tls/api/service/OrderApiService.java @@ -0,0 +1,237 @@ +package com.ffii.tbms.api.service; + +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.order.Order; +import com.ffii.tbms.order.dao.OrderDao; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * OrderApiService + */ +@Service +public class OrderApiService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private OrderDao orderDao; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(final Order instance) { + return orderDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Order find(final Integer id) { + return orderDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + StringBuilder sql = new StringBuilder(" SELECT " + + " orders.id," + + " orders.date," + + " orders.type," + + " orders.code," + + " orders.targetCompleteDate," + + " orders.status," + + " orders.remarks," + + " _p.paymentAmount, " + + " _oi.orderAmount, " + + " CONCAT(IF(cu.firstName IS NULL, '', CONCAT(cu.firstName, ' '))," + + " IF(cu.surname IS NULL, '', CONCAT(cu.surname, ' '))," + + " IF(cu.nameCh IS NULL, '', cu.nameCh)) AS customerName " + + " FROM orders" + + " LEFT JOIN customer cu ON cu.id = orders.custId" + +" LEFT JOIN (SELECT oi.orderId, SUM(oi.price) AS orderAmount, " + +" GROUP_CONCAT(oi.name SEPARATOR ' ') AS itemName " + +" FROM order_item oi WHERE oi.deleted = 0 " + +" GROUP BY oi.orderId) _oi ON _oi.orderId = orders.id " + +" LEFT JOIN ( " + +" SELECT " + +" SUM(p.amount) AS paymentAmount, " + +" p.orderId " + +" FROM payment p " + +" WHERE p.deleted = 0 " + +" GROUP BY p.orderId) _p ON _p.orderId = orders.id " + + + " WHERE orders.deleted = 0 "); + + if (args != null) { + if (args.containsKey("searchStr")) { + sql.append( + " AND (CONCAT(IFNULL(cu.firstName, ''), " + + " IFNULL(cu.surname, ''), " + + " IFNULL(cu.nameCh,''), " + + " IFNULL(orders.type, ''), " + + " IFNULL(orders.code, '') " + // +", " + // +" IFNULL(oi.name, '')" + + ")) LIKE :searchStr"); + } + if(args.containsKey("custId")){ + sql.append(" AND orders.custId = :custId "); + } + if(args.containsKey("sysGroupId")){ + sql.append(" AND orders.sysGroupId = :sysGroupId "); + } + } + sql.append(" GROUP BY orders.id"); + sql.append(" ORDER BY orders.date DESC"); + + if (args != null) { + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map loadOrder(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " concat(orders.type,orders.code) AS orderNo," + + " orders.id," + + " orders.type," + + " orders.code," + + " orders.custId," + + " orders.remarks," + + " orders.status," + + " orders.date," + + " orders.ref," + + " orders.refNo," + + " orders.targetCompleteDate," + + " CONCAT(IF(cu.firstName IS NULL, '', CONCAT(cu.firstName, ' '))," + + " IF(cu.surname IS NULL, '', CONCAT(cu.surname, ' '))," + + " IF(cu.nameCh IS NULL, '', cu.nameCh)) AS customerName," + + " orders.date AS orderDate" + + " FROM" + + " orders " + + " LEFT JOIN customer cu ON orders.custId = cu.id " + + " WHERE orders.deleted = 0 AND orders.id =:id"); + + if(args.containsKey("sysGroupId")){ + sql.append(" AND orders.sysGroupId = :sysGroupId "); + } + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchItems(Map args) { + + StringBuilder sql = new StringBuilder(" SELECT" + + " oi.id," + + " oi.orderId," + + " oi.name," + + " oi.price" + + " FROM order_item oi" + + " WHERE oi.deleted = 0"); + + if (args != null) { + if (args.containsKey(Params.ID)) sql.append(" AND oi.orderId = :id"); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + //todo: remove start + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchDetail(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " concat(orders.type,orders.code) AS orderNo," + + " orders.refNo," + + " CONCAT(IF(cu.firstName IS NULL, '', CONCAT(cu.firstName, ' '))," + + " IF(cu.surname IS NULL, '', CONCAT(cu.surname, ' '))," + + " IF(cu.nameCh IS NULL, '', cu.nameCh)) AS customerName," + + " orders.targetCompleteDate," + + " orders.date AS orderDate" + + " FROM" + + " orders " + + " LEFT JOIN customer cu ON orders.custId = cu.id " + + " WHERE orders.deleted = 0"); + if (args != null) { + if (args.containsKey(Params.ID)) sql.append(" AND orders.id =:id"); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> comboSearch(Map args) { + + StringBuilder sql = new StringBuilder(" SELECT " + + " orders.id," + + " orders.type," + + " orders.code," + + " CONCAT(IF(cu.firstName IS NULL, '', CONCAT(cu.firstName, ' '))," + + " IF(cu.surname IS NULL, '', CONCAT(cu.surname, ' '))," + + " IF(cu.nameCh IS NULL, '', cu.nameCh)) AS customerName " + + " FROM orders" + + " LEFT JOIN customer cu ON cu.id = orders.custId" + + " WHERE orders.deleted = 0 "); + + if (args != null) { + if (args.containsKey("searchStr")) { + sql.append( + " AND( " + +" (CONCAT(IFNULL(cu.firstName, ''), " + + " IFNULL(cu.surname, ''), " + + " IFNULL(cu.nameCh,''), " + + " IFNULL(orders.type, ''), " + + " IFNULL(orders.code, '') " + + ")) LIKE :searchStr " + +" OR " + +" (CONCAT(IFNULL(cu.surname, ''), " + + " IFNULL(cu.firstName, ''), " + + " IFNULL(cu.nameCh,''), " + + " IFNULL(orders.type, ''), " + + " IFNULL(orders.code, '') " + + ")) LIKE :searchStr " + +" )"); + } + if(args.containsKey("orderId")){ + sql.append(" AND orders.id = :orderId "); + } + if(args.containsKey("customerId")){ + sql.append(" AND orders.custId = :customerId "); + } + } + sql.append(" GROUP BY orders.id"); + sql.append(" ORDER BY orders.date DESC"); + + if (args != null) { + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> comboSearch(Integer customerId) { + + StringBuilder sql = new StringBuilder("SELECT id, code FROM orders WHERE orders.deleted =0"); + + if (customerId != -1) { + sql.append(" AND orders.custId = :customerId"); + } + return jdbcDao.queryForList(sql.toString(), MapUtils.toHashMap("customerId", customerId)); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/api/web/AuthenticationController.java b/src/main/java/com/ffii/tls/api/web/AuthenticationController.java new file mode 100644 index 0000000..ead77a2 --- /dev/null +++ b/src/main/java/com/ffii/tls/api/web/AuthenticationController.java @@ -0,0 +1,77 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.api.web; + +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.api.service.AuthenticationService; +import com.ffii.tbms.user.service.UserService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.security.crypto.password.StandardPasswordEncoder; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +/** + * Authentication API Controller + * + * @author Patrick + */ +@Controller +@RequestMapping(value = "/api") +public class AuthenticationController extends AbstractController { + + private static final StandardPasswordEncoder PASSWORD_ENCODER = new StandardPasswordEncoder(); + + @Autowired + private AuthenticationService authenticationService; + + @Autowired + private UserService userService; + + @RequestMapping(value = "/auth", method = { RequestMethod.GET, RequestMethod.POST }) + public String auth(Model model, @RequestParam String deviceId, @RequestParam String username, + @RequestParam String password, HttpServletRequest request) throws Exception { + + Map data = userService.findUserMap(MapUtils.toHashMap("username", username)); + + if (data != null) { + String encodedPassword = (String) data.get("password"); + + boolean matches = PASSWORD_ENCODER.matches(password, encodedPassword); + + // if password matches + if (matches) { + int userId = NumberUtils.intValue(data.get("id")); + String token = authenticationService.createAccessToken(userId, deviceId); + model.addAttribute("token", token); + model.addAttribute("id", data.get("id")); + model.addAttribute("firstname", data.get("firstname")); + model.addAttribute("lastname", data.get("lastname")); + model.addAttribute("fullname", data.get("fullname")); + } + model.addAttribute(Params.SUCCESS, matches); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/api/web/CustomerApiController.java b/src/main/java/com/ffii/tls/api/web/CustomerApiController.java new file mode 100644 index 0000000..a8556ba --- /dev/null +++ b/src/main/java/com/ffii/tls/api/web/CustomerApiController.java @@ -0,0 +1,203 @@ +package com.ffii.tbms.api.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import javax.servlet.http.HttpServletRequest; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.api.service.AuthenticationService; +import com.ffii.tbms.api.service.CustomerApiService; +import com.ffii.tbms.api.service.OrderApiService; +import com.ffii.tbms.customer.Customer; +import com.ffii.tbms.customer.service.CustomerService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +@Controller +@RequestMapping(value = "api/customer/") +/** + * OrderApiController + */ +public class CustomerApiController extends AbstractController { + + @Autowired + AuthenticationService authenticationService; + + @Autowired + CustomerApiService service; + + @Autowired + OrderApiService orderApiService; + + + @RequestMapping(value = "save", method = { RequestMethod.GET, RequestMethod.POST }) + public String saveCustomer(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id) { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth(userData.get("id"),"CUSTOMER_MAINTAIN"); + if (!haveAuth) { + model.addAllAttributes(authenticationService.getNoAuthFoundMap()); + return JsonView.NAME; + } + + Customer instance; + if (id > 0) { + instance = service.find(id); + logger.info("meeting found"); + } else { + instance = new Customer(); + instance.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + } + + ServletRequestUtils.doBind(request, instance, null); + id = service.saveOrUpdate(instance); + + logger.info("Meeting Save: "+request.getParameter("date")); + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + + return JsonView.NAME; + } + + @RequestMapping(value = "list", method = { RequestMethod.GET, RequestMethod.POST }) + public String listCustomer(Model model, @RequestParam String deviceId, @RequestParam String token, + HttpServletRequest request) throws Exception { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth(userData.get("id"),"CUSTOMER_MAINTAIN"); + if (!haveAuth) { + model.addAllAttributes(authenticationService.getNoAuthFoundMap()); + return JsonView.NAME; + } + + final Map args = new HashMap(); + args.put("sysGroupId", userData.get("sysGroupId")); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, "searchStr"); + + if(args.containsKey("searchStr") && args.get("searchStr").toString().length()>=2){ + args.put("_searchStr", args.get("searchStr")); + CriteriaUtils.addString(request, args, "searchStr"); + }else{ + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + model.addAttribute(Params.RECORDS, null); + return JsonView.NAME; + } + + logger.info("list: args: " + args); + final List> records = service.searchCustomerList(args); + logger.info("list: records: " + records); + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + + @RequestMapping(value = "load", method = { RequestMethod.GET, RequestMethod.POST }) + public String loadCustomer(Model model, @RequestParam String deviceId, @RequestParam String token, + HttpServletRequest request) throws Exception { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth(userData.get("id"),"CUSTOMER_MAINTAIN"); + if (!haveAuth) { + model.addAllAttributes(authenticationService.getNoAuthFoundMap()); + return JsonView.NAME; + } + + final Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addInteger(request, args, "custId"); + + logger.info("load: args: " + args); + + Map data = service.loadCustomer(args); + logger.info("load: data: " + data); + + List> orderList = orderApiService.search(args); + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + model.addAttribute(Params.DATA, data); + model.addAttribute("orderList", orderList); + + return JsonView.NAME; + } + + + @RequestMapping(value = "combo.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String getCustomerComboJson(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request) throws Exception { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, Params.QUERY); + CriteriaUtils.addInteger(request, args, "deptId"); + args.put("sysGroupId", userData.get("sysGroupId")); + + if(args.containsKey("query") && args.get("query").toString().length()>=2){ + args.put("_query", args.get("query")); + CriteriaUtils.addStringLike(request, args, "query"); + List> records = service.searchForCombo(args); + model.addAttribute(Params.RECORDS, records); + }else if(args.containsKey("id")){ + List> records = service.searchForCombo(args); + if(records != null && records.size()>0) + model.addAttribute(Params.DATA, records.get(0)); + else + model.addAttribute(Params.DATA, null); + }else{ + List> records = service.searchForCombo(args); + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + model.addAttribute(Params.RECORDS, records); + return JsonView.NAME; + } + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/api/web/FileApiController.java b/src/main/java/com/ffii/tls/api/web/FileApiController.java new file mode 100644 index 0000000..b7b175e --- /dev/null +++ b/src/main/java/com/ffii/tls/api/web/FileApiController.java @@ -0,0 +1,437 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.api.web; + +import java.awt.image.BufferedImage; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.imageio.ImageIO; +import javax.servlet.ServletOutputStream; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import com.fasterxml.jackson.databind.ObjectMapper; +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.FileUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.StringUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.AbstractView; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.api.service.AuthenticationService; +import com.ffii.tbms.api.service.OrderApiService; +import com.ffii.tbms.file.File; +import com.ffii.tbms.file.FileBlob; +import com.ffii.tbms.file.FileRef; +import com.ffii.tbms.file.FileRefType; +import com.ffii.tbms.file.service.FileService; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.log.service.AuditLogService; +import com.ffii.tbms.order.Order; +import com.ffii.tbms.order.service.OrderService; + +import org.apache.commons.lang3.RandomStringUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.multipart.MultipartFile; + +@Controller +@RequestMapping(value = "/api/file") +public class FileApiController extends AbstractController { + + @Autowired + private AuthenticationService authenticationService; + + @Autowired + OrderApiService orderApiService; + + @Autowired + private FileService fileService; + + @Autowired + private SettingsService settingsService; + + @Autowired + private AuditLogService auditLogService; + + private static final long MAX_FILE_UPLOAD_SIZE = 25 * 1024 * 1024; // 25 MB + + private static final boolean OVERWRITE_SAME_FILENAME = false; + + private static final int DEFAULT_UPLOAD_MAX_FILE_SIZE_MB = 50; + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, @RequestParam String deviceId, @RequestParam String token, + @RequestParam String refType, @RequestParam Integer refId) { + + Map data = authenticationService.findUserByAccessToken(deviceId, token); + if (data == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + Map args = new HashMap(); + args.put(Params.REF_TYPE, refType); + args.put(Params.REF_ID, refId); + + List> records = fileService.searchFiles(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "/measurement-sheet/ul", method = RequestMethod.POST) + public String uploadMeasurementSheetFile(HttpServletRequest request, Model model, @RequestParam String deviceId, @RequestParam String token, + @RequestParam int orderId, @RequestParam MultipartFile multipartFile) throws Exception { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + logger.info("upload file start"); + Order order = orderApiService.find(orderId); + String refType = FileRefType.MEASUREMENT_SHEET; + String refCode = order.getCustId() + ""; + Integer refId = orderId; + + // get file upload max file size setting + int uploadMaxFileSize = settingsService.getInt("FILE.upload.maxFileSize", DEFAULT_UPLOAD_MAX_FILE_SIZE_MB) * 1024 * 1024; + + Boolean success = Boolean.TRUE; + + // only proceed if multipartFile is not null, and has file size + if (multipartFile != null && multipartFile.getSize() > 0 && multipartFile.getSize() <= uploadMaxFileSize) { + + // DEBUG LOG + logger.info("multipartFile.getSize() = " + multipartFile.getSize()); + + File file = new File(); + file.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + file.setFilename(multipartFile.getOriginalFilename()); + // file.setMimetype(multipartFile.getContentType()); + file.setMimetype(FileUtils.guessMimetype(file.getFilename())); + file.setFilesize(multipartFile.getSize()); + file.setDescription(ServletRequestUtils.getTrimmedStringParameter(request, "description")); + + FileBlob fileBlob = new FileBlob(); + fileBlob.setBytes(multipartFile.getBytes()); + fileBlob.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + + FileRef fileRef = new FileRef(); + fileRef.setRefId(refId); + fileRef.setRefType(refType); + fileRef.setRefCode(refCode); + fileRef.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + + // get height and width if mimetype is png or jpeg + if (AbstractView.CONTENT_TYPE_PNG.equals(file.getMimetype()) || AbstractView.CONTENT_TYPE_JPEG.equals(file.getMimetype())) { + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + if (image != null) { + file.setImageHeight(image.getHeight()); + file.setImageWidth(image.getWidth()); + } + } + + if (OVERWRITE_SAME_FILENAME) { + // search for existing file(s) with the same refType, refId, and filename + List> existingFiles = fileService.searchFiles( + MapUtils.toHashMap("refType", refType, "refId", refId, "filename", file.getFilename())); + + // delete them if found + for (Map existingFile : existingFiles) { + fileService.deleteFile((Integer) existingFile.get("id"), (Integer) existingFile.get("refId"), + (String) existingFile.get("refType"), (String) existingFile.get("skey")); + } + } + + // create UserFile + file.setSkey(RandomStringUtils.randomAlphanumeric(16)); + fileService.saveFile(file); + + // create UserFileBlob + fileBlob.setFileId(file.getId()); + fileService.saveFileBlob(fileBlob); + + // create UserFileRef + fileRef.setFileId(file.getId()); + fileService.saveFileRef(fileRef); + + order.setFileId(file.getId()); + orderApiService.saveOrUpdate(order); + } else { + success = Boolean.FALSE; + + // if not success, return msg to client + model.addAttribute(Params.MSG, getMessageSourceAccessor().getMessage("Upload Failed")); + } + + model.addAttribute(Params.SUCCESS, success); + + return JsonView.NAME; + } + + @RequestMapping(value = "/ul", method = RequestMethod.POST) + public String uploadFile(HttpServletRequest request, Model model, @RequestParam String deviceId, + @RequestParam String token, @RequestParam int refId, @RequestParam String refType, + @RequestParam(defaultValue = StringUtils.EMPTY) String refCode, @RequestParam MultipartFile multipartFile) + throws IOException { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + // only proceed if multipartFile is not null, and has file size + if(multipartFile == null || multipartFile.getSize() <= 0 || multipartFile.getSize() > MAX_FILE_UPLOAD_SIZE){ + model.addAttribute(Params.MSG, getMessageSourceAccessor().getMessage("FILE.msg.uploadFailed")); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + + // DEBUG LOG + logger.info("multipartFile.getSize() = " + multipartFile.getSize()); + + File file = new File(); + file.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + file.setFilename(multipartFile.getOriginalFilename()); + // file.setMimetype(multipartFile.getContentType()); + file.setMimetype(FileUtils.guessMimetype(file.getFilename())); + file.setFilesize(multipartFile.getSize()); + + FileBlob fileBlob = new FileBlob(); + fileBlob.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + fileBlob.setBytes(multipartFile.getBytes()); + + FileRef fileRef = new FileRef(); + fileRef.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + fileRef.setRefId(refId); + fileRef.setRefType(refType); + fileRef.setRefCode(refCode); + + // get height and width if mimetype is png or jpeg + if (AbstractView.CONTENT_TYPE_PNG.equals(file.getMimetype()) + || AbstractView.CONTENT_TYPE_JPEG.equals(file.getMimetype())) { + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + if (image != null) { + file.setImageHeight(image.getHeight()); + file.setImageWidth(image.getWidth()); + } + } + + // search for existing file(s) with the same refType, refId, and filename + List> existingFiles = fileService.searchFiles( + MapUtils.toHashMap("refType", refType, "refId", refId, "filename", file.getFilename())); + + // delete them if found + for (Map existingFile : existingFiles) { + fileService.deleteFile((Integer) existingFile.get("id"), (Integer) existingFile.get("refId"), + (String) existingFile.get("refType"), (String) existingFile.get("skey")); + } + + // create UserFile + file.setSkey(RandomStringUtils.randomAlphanumeric(16)); + fileService.saveFile(file); + + // create UserFileBlob + fileBlob.setFileId(file.getId()); + fileService.saveFileBlob(fileBlob); + + // create UserFileRef + fileRef.setFileId(file.getId()); + fileService.saveFileRef(fileRef); + + Map map = new HashMap<>(); + map.put("skey", file.getSkey()); + map.put("fileId", file.getId()); + map.put("filename", file.getFilename()); + map.put("filesize", file.getFilesize()); + map.put("refType", fileRef.getRefType()); + map.put("refId", fileRef.getRefId()); + map.put("mimetype", file.getMimetype()); + + model.addAttribute(Params.DATA, map); + + if(refType.equals(FileRefType.ORDER)){ + ObjectMapper mapper = new ObjectMapper(); + auditLogService.save("orders", + refId, + NumberUtils.intValue(userData.get("id")), + new Date(), + LogUtils.ACTION_CREATE, + mapper.writeValueAsString(MapUtils.toHashMap("photoFileId", file.getId(), "filename",file.getFilename()))); + } + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "/dl/{id}/{skey}/{filename}", method = RequestMethod.GET) + public void download(HttpServletResponse response, Model model, @RequestParam(defaultValue = "false") boolean dl, + @PathVariable int id, @PathVariable String skey) throws IOException { + + File file = fileService.findFileByIdAndKey(id, skey); + + if (file != null) { + FileBlob fileBlob = fileService.findFileBlobByFileId(id); + + response.reset(); + response.setContentType(file.getMimetype()); + response.setContentLength((int) file.getFilesize()); + response.setHeader("Content-Transfer-Encoding", "binary"); + response.setHeader("Content-Disposition", String.format("%s; filename=\"%s\"", dl ? "attachment" : "inline", + response.encodeURL(file.getFilename()))); + + ServletOutputStream out = response.getOutputStream(); + + try { + out.write(fileBlob.getBytes()); + out.flush(); + out.close(); + } catch (IOException e) { + logger.warn(e.getMessage()); + } finally { + out.close(); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } + } else { + logger.info("*** 400 BAD REQUEST ***"); + response.setStatus(HttpServletResponse.SC_BAD_REQUEST); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + } + + @RequestMapping(value = "/delete", method = RequestMethod.POST) + public String delete(HttpServletResponse response, Model model, @RequestParam String deviceId, + @RequestParam String token, @RequestParam Integer fileId, @RequestParam Integer refId, + @RequestParam String refType, @RequestParam String skey) throws IOException { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + fileService.deleteFile(fileId, refId, refType, skey); + + if(refType.equals(FileRefType.MEASUREMENT_SHEET)){ + ObjectMapper mapper = new ObjectMapper(); + auditLogService.save("orders", + refId, + NumberUtils.intValue(userData.get("id")), + new Date(), + LogUtils.ACTION_DELETE, + mapper.writeValueAsString(MapUtils.toHashMap("fileId", fileId))); + }else if(refType.equals(FileRefType.ORDER)){ + ObjectMapper mapper = new ObjectMapper(); + auditLogService.save("orders", + refId, + NumberUtils.intValue(userData.get("id")), + new Date(), + LogUtils.ACTION_DELETE, + mapper.writeValueAsString(MapUtils.toHashMap("photoFileId", fileId))); + } + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "/thumbnail/{id}/{skey}/{filename}", method = RequestMethod.GET) + public void thumbnail(HttpServletResponse response, Model model, @RequestParam(defaultValue = "false") boolean dl, + @PathVariable int id, @PathVariable String skey) throws IOException { + + File file = fileService.findFileByIdAndKey(id, skey); + + if (file != null) { + FileBlob fileBlob = fileService.findFileBlobByFileId(id); + + response.reset(); + response.setContentType(file.getMimetype()); + // response.setContentLength((int) file.getFilesize()); + response.setHeader("Content-Transfer-Encoding", "binary"); + response.setHeader("Content-Disposition", String.format("%s; filename=\"%s\"", dl ? "attachment" : "inline", + response.encodeURL(file.getFilename()))); + + int limit = 500; + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + int width = image.getWidth(); + int height = image.getHeight(); + if (width > height) { + if (width > limit) { + height = height * limit / width; + width = limit; + } + } else { + if (height > limit) { + width = width * limit / height; + height = limit; + } + } + image = scale(image, width, height); + ByteArrayOutputStream tmp = new ByteArrayOutputStream(); + ImageIO.write(image, "jpg", tmp); + tmp.close(); + response.setContentLength((int) tmp.size()); + + ServletOutputStream out = response.getOutputStream(); + + try { + out.write(tmp.toByteArray()); + out.flush(); + out.close(); + } catch (IOException e) { + logger.warn(e.getMessage()); + } finally { + out.close(); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } + } else { + logger.info("*** 400 BAD REQUEST ***"); + response.setStatus(HttpServletResponse.SC_BAD_REQUEST); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + } + + static BufferedImage scale(BufferedImage originalImage, int w, int h) { + BufferedImage img = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB); + int x, y; + int ww = originalImage.getWidth(); + int hh = originalImage.getHeight(); + for (x = 0; x < w; x++) { + for (y = 0; y < h; y++) { + int col = originalImage.getRGB(x * ww / w, y * hh / h); + img.setRGB(x, y, col); + } + } + return img; + } + + +} diff --git a/src/main/java/com/ffii/tls/api/web/MainApiController.java b/src/main/java/com/ffii/tls/api/web/MainApiController.java new file mode 100644 index 0000000..87b00a9 --- /dev/null +++ b/src/main/java/com/ffii/tls/api/web/MainApiController.java @@ -0,0 +1,75 @@ +package com.ffii.tbms.api.web; + +import java.io.IOException; +import java.util.Map; +import javax.servlet.ServletOutputStream; +import javax.servlet.http.HttpServletResponse; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractController; +import com.ffii.tbms.api.service.AuthenticationService; +import com.ffii.tbms.file.File; +import com.ffii.tbms.file.FileBlob; +import com.ffii.tbms.file.service.FileService; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +@Controller +@RequestMapping(value = "api/") + +public class MainApiController extends AbstractController { + + @Autowired + AuthenticationService authenticationService; + + @Autowired + private FileService fileService; + + + @RequestMapping(value = "/dl/{id}/{skey}/{filename}", method = { RequestMethod.GET, RequestMethod.POST }) + public void download(HttpServletResponse response, @RequestParam String deviceId, @RequestParam String token, Model model, + @RequestParam(defaultValue = "false") boolean dl, + @PathVariable int id, @PathVariable String skey) throws IOException { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return; + } + + File file = fileService.findFileByIdAndKey(id, skey); + + if (file != null) { + FileBlob fileBlob = fileService.findFileBlobByFileId(id); + + response.reset(); + response.setContentType(file.getMimetype()); + response.setContentLength((int) file.getFilesize()); + response.setHeader("Content-Transfer-Encoding", "binary"); + response.setHeader("Content-Disposition", String.format("%s; filename=\"%s\"", dl ? "attachment" : "inline", + response.encodeURL(file.getFilename()))); + + ServletOutputStream out = response.getOutputStream(); + + try { + out.write(fileBlob.getBytes()); + out.flush(); + out.close(); + } catch (IOException e) { + logger.warn(e.getMessage()); + } finally { + out.close(); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } + } else { + logger.info("*** 400 BAD REQUEST ***"); + response.setStatus(HttpServletResponse.SC_BAD_REQUEST); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/api/web/MeetingApiController.java b/src/main/java/com/ffii/tls/api/web/MeetingApiController.java new file mode 100644 index 0000000..b76debe --- /dev/null +++ b/src/main/java/com/ffii/tls/api/web/MeetingApiController.java @@ -0,0 +1,247 @@ +package com.ffii.tbms.api.web; + +import java.text.DateFormat; +import java.text.SimpleDateFormat; +import java.util.ArrayList; +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.DateUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.api.service.AuthenticationService; +import com.ffii.tbms.api.service.MeetingApiService; +import com.ffii.tbms.meeting.Meeting; +import com.ffii.tbms.meeting.service.MeetingService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +@Controller +@RequestMapping(value = "api/meeting/") +/** + * OrderApiController + */ +public class MeetingApiController extends AbstractController { + + @Autowired + MeetingApiService service; + + @Autowired + AuthenticationService authenticationService; + + @Autowired + private MeetingService meetingService; + + + @RequestMapping(value = "list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String getMeetingJson(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request) throws ServletRequestBindingException { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAttribute(Params.AUTH, Boolean.FALSE); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + + /* + Calendar formMonthCalendar = Calendar.getInstance(); + formMonthCalendar.setTime(DateUtils.truncate(new Date(), Calendar.DAY_OF_MONTH)); + formMonthCalendar.set(Calendar.DAY_OF_MONTH, 1); + formMonthCalendar.set(Calendar.MONTH, fromMonth); + formMonthCalendar.set(Calendar.YEAR, year); + + Calendar toMonthCalendar = Calendar.getInstance(); + toMonthCalendar.setTime(DateUtils.truncate(new Date(), Calendar.DAY_OF_MONTH)); + toMonthCalendar.set(Calendar.DAY_OF_MONTH, 1); + toMonthCalendar.set(Calendar.MONTH, toMonth); + toMonthCalendar.set(Calendar.YEAR, year); + */ + + Map args = new HashMap(); + CriteriaUtils.addDate(request, args, "fromDate"); + CriteriaUtils.addDate(request, args, "toDate"); + + //toDo remove + CriteriaUtils.addInteger(request, args, "fromMonth"); + CriteriaUtils.addInteger(request, args, "toMonth"); + CriteriaUtils.addInteger(request, args, "year"); + + Date firstDateOfMonth=null, lastDateOfMonth=null; + + logger.info("args:"+args); + + if(args.containsKey("fromDate") && args.containsKey("toDate")){ + firstDateOfMonth = (Date)args.get("fromDate"); + lastDateOfMonth = (Date)args.get("toDate"); + }else if(args.containsKey("fromMonth") && args.containsKey("toMonth") && args.containsKey("year")){ + logger.info("fromMonth:"+args.get("fromMonth")+", toMonth:"+args.get("toMonth")+", year:"+args.get("year")); + logger.info("year:"+Integer.parseInt(args.get("year").toString())); + logger.info("fromMonth:"+Integer.parseInt(args.get("fromMonth").toString())); + firstDateOfMonth = DateUtils.getFirstDateOfMonthByYearAndMonth(Integer.parseInt(args.get("year").toString()), Integer.parseInt(args.get("fromMonth").toString())); + lastDateOfMonth = DateUtils.getLastDateOfMonthByYearAndMonth(Integer.parseInt(args.get("year").toString()), Integer.parseInt(args.get("toMonth").toString())); + }else{ + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.DATA, new HashMap<>()); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + //todo remove + model.addAttribute(Params.RECORDS, new ArrayList<>()); + + return JsonView.NAME; + } + + logger.info(firstDateOfMonth.getTime()); + logger.info(lastDateOfMonth.getTime()); + + List> records = new ArrayList<>(); + Map dayMap = new HashMap<>(); + while (DateUtils.isEarlierThan(firstDateOfMonth, lastDateOfMonth)) { + DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd"); + String dateStr = dateFormat.format(firstDateOfMonth); + List> events = service.searchMeeting(dateStr); + dayMap.put(dateStr, events); + firstDateOfMonth = DateUtils.addDays(firstDateOfMonth, 1); + } + + DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd"); + String dateStr = dateFormat.format(lastDateOfMonth); + List> events = service.searchMeeting(dateStr); + dayMap.put(dateStr, events); + + records.add(dayMap); + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.DATA, dayMap); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + //todo remove + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + @RequestMapping(value = "selected-list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String getMeetingSelectedJson(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, + @RequestParam Date selectedDate) throws ServletRequestBindingException { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAttribute(Params.AUTH, Boolean.FALSE); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + + Map args = new HashMap<>(); + CriteriaUtils.addDate(request, args, "selectedDate"); + + List> searchMeetingByDate = service.searchMeetingByDate(args); + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.RECORDS, searchMeetingByDate); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "load", method = { RequestMethod.GET, RequestMethod.POST }) + public String loadMeeting(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, + @RequestParam int id) throws ServletRequestBindingException { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAttribute(Params.AUTH, Boolean.FALSE); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + + Map args = new HashMap<>(); + args.put("id", id); + + Map data = service.loadMeeting(args); + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "save", method = { RequestMethod.GET, RequestMethod.POST }) + public String saveMeeting(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id) { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAttribute(Params.AUTH, Boolean.FALSE); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth( userData.get("id"), "MEETING_MAINTAIN"); + if (!haveAuth) { + model.addAttribute(Params.AUTH, Boolean.FALSE); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + + Meeting instance; + if (id > 0) { + instance = meetingService.find(id); + logger.info("meeting found"); + } else { + instance = new Meeting(); + instance.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + } + + ServletRequestUtils.doBind(request, instance, null); + id = meetingService.saveOrUpdate(instance); + + logger.info("Meeting Save: "+request.getParameter("date")); + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "delete", method = { RequestMethod.GET, RequestMethod.POST }) + public String deleteMeeting(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, + @RequestParam Integer id) { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAttribute(Params.AUTH, Boolean.FALSE); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth( userData.get("id"), "MEETING_MAINTAIN"); + if (!haveAuth) { + model.addAttribute(Params.AUTH, Boolean.FALSE); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + + Meeting instance = meetingService.find(id); + instance.setDeleted(true); + meetingService.saveOrUpdate(instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/api/web/OrderApiController.java b/src/main/java/com/ffii/tls/api/web/OrderApiController.java new file mode 100644 index 0000000..0f72b64 --- /dev/null +++ b/src/main/java/com/ffii/tls/api/web/OrderApiController.java @@ -0,0 +1,386 @@ +package com.ffii.tbms.api.web; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import com.fasterxml.jackson.core.JsonProcessingException; +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.api.service.AuthenticationService; +import com.ffii.tbms.api.service.CustomerApiService; +import com.ffii.tbms.api.service.OrderApiService; +import com.ffii.tbms.customer.service.CustomerService; +import com.ffii.tbms.file.FileRefType; +import com.ffii.tbms.file.service.FileService; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.order.Order; +import com.ffii.tbms.order.OrderItem; +import com.ffii.tbms.order.service.OrderItemService; +import com.ffii.tbms.order.service.OrderService; + +import org.apache.commons.lang3.SerializationUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +@Controller +@RequestMapping(value = "api/order/") +/** + * OrderApiController + */ +public class OrderApiController extends AbstractController { + + @Autowired + AuthenticationService authenticationService; + + @Autowired + OrderApiService service; + + @Autowired + OrderItemService orderItemService; + + @Autowired + CustomerApiService customerApiService; + + @Autowired + private FileService fileService; + + @RequestMapping(value = "save", method = { RequestMethod.GET, RequestMethod.POST }) + public String saveOrder(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id) { + + logger.info("saveOrder : "+id); + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth(userData.get("id"),"ORDER_MAINTAIN"); + if (!haveAuth) { + model.addAllAttributes(authenticationService.getNoAuthFoundMap()); + return JsonView.NAME; + } + + Order instance; + if (id > 0) { + instance = service.find(id); + logger.info("order found : "+id); + } else { + instance = new Order(); + instance.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + logger.info("new order: "+NumberUtils.toInt(userData.get("sysGroupId"),0)); + } + + ServletRequestUtils.doBind(request, instance, null); + id = service.saveOrUpdate(instance); + logger.info("Order Save: "+instance.toString()); + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "list", method = { RequestMethod.GET, RequestMethod.POST }) + public String listOrder(Model model, @RequestParam String deviceId, @RequestParam String token, + HttpServletRequest request) throws Exception { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth(userData.get("id"),"ORDER_MAINTAIN"); + if (!haveAuth) { + model.addAllAttributes(authenticationService.getNoAuthFoundMap()); + return JsonView.NAME; + } + + final Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, "searchStr"); + CriteriaUtils.addInteger(request, args, "custId"); + args.put("sysGroupId", userData.get("sysGroupId")); + + CriteriaUtils.addInteger(request, args, "start"); + CriteriaUtils.addInteger(request, args, "limit"); + + logger.info("args : " + args); + + final List> records = service.search(args); + + //logger.info("record : " + records); + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + + @RequestMapping(value = "combo", method = { RequestMethod.GET, RequestMethod.POST }) + public String OrderCombo(Model model, @RequestParam String deviceId, @RequestParam String token, + HttpServletRequest request) throws ServletRequestBindingException { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + final Map args = new HashMap(); + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addInteger(request, args, "customerId"); + CriteriaUtils.addStringLike(request, args, "searchStr"); + + if(args.containsKey("searchStr") && args.get("searchStr").toString().length()>=2){ + args.put("_searchStr", args.get("searchStr")); + CriteriaUtils.addString(request, args, "searchStr"); + List> records = service.comboSearch(args); + model.addAttribute(Params.RECORDS, records); + }else if(args.containsKey("id")){ + List> records = service.comboSearch(args); + if(records != null) + model.addAttribute(Params.DATA, records.get(0)); + else + model.addAttribute(Params.DATA, new HashMap<>()); + }else if(args.containsKey("customerId")){ + List> records = service.comboSearch(NumberUtils.intValue(args.get("customerId"))); + if(records != null) + model.addAttribute(Params.DATA, records.get(0)); + else + model.addAttribute(Params.DATA, new HashMap<>()); + }else{ + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + model.addAttribute(Params.RECORDS, null); + return JsonView.NAME; + } + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "detail", method = { RequestMethod.GET, RequestMethod.POST }) + public String loadDetail(Model model, @RequestParam String deviceId, @RequestParam String token, + HttpServletRequest request) throws Exception { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth(userData.get("id"),"ORDER_MAINTAIN"); + if (!haveAuth) { + model.addAllAttributes(authenticationService.getNoAuthFoundMap()); + return JsonView.NAME; + } + + final Map args = new HashMap<>(); + + CriteriaUtils.addInteger(request, args, Params.ID); + + final Map data = service.loadOrder(args); + final List> itemRecords = service.searchItems(args); + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + model.addAttribute(Params.DATA, data); + model.addAttribute("itemRecords", itemRecords); + + return JsonView.NAME; + } + + + @RequestMapping(value = "load", method = { RequestMethod.GET, RequestMethod.POST }) + public String loadForOrderEdit(Model model, @RequestParam String deviceId, @RequestParam String token, + HttpServletRequest request) throws Exception { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth(userData.get("id"),"ORDER_MAINTAIN"); + if (!haveAuth) { + model.addAllAttributes(authenticationService.getNoAuthFoundMap()); + return JsonView.NAME; + } + + final Map args = new HashMap<>(); + + CriteriaUtils.addInteger(request, args, Params.ID); + + final Map data = service.loadOrder(args); + + model.addAttribute("selectedOrderRef", null); + if(data.get("ref") != null){ + List> refOrder = service.comboSearch(MapUtils.toHashMap("sysGroupId", userData.get("sysGroupId"),"orderId", data.get("ref"))); + if(refOrder!=null && refOrder.size()>0){ + model.addAttribute("selectedOrderRef", refOrder.get(0)); + } + } + + model.addAttribute("selectedCustomer", null); + if(data.get("custId") != null){ + List> cust = customerApiService.searchForCombo(MapUtils.toHashMap("id", data.get("custId"))); + if(cust!=null && cust.size()>0){ + model.addAttribute("selectedCustomer", cust.get(0)); + } + } + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + model.addAttribute(Params.DATA, data); + + return JsonView.NAME; + } + + + @RequestMapping(value = "get-current-ms.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String getCurrentMS(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, Integer orderId) { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + Order order = service.find(orderId); + + Map args = new HashMap(); + List> records = new ArrayList<>(); + if (order != null && order.getFileId() != null && order.getFileId() > 0) { + args.put("fileId", order.getFileId()); + args.put("refType", FileRefType.MEASUREMENT_SHEET); + records = fileService.searchFiles(args); + } + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "image-list-json", method = { RequestMethod.GET, RequestMethod.POST }) + public String getImageJson(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, Integer orderId) { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + final Map args = new HashMap(); + args.put("refType", FileRefType.ORDER); + args.put("refId", orderId); + final List> records = fileService.searchFiles(args); + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "item/save", method = { RequestMethod.GET, RequestMethod.POST }) + public String saveOrderItem(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id) throws ServletRequestBindingException, JsonProcessingException { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth(userData.get("id"),"ORDER_MAINTAIN"); + if (!haveAuth) { + model.addAllAttributes(authenticationService.getNoAuthFoundMap()); + return JsonView.NAME; + } + + OrderItem instance; + OrderItem oldRecord; + if (id > 0) { + instance = orderItemService.find(id); + logger.info("order Item found : "+id); + orderItemService.compare(instance, request); + oldRecord = SerializationUtils.clone(instance); + } else { + instance = new OrderItem(); + oldRecord = new OrderItem(); + instance.setSysGroupId(NumberUtils.toInt(userData.get("sysGroupId"),0)); + logger.info("new order Item"); + } + + ServletRequestUtils.doBind(request, instance, null); + id = orderItemService.saveOrUpdate(instance); + logger.info("Order Item Save: "+instance.toString()); + + //save log + if(oldRecord.getId() != null){ + orderItemService.log(LogUtils.ACTION_UPDATE, id, NumberUtils.intValue(userData.get("id")), instance, oldRecord); + }else{ + orderItemService.log(LogUtils.ACTION_CREATE, id, NumberUtils.intValue(userData.get("id")), instance); + } + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + + @RequestMapping(value = "item/delete", method = { RequestMethod.GET, RequestMethod.POST }) + public String deleteOrderItem(Model model, @RequestParam String deviceId, @RequestParam String token, HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id) throws JsonProcessingException { + + Map userData = authenticationService.findUserByAccessToken(deviceId, token); + if (userData == null) { + model.addAllAttributes(authenticationService.getNoUserFoundMap()); + return JsonView.NAME; + } + + boolean haveAuth = authenticationService.haveAuth(userData.get("id"),"ORDER_MAINTAIN"); + if (!haveAuth) { + model.addAllAttributes(authenticationService.getNoAuthFoundMap()); + return JsonView.NAME; + } + + OrderItem instance; + if (id > 0) { + instance = orderItemService.find(id); + logger.info("order Item found (delete) : "+id); + instance.setDeleted(true); + id = orderItemService.saveOrUpdate(instance); + orderItemService.log("Delete", id, NumberUtils.intValue(userData.get("id")), instance); + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/common/MaterialBand.java b/src/main/java/com/ffii/tls/common/MaterialBand.java new file mode 100644 index 0000000..6c6e615 --- /dev/null +++ b/src/main/java/com/ffii/tls/common/MaterialBand.java @@ -0,0 +1,51 @@ +package com.ffii.tbms.common; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "material_band") +public class MaterialBand extends BaseEntity { + + private static final long serialVersionUID = 8039256623625569162L; + + @Column(columnDefinition = "varchar(255)") + private String name; + + @Column(columnDefinition = "int(11)") + private Integer fileId; + + @Column(columnDefinition = "varchar(255)") + private String expectedPriceFormula; + + public MaterialBand() { + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public Integer getFileId() { + return fileId; + } + + public void setFileId(Integer fileId) { + this.fileId = fileId; + } + + public String getExpectedPriceFormula() { + return expectedPriceFormula; + } + + public void setExpectedPriceFormula(String expectedPriceFormula) { + this.expectedPriceFormula = expectedPriceFormula; + } + +} diff --git a/src/main/java/com/ffii/tls/common/MaterialItem.java b/src/main/java/com/ffii/tls/common/MaterialItem.java new file mode 100644 index 0000000..4c6317c --- /dev/null +++ b/src/main/java/com/ffii/tls/common/MaterialItem.java @@ -0,0 +1,151 @@ +package com.ffii.tbms.common; + +import java.math.BigDecimal; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "material_item") +public class MaterialItem extends BaseEntity { + + private static final long serialVersionUID = -483809080806589852L; + + @Column(columnDefinition = "int(11)") + private Integer bandId; + + @Column(columnDefinition = "int(11)") + private Integer orderIdx; + + @Column(columnDefinition = "varchar(255)") + private String name; + + @Column(columnDefinition = "varchar(255)") + private String bunch; + + @Column(columnDefinition = "varchar(255)") + private String itemNo; + + @Column(columnDefinition = "decimal(18,4)") + private BigDecimal cost; + + @Column(columnDefinition = "varchar(255)") + private String fabricNum; + + @Column(columnDefinition = "decimal(18,4)") + private BigDecimal suitPrice; + + @Column(columnDefinition = "decimal(18,4)") + private BigDecimal jacketPrice; + + @Column(columnDefinition = "decimal(18,4)") + private BigDecimal overcoatPrice; + + @Column(columnDefinition = "decimal(18,4)") + private BigDecimal pantsPrice; + + @Column(columnDefinition = "decimal(18,4)") + private BigDecimal otherPrice; + + public MaterialItem(){} + + public Integer getBandId() { + return bandId; + } + + public void setBandId(Integer bandId) { + this.bandId = bandId; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getBunch() { + return bunch; + } + + public void setBunch(String bunch) { + this.bunch = bunch; + } + + public String getItemNo() { + return itemNo; + } + + public void setItemNo(String itemNo) { + this.itemNo = itemNo; + } + + public BigDecimal getCost() { + return cost; + } + + public void setCost(BigDecimal cost) { + this.cost = cost; + } + + public BigDecimal getSuitPrice() { + return suitPrice; + } + + public void setSuitPrice(BigDecimal suitPrice) { + this.suitPrice = suitPrice; + } + + public BigDecimal getJacketPrice() { + return jacketPrice; + } + + public void setJacketPrice(BigDecimal jacketPrice) { + this.jacketPrice = jacketPrice; + } + + public BigDecimal getOvercoatPrice() { + return overcoatPrice; + } + + public void setOvercoatPrice(BigDecimal overcoatPrice) { + this.overcoatPrice = overcoatPrice; + } + + public BigDecimal getPantsPrice() { + return pantsPrice; + } + + public void setPantsPrice(BigDecimal pantsPrice) { + this.pantsPrice = pantsPrice; + } + + public BigDecimal getOtherPrice() { + return otherPrice; + } + + public void setOtherPrice(BigDecimal otherPrice) { + this.otherPrice = otherPrice; + } + + public String getFabricNum() { + return fabricNum; + } + + public void setFabricNum(String fabricNum) { + this.fabricNum = fabricNum; + } + + public Integer getOrderIdx() { + return orderIdx; + } + + public void setOrderIdx(Integer orderIdx) { + this.orderIdx = orderIdx; + } + +} diff --git a/src/main/java/com/ffii/tls/common/dao/MaterialBandDao.java b/src/main/java/com/ffii/tls/common/dao/MaterialBandDao.java new file mode 100644 index 0000000..381bb0c --- /dev/null +++ b/src/main/java/com/ffii/tls/common/dao/MaterialBandDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.common.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.common.MaterialBand; + +@Repository +public class MaterialBandDao extends HibernateDao { + + @Autowired + public MaterialBandDao(SessionFactory sessionFactory) { + super(MaterialBand.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/common/dao/MaterialItemDao.java b/src/main/java/com/ffii/tls/common/dao/MaterialItemDao.java new file mode 100644 index 0000000..fe569d9 --- /dev/null +++ b/src/main/java/com/ffii/tls/common/dao/MaterialItemDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.common.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.common.MaterialItem; + +@Repository +public class MaterialItemDao extends HibernateDao { + + @Autowired + public MaterialItemDao(SessionFactory sessionFactory) { + super(MaterialItem.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/common/service/MaterialService.java b/src/main/java/com/ffii/tls/common/service/MaterialService.java new file mode 100644 index 0000000..735cec6 --- /dev/null +++ b/src/main/java/com/ffii/tls/common/service/MaterialService.java @@ -0,0 +1,265 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.common.service; + +import java.math.BigDecimal; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.ExcelUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.common.MaterialBand; +import com.ffii.tbms.common.MaterialItem; +import com.ffii.tbms.common.dao.MaterialBandDao; +import com.ffii.tbms.common.dao.MaterialItemDao; + +import org.apache.poi.ss.usermodel.Cell; +import org.apache.poi.ss.usermodel.Row; +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + + +@Service +public class MaterialService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private MaterialBandDao bandDao; + + @Autowired + private MaterialItemDao itemDao; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdateBand(MaterialBand instance) { + return bandDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdateBandItem(MaterialItem instance) { + return itemDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public MaterialBand findBand(Integer id) { + return bandDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public MaterialItem findItem(Integer id) { + return itemDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchBands() { + Map args = new HashMap<>(); + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + + StringBuilder sql = new StringBuilder(" SELECT mb.*, f.filename, f.skey " + +" FROM material_band mb " + +" LEFT JOIN files f ON f.id = mb.fileId " + +" WHERE mb.deleted = 0 " + +" AND mb.sysGroupId = :sysGroupId "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map loadBand(int id) { + + Map args = new HashMap<>(); + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + args.put("id", id); + + StringBuilder sql = new StringBuilder(" SELECT " + +" mb.* " + +" FROM material_band mb " + +" WHERE id = :id " + +" AND mb.sysGroupId = :sysGroupId "); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchBandItems(int bandId) { + + Map args = new HashMap<>(); + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + args.put("bandId", bandId); + + StringBuilder sql = new StringBuilder( + " SELECT mi.* " + +" FROM material_item mi " + +" WHERE mi.deleted =0 " + +" AND mi.bandId = :bandId " + +" AND mi.sysGroupId = :sysGroupId " + +" ORDER BY mi.orderIdx, mi.id "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map loadBandItem(int id) { + + Map args = new HashMap<>(); + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + args.put("id", id); + + StringBuilder sql = new StringBuilder(" SELECT " + +" mi.* " + +" FROM material_item mi " + +" WHERE mi.id = :id" + +" AND mi.sysGroupId = :sysGroupId " ); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchBandIcon(int bandId) { + + Map args = new HashMap<>(); + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + args.put("bandId", bandId); + + StringBuilder sql = new StringBuilder( + " SELECT f.filename, f.id, f.skey, f.imageHeight, f.imageWidth " + +" FROM files_ref fr " + +" LEFT JOIN files f ON fr.fileId = f.id " + +" WHERE fr.refType = 'bandIcon' AND fr.refId = :bandId " + +" AND fr.sysGroupId = :sysGroupId "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public boolean updateItemOrderIdx(int id, int orderIdx) { + return jdbcDao.executeUpdate("UPDATE material_item SET orderIdx = :orderIdx WHERE id = :id", + MapUtils.toHashMap("id", id, "orderIdx", orderIdx)) > 0; + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public boolean importDataFromExcel(Workbook wb) { + Sheet sheet = wb.getSheetAt(0); + int bankRow = 0; + int formulaRow = 1; + int itemnameRow = 2; + int itemname2Row = 3; + int bunchRow = 4; + int costRow = 5; + int suitRow = 6; + int jacketRow = 7; + int overcoatRow = 8; + int pantsRow = 9; + int otherRow = 10; + + int rownum = 1; + boolean next = true; + + int bandId = 0; + while(next){ + Row row = sheet.getRow(rownum); + if (row == null){ + next = false; + break; + } + + String bankName=null; + if(row.getCell(bankRow)!=null){ + bankName = ExcelUtils.getStringValue(row.getCell(bankRow)); + } + + String formula=null; + if(row.getCell(formulaRow)!=null){ + formula = ExcelUtils.getStringValue(row.getCell(formulaRow)); + } + + if(bankName != null){ + MaterialBand band = new MaterialBand(); + band.setName(bankName); + band.setExpectedPriceFormula(formula); + bandId = saveOrUpdateBand(band); + } + + String itemName=null; + if(row.getCell(itemnameRow)!=null){ + itemName = ExcelUtils.getStringValue(row.getCell(itemnameRow)); + } + + if(row.getCell(itemname2Row)!=null){ + String name2 = ExcelUtils.getStringValue(row.getCell(itemname2Row)); + if(name2.length()>0) + itemName = itemName==null?name2:itemName+" ("+name2+")"; + } + + String bunch = null; + if(row.getCell(bunchRow)!=null){ + bunch = ExcelUtils.getStringValue(row.getCell(bunchRow)); + } + + BigDecimal cost = null; + if(row.getCell(costRow)!=null){ + cost = ExcelUtils.getDecimalValue(row.getCell(costRow),null); + } + + BigDecimal suit = null; + if(row.getCell(suitRow)!=null){ + suit = ExcelUtils.getDecimalValue(row.getCell(suitRow),null); + } + + BigDecimal jacket = null; + if(row.getCell(jacketRow)!=null){ + jacket = ExcelUtils.getDecimalValue(row.getCell(jacketRow),null); + } + + BigDecimal overcoat = null; + if(row.getCell(overcoatRow)!=null){ + overcoat = ExcelUtils.getDecimalValue(row.getCell(overcoatRow),null); + } + + BigDecimal pants = null; + if(row.getCell(pantsRow)!=null){ + pants = ExcelUtils.getDecimalValue(row.getCell(pantsRow),null); + } + + BigDecimal other = null; + if(row.getCell(otherRow)!=null){ + other = ExcelUtils.getDecimalValue(row.getCell(otherRow),null); + } + + MaterialItem item = new MaterialItem(); + item.setBandId(bandId); + item.setName(itemName); + item.setBunch(bunch); + item.setCost(cost); + item.setSuitPrice(suit); + item.setJacketPrice(jacket); + item.setOvercoatPrice(overcoat); + item.setPantsPrice(pants); + item.setOtherPrice(other); + + saveOrUpdateBandItem(item); + + rownum++; + + } + return true; + } + +} diff --git a/src/main/java/com/ffii/tls/common/web/MaterialController.java b/src/main/java/com/ffii/tls/common/web/MaterialController.java new file mode 100644 index 0000000..9e69f4b --- /dev/null +++ b/src/main/java/com/ffii/tls/common/web/MaterialController.java @@ -0,0 +1,300 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.common.web; + +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.apache.poi.poifs.filesystem.OfficeXmlFileException; +import org.apache.poi.ss.usermodel.Workbook; +import org.apache.poi.xssf.usermodel.XSSFWorkbook; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.util.Assert; +import org.springframework.web.multipart.MultipartHttpServletRequest; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.multipart.MultipartFile; + +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.common.MaterialBand; +import com.ffii.tbms.common.MaterialItem; +import com.ffii.tbms.common.service.MaterialService; +import com.ffii.tbms.file.FileRefType; +import com.ffii.tbms.file.service.FileService; +import com.ffii.core.utils.web.ServletRequestUtils; + + +@Controller +@RequestMapping(value = "/common/material") +public class MaterialController extends AbstractController { + + @Autowired + private MaterialService service; + + @Autowired + private FileService fileService; + + @RequestMapping(value = "/band/save", method = RequestMethod.POST) + public String bandSave(Model model, HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + MaterialBand instance; + if (id > 0) { + instance = service.findBand(id); + } else { + instance = new MaterialBand(); + } + ServletRequestUtils.doBind(request, instance, null); + id = service.saveOrUpdateBand(instance); + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + + @RequestMapping(value = "/band/icon", method = { RequestMethod.GET, RequestMethod.POST }) + public String getIcon(Model model, HttpServletRequest request, @RequestParam Integer bandId) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_VIEW") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + List> list = service.searchBandIcon(bandId); + model.addAttribute(Params.RECORDS, list); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/band/delete", method = RequestMethod.POST) + public String bandDelete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + + // find, mark delete, and save + MaterialBand instance = service.findBand(id); + instance.setDeleted(true); + service.saveOrUpdateBand(instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/band/icon/delete", method = RequestMethod.POST) + public String bandIconDelete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + + // find, mark delete, and save + MaterialBand instance = service.findBand(id); + + // search for existing file(s) with the same refType, refId, and filename + List> existingFiles = fileService.searchFiles( + MapUtils.toHashMap("refType", FileRefType.BAND_ICON, "refId", id)); + + // delete them if found + for (Map existingFile : existingFiles) { + fileService.deleteFile((Integer) existingFile.get("id"), (Integer) existingFile.get("refId"), + (String) existingFile.get("refType"), (String) existingFile.get("skey")); + } + + instance.setFileId(null); + service.saveOrUpdateBand(instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + + @RequestMapping(value = "/band/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String bandList(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_VIEW") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + + List> list = service.searchBands(); + model.addAttribute(Params.RECORDS, list); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/band/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String loadBand(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_VIEW") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + + Map data = service.loadBand(id); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + + @RequestMapping(value = "/item/save", method = RequestMethod.POST) + public String itemSave(Model model, HttpServletRequest request, @RequestParam(defaultValue = "-1") Integer id) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + MaterialItem instance; + if (id > 0) { + instance = service.findItem(id); + } else { + instance = new MaterialItem(); + } + ServletRequestUtils.doBind(request, instance, null); + id = service.saveOrUpdateBandItem(instance); + + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/item/delete", method = RequestMethod.POST) + public String itemDelete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + + // find, mark delete, and save + MaterialItem instance = service.findItem(id); + instance.setDeleted(true); + service.saveOrUpdateBandItem(instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/item/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String itemList(Model model, HttpServletRequest request, @RequestParam Integer bandId) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_VIEW") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + List> list = service.searchBandItems(bandId); + model.addAttribute(Params.RECORDS, list); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + + @RequestMapping(value = "/item/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String loadItem(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_VIEW") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + Map data = service.loadBandItem(id); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + + @RequestMapping(value = "/item/import", method = { RequestMethod.GET, RequestMethod.POST }) + public String ImportItem(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_VIEW") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + + MultipartFile multipartFile = ((MultipartHttpServletRequest) request).getFile("multipartFile"); + Assert.notNull(multipartFile, "multipartFile cannot be null!"); + Workbook wb = null; + try { + wb = new XSSFWorkbook(multipartFile.getInputStream()); + } catch (final OfficeXmlFileException oe) { + logger.warn("wb is xlsx, ignored"); + } + Assert.notNull(wb, "Workbook cannot be null!"); + + + model.addAttribute(Params.SUCCESS, service.importDataFromExcel(wb)); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + @RequestMapping(value = "/item/set-orderIdx", method = { RequestMethod.GET, RequestMethod.POST }) + public String setOrderIdx(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER") + || SecurityUtils.isGranted("PRICE_LIST_VIEW") + || SecurityUtils.isGranted("PRICE_LIST_MAINTAIN")) { + + List> id_orderIdx = (List>) ServletRequestUtils.getJsonListParameter(request, "id_orderIdx"); + + for(Map item: id_orderIdx){ + service.updateItemOrderIdx(item.get("id"), item.get("orderIdx")); + } + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/counter/IdCounter.java b/src/main/java/com/ffii/tls/counter/IdCounter.java new file mode 100644 index 0000000..bbd3f03 --- /dev/null +++ b/src/main/java/com/ffii/tls/counter/IdCounter.java @@ -0,0 +1,67 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.counter; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +/** + * @author Patrick + */ +@Entity +@Table(name = "id_counter") +public class IdCounter extends BaseEntity { + + private static final long serialVersionUID = 2968431879107638750L; + + @Column(columnDefinition = "varchar(50)") + private String name; + + @Column(nullable = false) + private int count; + + // min. length for code formatting + @Column(nullable = false) + private int length; + + /** Default constructor */ + public IdCounter() { + + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public int getCount() { + return count; + } + + public void setCount(int count) { + this.count = count; + } + + public int getLength() { + return length; + } + + public void setLength(int length) { + this.length = length; + } + +} diff --git a/src/main/java/com/ffii/tls/counter/dao/IdCounterDao.java b/src/main/java/com/ffii/tls/counter/dao/IdCounterDao.java new file mode 100644 index 0000000..7f3b6bb --- /dev/null +++ b/src/main/java/com/ffii/tls/counter/dao/IdCounterDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.counter.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.counter.IdCounter; + +@Repository +public class IdCounterDao extends HibernateDao { + + @Autowired + public IdCounterDao(SessionFactory sessionFactory) { + super(IdCounter.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/counter/service/IdCounterService.java b/src/main/java/com/ffii/tls/counter/service/IdCounterService.java new file mode 100644 index 0000000..8ae2cc6 --- /dev/null +++ b/src/main/java/com/ffii/tls/counter/service/IdCounterService.java @@ -0,0 +1,143 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.counter.service; + +import java.text.DecimalFormat; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.counter.IdCounter; +import com.ffii.tbms.counter.dao.IdCounterDao; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * @author Patrick + */ +@Service +public class IdCounterService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private IdCounterDao idCounterDao; + + // DecimalFormat cache + private static final DecimalFormat FORMATTER[] = { new DecimalFormat(""), + new DecimalFormat("0"), new DecimalFormat("00"), new DecimalFormat("000"), new DecimalFormat("0000"), new DecimalFormat("00000"), + new DecimalFormat("000000"), new DecimalFormat("0000000"), new DecimalFormat("00000000"), new DecimalFormat("000000000"), + new DecimalFormat("0000000000"), new DecimalFormat("00000000000"), new DecimalFormat("000000000000") }; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(IdCounter instance) { + return idCounterDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public IdCounter find(Integer id) { + return idCounterDao.find(id); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public IdCounter find(String name) { + return idCounterDao.findByQuery("from com.ffii.tbms.counter.IdCounter idc where idc.name = ?", name); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map queryForMap(String name) { + String sql = "SELECT * FROM id_counter WHERE name = :name"; + + return jdbcDao.queryForMap(sql, MapUtils.toHashMap(Params.NAME, name)); + } + + /** + * Get the next IdCounter (will be created if not found) value as formatted String with the minimum length specified. + *

+ * The counter value will be incremented and saved. + * + * @param name + * the name of the IdCounter + * @param length + * the minimum length of the string to return (e.g. a length of 3 will return 012 if the counter value is 12), however it doesn't + * limit the maximum size of the counter value (e.g. a length of 3 will return 1234 if the counter value is 1234) + * + * @return the next IdCounter value as formatted String with the minimum length specified + */ + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public String getNextCountString(String name, int length) { + if (length < 0 || length > 12) throw new IllegalArgumentException("The length must be between 0 to 12"); + return FORMATTER[length].format(getNextCount(name, length)); + } + + /** + * Get the next IdCounter (will be created if not found) preview value as formatted String with the minimum length specified. + * + * @param name + * the name of the IdCounter + * @param length + * the minimum length of the string to return (e.g. a length of 3 will return 012 if the counter value is 12), however it doesn't + * limit the maximum size of the counter value (e.g. a length of 3 will return 1234 if the counter value is 1234) + * + * @return the next IdCounter preview value as formatted String with the minimum length specified + */ + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public String getNextCountPreviewString(String name, int length) { + if (length < 0 || length > 12) throw new IllegalArgumentException("The length must be between 0 to 12"); + return FORMATTER[length].format(getNextCountPreview(name, length)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int getNextCount(String name, int length) { + + // find existing IdCounter + IdCounter instance = find(name); + + if (instance == null) { + // create IdCounter if not found + instance = new IdCounter(); + instance.setName(name); + instance.setLength(length); + instance.setCount(1); + saveOrUpdate(instance); + } else { + // else just increment and update IdCounter + instance.setCount(instance.getCount() + 1); + saveOrUpdate(instance); + } + + // return the incremented counter value + return instance.getCount(); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int getNextCountPreview(String name, int length) { + + // find existing IdCounter + IdCounter instance = find(name); + + if (instance == null) { + // create IdCounter if not found + instance = new IdCounter(); + instance.setName(name); + instance.setLength(length); + saveOrUpdate(instance); + } + + // return the incremented counter value + return instance.getCount() + 1; + } + +} diff --git a/src/main/java/com/ffii/tls/customer/Customer.java b/src/main/java/com/ffii/tls/customer/Customer.java new file mode 100644 index 0000000..4c94828 --- /dev/null +++ b/src/main/java/com/ffii/tls/customer/Customer.java @@ -0,0 +1,184 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.customer; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "customer") +public class Customer extends BaseEntity { + + private static final long serialVersionUID = -7086241311009708530L; + + + @Column(columnDefinition = "varchar(255)") + private String surname; + + @Column(columnDefinition = "varchar(255)") + private String firstName; + + @Column(columnDefinition = "varchar(255)") + private String nameCh; + + @Column(columnDefinition = "varchar(255)") + private String phone1; + + @Column(columnDefinition = "varchar(255)") + private String phone2; + + @Column(columnDefinition = "varchar(255)") + private String companyName; + + @Column(columnDefinition = "varchar(255)") + private String companyPhone; + + @Column(columnDefinition = "varchar(255)") + private String companyEmail; + + @Column(columnDefinition = "varchar(255)") + private String companyAddress; + + @Column(columnDefinition = "varchar(255)") + private String email; + + @Column(columnDefinition = "varchar(255)") + private String address; + + @Column(columnDefinition = "varchar(255)") + private String remarks; + + @Column(columnDefinition = "int(11)") + private Integer ref; + + @Column(columnDefinition = "varchar(255)") + private String tag; + + + public Customer() { + } + + public String getSurname() { + return surname; + } + + public void setSurname(String surname) { + this.surname = surname; + } + + public String getFirstName() { + return firstName; + } + + public void setFirstName(String firstName) { + this.firstName = firstName; + } + + public String getNameCh() { + return nameCh; + } + + public void setNameCh(String nameCh) { + this.nameCh = nameCh; + } + + public String getPhone1() { + return phone1; + } + + public void setPhone1(String phone1) { + this.phone1 = phone1; + } + + public String getPhone2() { + return phone2; + } + + public void setPhone2(String phone2) { + this.phone2 = phone2; + } + + public String getCompanyPhone() { + return companyPhone; + } + + public void setCompanyPhone(String companyPhone) { + this.companyPhone = companyPhone; + } + + public String getCompanyEmail() { + return companyEmail; + } + + public void setCompanyEmail(String companyEmail) { + this.companyEmail = companyEmail; + } + + public String getCompanyAddress() { + return companyAddress; + } + + public void setCompanyAddress(String companyAddress) { + this.companyAddress = companyAddress; + } + + public String getEmail() { + return email; + } + + public void setEmail(String email) { + this.email = email; + } + + public String getAddress() { + return address; + } + + public void setAddress(String address) { + this.address = address; + } + + public String getRemarks() { + return remarks; + } + + public void setRemarks(String remarks) { + this.remarks = remarks; + } + + public Integer getRef() { + return ref; + } + + public void setRef(Integer ref) { + this.ref = ref; + } + + public String getCompanyName() { + return companyName; + } + + public void setCompanyName(String companyName) { + this.companyName = companyName; + } + + public String getTag() { + return tag; + } + + public void setTag(String tag) { + this.tag = tag; + } + +} diff --git a/src/main/java/com/ffii/tls/customer/dao/CustomerDao.java b/src/main/java/com/ffii/tls/customer/dao/CustomerDao.java new file mode 100644 index 0000000..1b7aaa4 --- /dev/null +++ b/src/main/java/com/ffii/tls/customer/dao/CustomerDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.customer.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.customer.Customer; + +@Repository +public class CustomerDao extends HibernateDao { + + @Autowired + public CustomerDao(SessionFactory sessionFactory) { + super(Customer.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/customer/service/CustomerService.java b/src/main/java/com/ffii/tls/customer/service/CustomerService.java new file mode 100644 index 0000000..539f65f --- /dev/null +++ b/src/main/java/com/ffii/tls/customer/service/CustomerService.java @@ -0,0 +1,369 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.customer.service; + +import java.util.Arrays; +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.BooleanUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.customer.Customer; +import com.ffii.tbms.customer.dao.CustomerDao; +import com.ffii.tbms.order.Order; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * @author Patrick + */ +@Service +public class CustomerService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private CustomerDao customerDao; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(Customer instance) { + return customerDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Customer find(Integer id) { + return customerDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchForCombo(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder(" SELECT " + +" c.id, " + +" c.phone1, " + +" c.phone2, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName " + +" FROM customer c WHERE deleted = 0 "); + + if (args.containsKey(Params.QUERY)) + sql.append(" AND ( concat_ws(' ', c.firstName ,c.surname, c.nameCh, c.phone1, c.phone2) LIKE :query " + +" OR concat_ws(' ', c.surname, c.firstName, c.nameCh, phone1, phone2) LIKE :query ) "); + + if (args.containsKey(Params.ID)) + sql.append(" AND c.id = :id"); + + if(args.containsKey("sysGroupId")){ + sql.append(" AND c.sysGroupId = :sysGroupId "); + } + + sql.append(" ORDER BY c.surname, c.firstName "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + private String getSearchCriteriaString(Map args){ + StringBuilder sql = new StringBuilder(""); + + if (args != null) { + if (args.containsKey(Params.ID)) + sql.append(" AND c.id = :id"); + if (args.containsKey("surname")) + sql.append(" AND c.surname LIKE :surname "); + if (args.containsKey("firstName")) + sql.append(" AND c.firstName LIKE :firstName "); + if (args.containsKey("nameCh")) + sql.append(" AND c.nameCh LIKE :nameCh "); + if(args.containsKey("sysGroupId")){ + sql.append(" AND c.sysGroupId = :sysGroupId "); + } + if (args.containsKey("contact")) + sql.append(" AND (c.phone1 LIKE :contact OR c.phone2 LIKE :contact " + + " OR c.address LIKE :contact OR c.companyPhone LIKE :contact " + + " OR c.companyAddress LIKE :contact ) "); + if (args.containsKey("email")) + sql.append(" AND (c.email LIKE :email OR c.companyEmail LIKE :email ) "); + + if (args.containsKey("tag")){ + String str = args.get("tag").toString().trim(); + String[] array = str.split(" "); + str = ""; + for(String tag: array){ + if(!str.equals("")){ + str = str+" OR "; + } + str = str+" c.tag LIKE '%"+tag+"%' "; + } + sql.append(" AND ( "+str+" ) "); + } + + //search customer order + if((args.containsKey("onHand") && BooleanUtils.isTrue(args.get("onHand"))) + || args.containsKey("orderType") + || args.containsKey("orderCode") + || args.containsKey("fromDate") + || args.containsKey("toDate")){ + + sql.append(" AND EXISTS( SELECT 1 FROM orders o " + +" WHERE o.custId = c.id " + +" AND o.deleted = 0 " + +" AND o.status != "+Order.STATUS_CANCELLED+" "); + + if (args.containsKey("onHand") && BooleanUtils.isTrue(args.get("onHand"))) + sql.append(" AND o.status = "+Order.STATUS_ON_HAND+" "); + if (args.containsKey("orderType")) + sql.append(" AND o.type = :orderType "); + if (args.containsKey("orderCode")) + sql.append(" AND o.code LIKE :orderCode "); + if (args.containsKey("fromDate")) + sql.append(" AND o.targetCompleteDate >= :fromDate "); + if (args.containsKey("toDate")) + sql.append(" AND o.targetCompleteDate < :toDate "); + + sql.append(" ) "); + } + + //search isBalance + if (args.containsKey("balance") && BooleanUtils.isTrue(args.get("balance"))) + sql.append(" AND IFNULL(custOrders.amount,0) > IFNULL(custPayment.amount,0) "); + + } + + return sql.toString(); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder( + " SELECT " + +" c.id," + +" c.surname, " + +" c.firstName, " + +" c.nameCh, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName, " + +" c.phone1, " + +" c.phone2, " + +" c.companyPhone, " + +" c.companyEmail, " + +" c.companyAddress, " + +" c.email, " + +" c.address, " + +" c.remarks, " + +" c.tag, " + +" lastMeetingDate.date As lastMeetingDate, " + +" nextMeetingDate.date AS nextMeetingDate, " + +" refCust.customerName AS refCustomerName, " + +" IFNULL(custOrders.amount,0) AS orderAmount, " + +" IFNULL(custPayment.amount,0) AS paymentAmount, " + +" (IFNULL(custOrders.amount,0) <= IFNULL(custPayment.amount,0)) AS isBalance, " + +" minTargetDate.targetCompleteDate AS targetCompleteDate," + +" custOrders.onHandOrderNum " + +" FROM " + +" customer c " + +" LEFT JOIN " + +" (SELECT " + +" CONCAT(IF(_c.firstName IS NULL, '', CONCAT(_c.firstName, ' ')), " + +" IF(_c.surname IS NULL, '', CONCAT(_c.surname, ' ')), " + +" IF(_c.nameCh IS NULL, '', _c.nameCh)) AS customerName, " + +" _c.id " + +" FROM customer _c ) refCust ON refCust.id = c.ref " + + +" LEFT JOIN " + +" (SELECT " + +" o.custId, SUM(oi.price) AS amount, " + +" SUM(IF(o.status = "+Order.STATUS_ON_HAND+", 1, 0)) AS onHandOrderNum " + +" FROM" + +" orders o " + +" LEFT JOIN order_item oi ON oi.orderId = o.id " + +" WHERE " + +" o.deleted = 0 AND oi.deleted = 0" + +" AND o.status != - 1" + +" GROUP BY o.custId) custOrders ON custOrders.custId = c.id" + + +" LEFT JOIN" + +" (SELECT " + +" o.custId, SUM(p.amount) AS amount" + +" FROM" + +" orders o" + +" LEFT JOIN payment p ON p.orderId = o.id" + +" WHERE" + +" o.deleted = 0 AND p.deleted = 0 " + //+" AND o.ignoreC = 0 " + +" AND o.status != - 1 " + +" GROUP BY o.custId) custPayment ON custPayment.custId = c.id" + + +" LEFT JOIN " + +" ( SELECT Max(m.date) AS date, m.custId " + +" FROM meeting m " + +" WHERE m.deleted = 0 " + +" AND DATE(m.date) < DATE(current_date()) " + +" GROUP BY m.custId ) lastMeetingDate ON lastMeetingDate.custId = c.id " + + +" LEFT JOIN " + +" ( SELECT MIN(m.date) AS date, m.custId " + +" FROM meeting m " + +" WHERE m.deleted = 0 " + +" AND DATE(m.date) >= DATE(current_date()) " + +" GROUP BY m.custId ) nextMeetingDate ON nextMeetingDate.custId = c.id " + + +"LEFT JOIN " + +" ( SELECT o.custId, " + +" MIN(o.targetCompleteDate) AS targetCompleteDate " + +" FROM orders o " + +" WHERE o.deleted = 0 " + +" AND o.status = "+Order.STATUS_ON_HAND+" " + +" AND o.targetCompleteDate IS NOT NULL " + +" GROUP BY o.custId) minTargetDate ON minTargetDate.custId = c.id " + + +" WHERE" + +" c.deleted = 0 "); + + sql.append(getSearchCriteriaString(args)); + + sql.append(" ORDER BY ( 0+0 "); + + if (args != null) { + if (args.containsKey("_surname")) + sql.append(" + IF( c.surname = :_surname,1,0) + IF( c.surname LIKE '"+args.get("_surname")+"%',1,0) "); + if (args.containsKey("_firstName")) + sql.append(" + IF( c.firstName = :_firstName,1,0) + IF( c.firstName LIKE '"+args.get("_firstName")+"%',1,0) "); + if (args.containsKey("_nameCh")) + sql.append(" + IF( c.nameCh = :_nameCh,1,0) + IF( c.nameCh LIKE '"+args.get("_nameCh")+"%',1,0) "); + } + sql.append(" ) DESC, "); + sql.append(" TRIM(c.firstName), TRIM(c.surname), TRIM(c.nameCh), c.id "); + + if (args != null) { + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map countSearch(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder( + " SELECT " + +" COUNT(*) AS count " + +" FROM" + +" ( SELECT " + +" c.id " + +" FROM " + +" customer c " + +" LEFT JOIN " + + +" (SELECT " + +" o.custId, SUM(oi.price) AS amount, " + +" SUM(IF(o.status = "+Order.STATUS_ON_HAND+", 1, 0)) AS onHandOrderNum " + +" FROM" + +" orders o " + +" LEFT JOIN order_item oi ON oi.orderId = o.id " + +" WHERE " + +" o.deleted = 0 AND oi.deleted = 0" + +" AND o.status != - 1" + +" GROUP BY o.custId) custOrders ON custOrders.custId = c.id" + + +" LEFT JOIN" + +" (SELECT " + +" o.custId, SUM(p.amount) AS amount" + +" FROM" + +" orders o" + +" LEFT JOIN payment p ON p.orderId = o.id" + +" WHERE" + +" o.deleted = 0 AND p.deleted = 0 " + //+" AND o.ignoreC = 0 " + +" AND o.status != - 1" + +" GROUP BY o.custId) custPayment ON custPayment.custId = c.id" + + +" WHERE" + +" c.deleted = 0"); + + sql.append(getSearchCriteriaString(args)); + + sql.append(") _t"); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map queryForMap(Integer id) { + Map args = MapUtils.toHashMap(Params.ID, id); + SecurityUtils.authArgs(args); + + String sql = "SELECT c.*, " + +" CONCAT_WS(' ',c.firstName , c.surname , c.nameCh) AS customerName, " + +" CONCAT_WS('/',c.phone1, c.phone2) AS phoneNum " + +" FROM customer c WHERE c.id = :id "; + + if(args.containsKey("sysGroupId")){ + sql+=" AND c.sysGroupId = :sysGroupId "; + } + return jdbcDao.queryForMap(sql, args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map getOrderIds(Map args) { + + SecurityUtils.authArgs(args); + + String sql = "SELECT GROUP_CONCAT(o.id ORDER BY o.date DESC, o.id DESC) AS ids " + +" FROM orders o " + +" WHERE 1=1 " + +" AND o.custId = :custId "; + + if (args != null) { + if (args.containsKey("ignoreOrderId")) + sql+=" AND o.id != :ignoreOrderId "; + + if(args.containsKey("sysGroupId")){ + sql+=" AND o.sysGroupId = :sysGroupId "; + } + } + sql+=" GROUP BY o.custId "; + + return jdbcDao.queryForMap(sql, args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> getRelatedOrder(int id) { + + Map args = MapUtils.toHashMap(Params.ID, id); + SecurityUtils.authArgs(args); + + String sql = " SELECT o.* FROM orders o WHERE o.custId = :id "; + if (args != null) { + + if(args.containsKey("sysGroupId")){ + sql+=" AND o.sysGroupId = :sysGroupId "; + } + } + return jdbcDao.queryForList(sql, args); + } +} diff --git a/src/main/java/com/ffii/tls/customer/web/CustomerController.java b/src/main/java/com/ffii/tls/customer/web/CustomerController.java new file mode 100644 index 0000000..b468ffa --- /dev/null +++ b/src/main/java/com/ffii/tls/customer/web/CustomerController.java @@ -0,0 +1,258 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.customer.web; + +import java.util.Arrays; +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.security.crypto.password.StandardPasswordEncoder; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.customer.Customer; +import com.ffii.tbms.customer.service.CustomerService; +import com.ffii.tbms.file.FileRefType; +import com.ffii.tbms.file.service.FileService; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.order.Order; +import com.ffii.tbms.order.service.OrderService; + +@Controller +@RequestMapping(value = "/customer") +public class CustomerController extends AbstractController { + + @Autowired + private CustomerService customerService; + + @Autowired + private FileService fileService; + + @Autowired + private OrderService orderService; + + @Autowired + private StandardPasswordEncoder passwordEncoder; + + @RequestMapping(value = "/save", method = RequestMethod.POST) + public String save(Model model, HttpServletRequest request, @RequestParam(defaultValue = "-1") Integer id) throws Exception { + + if (SecurityUtils.isGranted("CUSTOMER_MAINTAIN")) { + Customer instance; + if (id > 0) { + instance = customerService.find(id); + } else { + instance = new Customer(); + } + + ServletRequestUtils.doBind(request, instance, null); + id = customerService.saveOrUpdate(instance); + + model.addAttribute(Params.ID, id); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/delete", method = RequestMethod.POST) + public String delete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("CUSTOMER_MAINTAIN") && SecurityUtils.isGranted("CUSTOMER_DELETE")) { + + // find, mark delete, and save + Customer instance = customerService.find(id); + instance.setDeleted(true); + customerService.saveOrUpdate(instance); + + List> orderList = customerService.getRelatedOrder(id); + for(Map o : orderList){ + orderService.deletedOrder(NumberUtils.intValue(o.get("id"), 0)); + } + + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + model.addAttribute(Params.AUTH, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String load(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("CUSTOMER_MAINTAIN")) { + Map data = customerService.queryForMap(id); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/combo.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String comboJson(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, Params.QUERY); + CriteriaUtils.addInteger(request, args, "deptId"); + + List> records = customerService.searchForCombo(args); + + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("CUSTOMER_MAINTAIN")) { + Map args = new HashMap(); + + CriteriaUtils.addStringLike(request, args, Params.QUERY); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addString(request, args, "surname"); + CriteriaUtils.addString(request, args, "firstName"); + CriteriaUtils.addString(request, args, "nameCh"); + CriteriaUtils.addStringLike(request, args, "contact"); + CriteriaUtils.addStringLike(request, args, "email"); + CriteriaUtils.addBoolean(request, args, "onHand"); + CriteriaUtils.addBoolean(request, args, "balance"); + CriteriaUtils.addString(request, args, "orderType"); + CriteriaUtils.addStringLike(request, args, "orderCode"); + CriteriaUtils.addDate(request, args, "fromDate"); + CriteriaUtils.addDateTo(request, args, "toDate"); + CriteriaUtils.addString(request, args, "tag"); + + CriteriaUtils.addInteger(request, args, "start"); + CriteriaUtils.addInteger(request, args, "limit"); + + if(args.containsKey("surname")){ + args.put("_surname", args.get("surname")); + args.put("surname", "%"+args.get("surname")+"%"); + } + + if(args.containsKey("firstName")){ + args.put("_firstName", args.get("firstName")); + args.put("firstName", "%"+args.get("firstName")+"%"); + } + + if(args.containsKey("nameCh")){ + args.put("_nameCh", args.get("nameCh")); + args.put("nameCh", "%"+args.get("nameCh")+"%"); + } + + args.put("today", new Date()); + + if(args.containsKey("tag")){ + String str = args.get("tag").toString().trim(); + List strList = Arrays.asList(str.split("")); + if(strList != null && strList.size()>0){ + for(String s: strList){ + + } + }else{ + args.remove("tag"); + } + } + + List> records = customerService.search(args); + Map count = customerService.countSearch(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("total", NumberUtils.intValue(count.get("count"))); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/image-list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String imageListJson(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("CUSTOMER_MAINTAIN")) { + Map args = new HashMap(); + args.put("refType", FileRefType.CUSTOMER); + args.put("refId", id); + + List> records = fileService.searchFiles(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("title", "Customer Photo"); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/order-list", method = { RequestMethod.GET, RequestMethod.POST }) + public String orderListJson(Model model, HttpServletRequest request, @RequestParam Integer custId) throws Exception { + + if (SecurityUtils.isGranted("CUSTOMER_MAINTAIN")) { + Map args = new HashMap(); + args.put("custId", custId); + CriteriaUtils.addInteger(request, args, "ignoreOrderId"); + + Map records = customerService.getOrderIds(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/get-auth", method = { RequestMethod.POST }) + public String getDeleteAuth(Model model, HttpServletRequest request, @RequestParam String v) throws Exception { + + if (SecurityUtils.isGranted("CUSTOMER_MAINTAIN")) { + + if(passwordEncoder.matches(v, SecurityUtils.getUser().getPassword())) + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + else + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/example/Example.java b/src/main/java/com/ffii/tls/example/Example.java new file mode 100644 index 0000000..4a4a9e8 --- /dev/null +++ b/src/main/java/com/ffii/tls/example/Example.java @@ -0,0 +1,134 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.example; + +import java.math.BigDecimal; +import java.util.Date; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; +import javax.persistence.Transient; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "example") +public class Example extends BaseEntity { + + private static final long serialVersionUID = 6045007748715095923L; + + @Column(columnDefinition = "varchar(50)", nullable = false) + private String name; + + @Column(columnDefinition = "varchar(255)") + private String description; + + @Column(columnDefinition = "int", nullable = false) + private int intValue; + + @Column(columnDefinition = "int") + private Integer integerValue; + + @Column(columnDefinition = "decimal(12,2)") + private BigDecimal decimalValue; + + @Column(columnDefinition = "boolean", nullable = false) + private boolean booleanValue; + + @Column(columnDefinition = "date") + private Date dateValue; + + @Column(columnDefinition = "datetime") + private Date datetimeValue; + + // @Transient means it wont be saved to database + @Transient + private String transientField; + + /** Default constructor */ + public Example() { + + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getDescription() { + return description; + } + + public void setDescription(String description) { + this.description = description; + } + + public int getIntValue() { + return intValue; + } + + public void setIntValue(int intValue) { + this.intValue = intValue; + } + + public Integer getIntegerValue() { + return integerValue; + } + + public void setIntegerValue(Integer integerValue) { + this.integerValue = integerValue; + } + + public BigDecimal getDecimalValue() { + return decimalValue; + } + + public void setDecimalValue(BigDecimal decimalValue) { + this.decimalValue = decimalValue; + } + + public boolean isBooleanValue() { + return booleanValue; + } + + public void setBooleanValue(boolean booleanValue) { + this.booleanValue = booleanValue; + } + + public Date getDateValue() { + return dateValue; + } + + public void setDateValue(Date dateValue) { + this.dateValue = dateValue; + } + + public Date getDatetimeValue() { + return datetimeValue; + } + + public void setDatetimeValue(Date datetimeValue) { + this.datetimeValue = datetimeValue; + } + + public String getTransientField() { + return transientField; + } + + public void setTransientField(String transientField) { + this.transientField = transientField; + } + +} diff --git a/src/main/java/com/ffii/tls/example/dao/ExampleDao.java b/src/main/java/com/ffii/tls/example/dao/ExampleDao.java new file mode 100644 index 0000000..5669379 --- /dev/null +++ b/src/main/java/com/ffii/tls/example/dao/ExampleDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.example.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.example.Example; + +@Repository +public class ExampleDao extends HibernateDao { + + @Autowired + public ExampleDao(SessionFactory sessionFactory) { + super(Example.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/example/service/ExampleService.java b/src/main/java/com/ffii/tls/example/service/ExampleService.java new file mode 100644 index 0000000..7890ade --- /dev/null +++ b/src/main/java/com/ffii/tls/example/service/ExampleService.java @@ -0,0 +1,134 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.example.service; + +import java.util.Date; +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.DateUtils; +import com.ffii.core.utils.ExcelUtils; +import com.ffii.core.utils.JsonUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.example.Example; +import com.ffii.tbms.example.dao.ExampleDao; +import com.ffii.tbms.file.service.FileService; +import com.ffii.tbms.log.service.AuditLogService; + +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.core.io.ResourceLoader; +import org.springframework.scheduling.annotation.Scheduled; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * Example Service + * + * @author Patrick + */ +@Service +public class ExampleService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private ExampleDao exampleDao; + + @Autowired + private FileService fileService; + + @Autowired + private ResourceLoader resourceLoader; + + @Autowired + private AuditLogService auditLogService; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveExample(Example instance) { + return exampleDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int insertSomething(Map args) { + return jdbcDao.executeInsertAndReturnKey("example", Params.ID, args).intValue(); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void updateStatusWithAuditLog() { + Map args = MapUtils.toHashMap(Params.ID, 1, "status", "pig", "mode", "B"); + int rs = jdbcDao.executeUpdateByTable("job", args); + + if (rs > 0) auditLogService.save("job", 1, SecurityUtils.getUser().getId(), new Date(), null, JsonUtils.toJsonString(args)); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + String sql = "SELECT 1"; + + return jdbcDao.queryForList(sql, args); + } + + /** + * Scheduled method example using cron expression
+ * 1. return type must be void
+ * 2. must not have any parameters
+ * + *

+ * Cron expression:
+ * 1. Seconds: 0-59
+ * 2. Minutes: 0-59
+ * 3. Hours: 0-23
+ * 4. Day of month: 1-31
+ * 5. Month: 0-11 = Jan to Dec
+ * 6. Day of week: 1-7 = Sunday to Saturday
+ */ + @Scheduled(cron = "0 5 0 * * ?") // everyday at 00:05:00 + public void scheduledMethodCron() { + logger.info("scheduledMethodCron at 00:05:00"); + } + + @Scheduled(cron = "0 0 12 * * ?") // everyday at noon 12:00:00 + public void scheduledExcelReports() { + Workbook workbook = ExcelUtils.loadXSSFWorkbookFromTemplateSource(resourceLoader, "WEB-INF/report/exampleTemplate.xlsx"); + Sheet sheet = workbook.getSheetAt(0); + + int colIndex = 1; + for (int i = 0; i < 10; i++) { + ExcelUtils.setCellValue(sheet, i, colIndex, i); + } + + // save the Excel file + byte[] bytes = ExcelUtils.toByteArray(workbook); + fileService.saveFile("Example_Report_" + DateUtils.SQL_DATE_FORMAT.format(new Date()), "", "exampleReport", 0, "", bytes); + } + + /** + * Scheduled method example using fixed rate
+ * 1. return type must be void
+ * 2. must not have any parameters
+ * + * fixedRate in ms, e.g. 60000ms = run every 60 seconds + */ + @Scheduled(fixedRate = 60000) + public void scheduledMethodFixedRate() { + logger.debug("scheduledMethodFixedRate at 60000ms"); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/example/web/ExampleController.java b/src/main/java/com/ffii/tls/example/web/ExampleController.java new file mode 100644 index 0000000..39f3a1d --- /dev/null +++ b/src/main/java/com/ffii/tls/example/web/ExampleController.java @@ -0,0 +1,41 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.example.web; + +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.example.service.ExampleService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestParam; + +@Controller +@RequestMapping(value = "/example") +public class ExampleController { + + @Autowired + private ExampleService exampleService; + + @RequestMapping("/1") + public String example1(@RequestParam(defaultValue = "Pig") String name, Model model) { + model.addAttribute("name", name); + return JsonView.NAME; + } + + @RequestMapping("/test2") + public String test2(Model model) { + exampleService.updateStatusWithAuditLog(); + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/file/File.java b/src/main/java/com/ffii/tls/file/File.java new file mode 100644 index 0000000..105f12e --- /dev/null +++ b/src/main/java/com/ffii/tls/file/File.java @@ -0,0 +1,124 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "files") +public class File extends BaseEntity { + + private static final long serialVersionUID = -8832818363002693551L; + + public static final int ONE_KILOBYTE = 1024; + public static final int ONE_MEGABYTE = 1048576; + + @Column(columnDefinition = "varchar(20)") + private String systemType; + + @Column(columnDefinition = "varchar(16)", nullable = false) + private String skey; + + @Column(columnDefinition = "varchar(255)") + private String description; + + @Column(columnDefinition = "varchar(255)") + private String filename; + + @Column(columnDefinition = "varchar(255)") + private String mimetype; + + @Column(columnDefinition = "int") + private long filesize; + + @Column(columnDefinition = "int") + private int imageHeight; + @Column(columnDefinition = "int") + private int imageWidth; + + /** Default constructor */ + public File() { + + } + + /* + * getters and setters + */ + + public String getSystemType() { + return systemType; + } + + public void setSystemType(String systemType) { + this.systemType = systemType; + } + + public String getSkey() { + return skey; + } + + public void setSkey(String skey) { + this.skey = skey; + } + + public String getDescription() { + return description; + } + + public void setDescription(String description) { + this.description = description; + } + + public String getFilename() { + return filename; + } + + public void setFilename(String filename) { + this.filename = filename; + } + + public String getMimetype() { + return mimetype; + } + + public void setMimetype(String mimetype) { + this.mimetype = mimetype; + } + + public long getFilesize() { + return filesize; + } + + public void setFilesize(long filesize) { + this.filesize = filesize; + } + + public int getImageHeight() { + return imageHeight; + } + + public void setImageHeight(int imageHeight) { + this.imageHeight = imageHeight; + } + + public int getImageWidth() { + return imageWidth; + } + + public void setImageWidth(int imageWidth) { + this.imageWidth = imageWidth; + } + +} diff --git a/src/main/java/com/ffii/tls/file/FileBlob.java b/src/main/java/com/ffii/tls/file/FileBlob.java new file mode 100644 index 0000000..15552f7 --- /dev/null +++ b/src/main/java/com/ffii/tls/file/FileBlob.java @@ -0,0 +1,56 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "files_blob") +public class FileBlob extends BaseEntity { + + private static final long serialVersionUID = -9044712421536780602L; + + @Column(columnDefinition = "int") + private int fileId; + + @Column(columnDefinition = "longblob") + private byte[] bytes; + + /** Default constructor */ + public FileBlob() { + + } + + /* + * getters and setters + */ + + public int getFileId() { + return fileId; + } + + public void setFileId(int fileId) { + this.fileId = fileId; + } + + public byte[] getBytes() { + return bytes; + } + + public void setBytes(byte[] bytes) { + this.bytes = bytes; + } + +} diff --git a/src/main/java/com/ffii/tls/file/FileRef.java b/src/main/java/com/ffii/tls/file/FileRef.java new file mode 100644 index 0000000..d047a20 --- /dev/null +++ b/src/main/java/com/ffii/tls/file/FileRef.java @@ -0,0 +1,77 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "files_ref") +public class FileRef extends BaseEntity { + + private static final long serialVersionUID = -9133877150126183428L; + + @Column(columnDefinition = "int", nullable = false) + private int fileId; + + @Column(columnDefinition = "varchar(30)", nullable = false) + private String refType; + + @Column(columnDefinition = "int", nullable = false) + private int refId; + + @Column(columnDefinition = "varchar(50)") + private String refCode; + + /** Default constructor */ + public FileRef() { + } + + /* + * getters and setters + */ + + public int getFileId() { + return fileId; + } + + public void setFileId(int fileId) { + this.fileId = fileId; + } + + public String getRefType() { + return refType; + } + + public void setRefType(String refType) { + this.refType = refType; + } + + public int getRefId() { + return refId; + } + + public void setRefId(int refId) { + this.refId = refId; + } + + public String getRefCode() { + return refCode; + } + + public void setRefCode(String refCode) { + this.refCode = refCode; + } + +} diff --git a/src/main/java/com/ffii/tls/file/FileRefType.java b/src/main/java/com/ffii/tls/file/FileRefType.java new file mode 100644 index 0000000..dc03a09 --- /dev/null +++ b/src/main/java/com/ffii/tls/file/FileRefType.java @@ -0,0 +1,28 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file; + +public class FileRefType { + + /** ref by Customer ID */ + public static final String CUSTOMER = "customer"; + + /** ref by Order ID */ + public static final String ORDER = "order"; + + /** ref by Order ID , refCode = custId*/ + public static final String MEASUREMENT_SHEET = "ms"; + + /** ref by Band Id */ + public static final String BAND_ICON = "bandIcon"; + + +} diff --git a/src/main/java/com/ffii/tls/file/dao/FileBlobDao.java b/src/main/java/com/ffii/tls/file/dao/FileBlobDao.java new file mode 100644 index 0000000..7e99a99 --- /dev/null +++ b/src/main/java/com/ffii/tls/file/dao/FileBlobDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.file.FileBlob; + +@Repository +public class FileBlobDao extends HibernateDao { + + @Autowired + public FileBlobDao(SessionFactory sessionFactory) { + super(FileBlob.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/file/dao/FileDao.java b/src/main/java/com/ffii/tls/file/dao/FileDao.java new file mode 100644 index 0000000..4e910f5 --- /dev/null +++ b/src/main/java/com/ffii/tls/file/dao/FileDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.file.File; + +@Repository +public class FileDao extends HibernateDao { + + @Autowired + public FileDao(SessionFactory sessionFactory) { + super(File.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/file/dao/FileRefDao.java b/src/main/java/com/ffii/tls/file/dao/FileRefDao.java new file mode 100644 index 0000000..5087654 --- /dev/null +++ b/src/main/java/com/ffii/tls/file/dao/FileRefDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.file.FileRef; + +@Repository +public class FileRefDao extends HibernateDao { + + @Autowired + public FileRefDao(SessionFactory sessionFactory) { + super(FileRef.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/file/service/FileService.java b/src/main/java/com/ffii/tls/file/service/FileService.java new file mode 100644 index 0000000..2dfbc13 --- /dev/null +++ b/src/main/java/com/ffii/tls/file/service/FileService.java @@ -0,0 +1,292 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file.service; + +import java.awt.image.BufferedImage; +import java.io.ByteArrayInputStream; +import java.io.IOException; +import java.util.List; +import java.util.Map; + +import javax.imageio.ImageIO; + +import org.apache.commons.lang3.RandomStringUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.scheduling.annotation.Scheduled; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.FileUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.core.web.view.AbstractView; +import com.ffii.tbms.file.File; +import com.ffii.tbms.file.FileBlob; +import com.ffii.tbms.file.FileRef; +import com.ffii.tbms.file.dao.FileBlobDao; +import com.ffii.tbms.file.dao.FileDao; +import com.ffii.tbms.file.dao.FileRefDao; + +/** + * @author Patrick + */ +@Service +public class FileService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private FileDao fileDao; + + @Autowired + private FileBlobDao fileBlobDao; + + @Autowired + private FileRefDao fileRefDao; + + /** + * Save File, FileBlob, and FileRef in one go + * + * @param filename + * the filename, cannot be null + * @param description + * optional File description + * @param refType + * the File reference type, should not be empty + * @param refId + * mandatory, use 0 if N/A + * @param refCode + * optional + * @param bytes + * the File byte array + * + * @return File ID + */ + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveFile(String filename, String description, String refType, int refId, String refCode, byte[] bytes) { + File file = new File(); + file.setFilename(filename); + file.setDescription(description); + file.setMimetype(FileUtils.guessMimetype(filename)); + file.setFilesize(bytes.length); + file.setSkey(RandomStringUtils.randomAlphanumeric(16)); + + FileBlob fileBlob = new FileBlob(); + fileBlob.setBytes(bytes); + + FileRef fileRef = new FileRef(); + fileRef.setRefId(refId); + fileRef.setRefType(refType); + fileRef.setRefCode(refCode); + + // try to get width and height if mimetype is png or jpeg + if (AbstractView.CONTENT_TYPE_PNG.equals(file.getMimetype()) || AbstractView.CONTENT_TYPE_JPEG.equals(file.getMimetype())) { + BufferedImage image; + try { + image = ImageIO.read(new ByteArrayInputStream(bytes)); + if (image != null) { + file.setImageWidth(image.getWidth()); + file.setImageHeight(image.getHeight()); + } + } catch (IOException e) { + // ignore + } + } + + // save File + saveFile(file); + + // save FileBlob + fileBlob.setFileId(file.getId()); + saveFileBlob(fileBlob); + + // save FileRef + fileRef.setFileId(file.getId()); + saveFileRef(fileRef); + + return file.getId(); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveFile(File instance) { + return fileDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveFileBlob(FileBlob instance) { + return fileBlobDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveFileRef(FileRef instance) { + return fileRefDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public File findFileByIdAndKey(int id, String skey) { + return fileDao.findByQuery("from com.ffii.tbms.file.File f where f.id = ? and f.skey = ?", id, skey); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public File findFileById(int id) { + return fileDao.findByQuery("from com.ffii.tbms.file.File f where f.id = ? ", id); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public FileRef findFileRefByTypeAndId(String refType, int refId) { + return fileRefDao.findByQuery("from com.ffii.tbms.file.FileRef where refType = ? and refId = ?", refType, refId); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public FileRef findFileRefByfileId(int fileId) { + return fileRefDao.findByQuery("from com.ffii.tbms.file.FileRef where fileId = ?", fileId); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public FileBlob findFileBlobByFileId(int fileId) { + return fileBlobDao.findByQuery("from com.ffii.tbms.file.FileBlob fb where fb.fileId = ?", fileId); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public boolean isFileExists(int id, String skey) { + + String sql = "SELECT" + + " COUNT(1)" + + " FROM files f" + + " WHERE f.deleted = 0" + + " AND f.id = :id" + + " AND f.skey = :skey"; + + int count = jdbcDao.queryForInt(sql, MapUtils.toHashMap("id", id, "skey", skey)); + + return (count > 0); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> searchFiles(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " f.id," + + " f.filename," + + " f.filesize," + + " f.mimetype, " + + " f.skey," + + " fr.refId," + + " fr.refType," + + " f.created," + + " f.imageWidth," + + " f.imageHeight," + + " u.fullname AS createdByName," + + " f.description" + + " FROM files f" + + " LEFT JOIN files_ref fr ON f.id = fr.fileId" + + " LEFT JOIN users u ON f.createdBy = u.id" + + " WHERE f.deleted = 0 AND fr.deleted =0 "); + + if (args.containsKey("filename")) sql.append(" AND f.filename = :filename"); + + if (args.containsKey("refType")) sql.append(" AND fr.refType = :refType"); + + if (args.containsKey("refId")) sql.append(" AND fr.refId = :refId"); + + if (args.containsKey("startDate")) sql.append(" AND f.created >= :startDate"); + + if (args.containsKey("endDate")) sql.append(" AND f.created < :endDate"); + + if (args.containsKey("fileId")) sql.append(" AND f.id = :fileId"); + + + sql.append(" ORDER BY f.created DESC"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> searchFilesFromDocument(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " f.id," + + " f.filename," + + " f.filesize," + + " f.mimetype," + + " f.skey," + + " fr.refId," + + " fr.refType," + + " f.created," + + " u.fullname AS createdByName," + + " f.description" + + " FROM files_ref fr" + + " LEFT JOIN files f ON f.id = fr.fileId" + + " LEFT JOIN users u ON f.createdBy = u.id" + + " LEFT JOIN document_ref dr ON dr.documentId = fr.refId AND fr.refType = 'document'" + + " WHERE 1 = 1" + + " AND f.deleted = 0" + + " AND fr.deleted = 0" + + " AND dr.deleted = 0"); + + if (args != null) { + if (args.containsKey("filename")) sql.append(" AND f.filename = :filename"); + if (args.containsKey("refType")) sql.append(" AND fr.refType = :refType"); + if (args.containsKey("refId")) sql.append(" AND fr.refId = :refId"); + if (args.containsKey("startDate")) sql.append(" AND f.created >= :startDate"); + if (args.containsKey("endDate")) sql.append(" AND f.created < :endDate"); + if (args.containsKey("documentRefType")) sql.append(" AND dr.refType = :documentRefType"); + if (args.containsKey("documentRefId")) sql.append(" AND dr.refId = :documentRefId"); + } + + sql.append(" GROUP BY f.id" + + " ORDER BY f.created DESC"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + /** + * Delete FileRef by fileId, refId, refType, and skey + */ + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void deleteFile(Integer fileId, Integer refId, String refType, String skey) { + Map args = MapUtils.toHashMap("fileId", fileId, "refId", refId, "refType", refType, "skey", skey); + + jdbcDao.executeUpdate("DELETE FROM files_ref" + + " WHERE fileId = :fileId" + + " AND refId = :refId" + + " AND refType = :refType" + + " AND EXISTS (SELECT 1 FROM files WHERE id = files_ref.fileId AND skey = :skey)", + args); + jdbcDao.executeUpdate("DELETE FROM files_blob WHERE id = :fileId ",args); + } + + /** + * Scheduled daily job + * + * Delete all orphan (without any FileRef) Files and FileBlobs + */ + @Scheduled(cron = "0 0 0 * * ?") // everyday at 00:00:00 + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void deleteOrphanFiles() { + jdbcDao.executeUpdate("DELETE FROM files_blob WHERE NOT EXISTS (SELECT 1 FROM files_ref WHERE deleted = 0 AND fileId = files_blob.fileId)"); + jdbcDao.executeUpdate("DELETE FROM files WHERE NOT EXISTS (SELECT 1 FROM files_ref WHERE deleted = 0 AND fileId = files.id)"); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> getCustImageList() { + return jdbcDao.queryForList(" Select cp.* From cust_photo cp ", null); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> getOrderImageList() { + return jdbcDao.queryForList(" Select op.* From order_photo cp ", null); + } + + + +} diff --git a/src/main/java/com/ffii/tls/file/web/DeleteFileController.java b/src/main/java/com/ffii/tls/file/web/DeleteFileController.java new file mode 100644 index 0000000..6d2a978 --- /dev/null +++ b/src/main/java/com/ffii/tls/file/web/DeleteFileController.java @@ -0,0 +1,103 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file.web; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.file.FileRefType; +import com.ffii.tbms.file.service.FileService; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.order.service.OrderService; + +@Controller +@RequestMapping(value = "/file") +public class DeleteFileController extends AbstractController { + + @Autowired + private FileService fileService; + + @Autowired + private OrderService orderService; + + @RequestMapping(value = "/delete", method = { RequestMethod.GET, RequestMethod.POST }) + public String delete(Model model, + @RequestParam Integer fileId, @RequestParam Integer refId, @RequestParam String refType, @RequestParam String skey) + throws Exception { + + fileService.deleteFile(fileId, refId, refType, skey); + + if(refType.equals(FileRefType.MEASUREMENT_SHEET)){ + orderService.log(LogUtils.ACTION_DELETE, + refId, + MapUtils.toHashMap("fileId", fileId) + ); + }else if(refType.equals(FileRefType.ORDER)){ + orderService.log(LogUtils.ACTION_DELETE, + refId, + MapUtils.toHashMap("photoFileId", fileId) + ); + } + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "/multi-delete", method = { RequestMethod.GET, RequestMethod.POST }) + public String multiDelete(Model model, final HttpServletRequest request) + throws Exception { + + @SuppressWarnings("unchecked") + List> deleteRecord = + (List>)ServletRequestUtils.getJsonListParameter(request, "deleteRecord"); + + for(Map record: deleteRecord){ + int fileId = NumberUtils.intValue(record.get("fileId")); + int refId = NumberUtils.intValue(record.get("refId")); + String refType = record.get("refType").toString(); + String skey = record.get("skey").toString(); + + fileService.deleteFile(fileId, refId, refType, skey); + + if(refType.equals(FileRefType.MEASUREMENT_SHEET)){ + orderService.log(LogUtils.ACTION_DELETE, + refId, + MapUtils.toHashMap("fileId", fileId) + ); + }else if(refType.equals(FileRefType.ORDER)){ + orderService.log(LogUtils.ACTION_DELETE, + refId, + MapUtils.toHashMap("photoFileId", fileId) + ); + } + } + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/file/web/DownloadFileController.java b/src/main/java/com/ffii/tls/file/web/DownloadFileController.java new file mode 100644 index 0000000..d74e26c --- /dev/null +++ b/src/main/java/com/ffii/tls/file/web/DownloadFileController.java @@ -0,0 +1,203 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file.web; + +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.FileOutputStream; +import java.io.IOException; +import java.net.URLEncoder; +import java.text.DecimalFormat; +import java.util.Date; +import java.util.List; +import java.util.Map; +import java.util.zip.ZipEntry; +import java.util.zip.ZipOutputStream; + +import javax.imageio.ImageIO; +import javax.servlet.ServletOutputStream; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.DateUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.StringUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.tbms.file.File; +import com.ffii.tbms.file.FileBlob; +import com.ffii.tbms.file.service.FileService; +import java.awt.image.BufferedImage; + +@Controller +@RequestMapping(value = "/file") +public class DownloadFileController extends AbstractController { + + private boolean ZIP_NUMBERER = false; + + @Autowired + private FileService fileService; + + @RequestMapping(value = "/dl/{id}/{skey}/{filename}", method = RequestMethod.GET) + public void download(HttpServletResponse response, @RequestParam(defaultValue = "false") boolean dl, + @PathVariable int id, @PathVariable String skey) throws Exception { + + File file = fileService.findFileByIdAndKey(id, skey); + + if (file != null) { + FileBlob fileBlob = fileService.findFileBlobByFileId(id); + + response.reset(); + response.setContentType(file.getMimetype()); + response.setContentLength((int) file.getFilesize()); + response.setHeader("Content-Transfer-Encoding", "binary"); + response.setHeader("Content-Disposition", + String.format("%s; filename=\"%s\"", dl ? "attachment" : "inline", URLEncoder.encode(file.getFilename(), "UTF-8"))); + + ServletOutputStream out = response.getOutputStream(); + + try { + out.write(fileBlob.getBytes()); + out.flush(); + out.close(); + } catch (IOException e) { + logger.warn(e.getMessage()); + } finally { + out.close(); + } + } else { + logger.info("*** 400 BAD REQUEST ***"); + response.setStatus(HttpServletResponse.SC_BAD_REQUEST); + } + } + + @RequestMapping(value = "/dlz", produces = "application/zip", method = RequestMethod.GET) + public void downloadAsZip(HttpServletResponse response, + @RequestParam String filename, @RequestParam String ids, @RequestParam String skeys) throws IOException { + + filename += DateUtils.formatDate(new Date(), "_yyyy_MM_dd_HHmm", "") + ".zip"; + + response.setHeader("Content-Transfer-Encoding", "binary"); + response.setHeader("Content-Disposition", + String.format("%s; filename=\"%s\"", "attachment", response.encodeURL(filename))); + + DecimalFormat df00 = new DecimalFormat("00"); + + ZipOutputStream zipOutputStream = new ZipOutputStream(response.getOutputStream()); + + String[] idsA = StringUtils.split(ids, ','); + String[] skeysA = StringUtils.split(skeys, ','); + + int filePrefixIdx = 1; + + for (int i = 0; i < idsA.length; i++) { + int id = NumberUtils.intValue(idsA[i]); + String skey = skeysA[i]; + + File file = fileService.findFileByIdAndKey(id, skey); + + if (file == null) { + logger.warn("*** file is null, id = " + id + ", skey = " + skey); + } else { + FileBlob fileBlob = fileService.findFileBlobByFileId(id); + + if (fileBlob == null) { + logger.warn("*** fileBlob is null, id = " + id + ", skey = " + skey); + } else { + zipOutputStream.putNextEntry(new ZipEntry(ZIP_NUMBERER ? (df00.format(filePrefixIdx++) + "_" + file.getFilename()) + : file.getFilename())); + zipOutputStream.write(fileBlob.getBytes()); + zipOutputStream.closeEntry(); + } + } + } + zipOutputStream.flush(); + zipOutputStream.close(); + } + + @RequestMapping(value = "/thumbnail/{id}/{skey}/{filename}", method = RequestMethod.GET) + public void thumbnail(HttpServletResponse response, Model model, @RequestParam(defaultValue = "false") boolean dl, + @PathVariable int id, @PathVariable String skey) throws IOException { + + File file = fileService.findFileByIdAndKey(id, skey); + + if (file != null) { + FileBlob fileBlob = fileService.findFileBlobByFileId(id); + + response.reset(); + response.setContentType(file.getMimetype()); + // response.setContentLength((int) file.getFilesize()); + response.setHeader("Content-Transfer-Encoding", "binary"); + response.setHeader("Content-Disposition", String.format("%s; filename=\"%s\"", dl ? "attachment" : "inline", + response.encodeURL(file.getFilename()))); + + int limit = 500; + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + int width = image.getWidth(); + int height = image.getHeight(); + if (width > height) { + if (width > limit) { + height = height * limit / width; + width = limit; + } + } else { + if (height > limit) { + width = width * limit / height; + height = limit; + } + } + image = scale(image, width, height); + ByteArrayOutputStream tmp = new ByteArrayOutputStream(); + ImageIO.write(image, "jpg", tmp); + tmp.close(); + response.setContentLength((int) tmp.size()); + + ServletOutputStream out = response.getOutputStream(); + + try { + out.write(tmp.toByteArray()); + out.flush(); + out.close(); + } catch (IOException e) { + logger.warn(e.getMessage()); + } finally { + out.close(); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } + } else { + logger.info("*** 400 BAD REQUEST ***"); + response.setStatus(HttpServletResponse.SC_BAD_REQUEST); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + } + + static BufferedImage scale(BufferedImage originalImage, int w, int h) { + BufferedImage img = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB); + int x, y; + int ww = originalImage.getWidth(); + int hh = originalImage.getHeight(); + for (x = 0; x < w; x++) { + for (y = 0; y < h; y++) { + int col = originalImage.getRGB(x * ww / w, y * hh / h); + img.setRGB(x, y, col); + } + } + return img; + } + +} diff --git a/src/main/java/com/ffii/tls/file/web/FileJsonController.java b/src/main/java/com/ffii/tls/file/web/FileJsonController.java new file mode 100644 index 0000000..7f37881 --- /dev/null +++ b/src/main/java/com/ffii/tls/file/web/FileJsonController.java @@ -0,0 +1,122 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file.web; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.ServletRequestUtils; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.StringUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.file.File; +import com.ffii.tbms.file.service.FileService; +import com.ffii.tbms.order.Order; +import com.ffii.tbms.order.service.OrderService; + +@Controller +@RequestMapping(value = "/file") +public class FileJsonController extends AbstractController { + + @Autowired + private FileService fileService; + + @Autowired + private OrderService orderService; + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request, @RequestParam(required = false) String refType, + @RequestParam(required = false) Integer refId) throws ServletRequestBindingException { + + Map args = new HashMap(); + CriteriaUtils.addDate(request, args, "startDate"); + CriteriaUtils.addDateTo(request, args, "endDate"); + + List> records = new ArrayList<>(); + + String documentRefType = ServletRequestUtils.getStringParameter(request, "documentRefType"); + Integer documentRefId = ServletRequestUtils.getIntParameter(request, "documentRefId"); + if (StringUtils.isNotEmpty(documentRefType) && documentRefId != null) { + args.put("documentRefType", documentRefType); + args.put("documentRefId", documentRefId); + + records = fileService.searchFilesFromDocument(args); + } else if (StringUtils.isNotEmpty(refType) && refId != null) { + args.put(Params.REF_TYPE, refType); + args.put(Params.REF_ID, refId); + + records = fileService.searchFiles(args); + } + + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + @RequestMapping(value = "/list-order.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listOrderJson(Model model, HttpServletRequest request, @RequestParam(required = false) String refType, + @RequestParam(required = false) Integer refId) throws ServletRequestBindingException { + + Map args = new HashMap(); + List> records = new ArrayList<>(); + args.put("refType", refType); + args.put("refId", refId); + records = fileService.searchFiles(args); + + Order order = orderService.find(refId); + + if(order.getFileId() != null) + records.addAll(fileService.searchFiles(MapUtils.toHashMap("fileId",order.getFileId()))); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("title", order.getType()+order.getCode()); + + return JsonView.NAME; + } + + @RequestMapping(value = "/update", method = RequestMethod.POST) + public String update(Model model, HttpServletResponse response, + @RequestParam int id, @RequestParam String skey, @RequestParam String filename, + @RequestParam(defaultValue = StringUtils.EMPTY) String description) { + + File file = fileService.findFileByIdAndKey(id, skey); + + if (file != null) { + + file.setFilename(filename); + file.setDescription(description); + fileService.saveFile(file); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/file/web/UploadFileController.java b/src/main/java/com/ffii/tls/file/web/UploadFileController.java new file mode 100644 index 0000000..f070eaf --- /dev/null +++ b/src/main/java/com/ffii/tls/file/web/UploadFileController.java @@ -0,0 +1,513 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.file.web; + +import java.awt.image.BufferedImage; +import java.io.ByteArrayInputStream; +import java.io.IOException; +import java.nio.file.Files; +import java.util.List; +import java.util.Map; + +import javax.imageio.ImageIO; +import javax.servlet.http.HttpServletRequest; + +import com.fasterxml.jackson.databind.JsonSerializable; +import com.fasterxml.jackson.databind.ser.std.JsonValueSerializer; +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.FileUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.StringUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.AbstractView; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.common.MaterialBand; +import com.ffii.tbms.common.service.MaterialService; +import com.ffii.tbms.file.File; +import com.ffii.tbms.file.FileBlob; +import com.ffii.tbms.file.FileRef; +import com.ffii.tbms.file.FileRefType; +import com.ffii.tbms.file.service.FileService; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.order.Order; +import com.ffii.tbms.order.service.OrderService; + +import org.apache.commons.io.IOUtils; +import org.apache.commons.lang3.RandomStringUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.multipart.MultipartFile; + +/** + * Upload File Controller + * + * @see File + * @see FileBlob + * @see FileRef + */ +@Controller +@RequestMapping(value = "/file") +public class UploadFileController extends AbstractController { + + @Autowired + private SettingsService settingsService; + + @Autowired + private FileService fileService; + + @Autowired + private OrderService orderService; + + @Autowired + private MaterialService materialService; + + private static final boolean OVERWRITE_SAME_FILENAME = false; + + private static final int DEFAULT_UPLOAD_MAX_FILE_SIZE_MB = 50; + + @RequestMapping(value = "/ul", method = RequestMethod.POST) + public String uploadFile(HttpServletRequest request, Model model, + @RequestParam int refId, @RequestParam String refType, @RequestParam(defaultValue = StringUtils.EMPTY) String refCode, + @RequestParam MultipartFile multipartFile) throws Exception { + + // get file upload max file size setting + int uploadMaxFileSize = settingsService.getInt("FILE.upload.maxFileSize", DEFAULT_UPLOAD_MAX_FILE_SIZE_MB) * 1024 * 1024; + + Boolean success = Boolean.TRUE; + + // only proceed if multipartFile is not null, and has file size + if (multipartFile != null && multipartFile.getSize() > 0 && multipartFile.getSize() <= uploadMaxFileSize) { + + // DEBUG LOG + logger.info("multipartFile.getSize() = " + multipartFile.getSize()); + + File file = new File(); + file.setFilename(multipartFile.getOriginalFilename()); + // file.setMimetype(multipartFile.getContentType()); + file.setMimetype(FileUtils.guessMimetype(file.getFilename())); + file.setFilesize(multipartFile.getSize()); + file.setDescription(ServletRequestUtils.getTrimmedStringParameter(request, "description")); + + FileBlob fileBlob = new FileBlob(); + fileBlob.setBytes(multipartFile.getBytes()); + + FileRef fileRef = new FileRef(); + fileRef.setRefId(refId); + fileRef.setRefType(refType); + fileRef.setRefCode(refCode); + + // get height and width if mimetype is png or jpeg + if (AbstractView.CONTENT_TYPE_PNG.equals(file.getMimetype()) || AbstractView.CONTENT_TYPE_JPEG.equals(file.getMimetype())) { + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + if (image != null) { + file.setImageHeight(image.getHeight()); + file.setImageWidth(image.getWidth()); + } + } + + if (OVERWRITE_SAME_FILENAME) { + // search for existing file(s) with the same refType, refId, and filename + List> existingFiles = fileService.searchFiles( + MapUtils.toHashMap("refType", refType, "refId", refId, "filename", file.getFilename())); + + // delete them if found + for (Map existingFile : existingFiles) { + fileService.deleteFile((Integer) existingFile.get("id"), (Integer) existingFile.get("refId"), + (String) existingFile.get("refType"), (String) existingFile.get("skey")); + } + } + + // create UserFile + file.setSkey(RandomStringUtils.randomAlphanumeric(16)); + fileService.saveFile(file); + + // create UserFileBlob + fileBlob.setFileId(file.getId()); + fileService.saveFileBlob(fileBlob); + + // create UserFileRef + fileRef.setFileId(file.getId()); + fileService.saveFileRef(fileRef); + + if(refType.equals(FileRefType.ORDER)){ + orderService.log(LogUtils.ACTION_CREATE, + refId, + MapUtils.toHashMap("photoFileId", file.getId(), "filename",file.getFilename())); + } + + } else { + success = Boolean.FALSE; + + // if not success, return msg to client + model.addAttribute(Params.MSG, getMessageSourceAccessor().getMessage("Upload Failed")); + } + + model.addAttribute(Params.SUCCESS, success); + + return JsonView.NAME; + } + + + @RequestMapping(value = "/files/ul", method = RequestMethod.POST) + public String uploadFiles(HttpServletRequest request, Model model,@RequestParam String refType, + @RequestParam int refId, @RequestParam(defaultValue = StringUtils.EMPTY) String refCode, + @RequestParam List multipartFiles) throws ServletRequestBindingException, IOException { + + // get file upload max file size setting + int uploadMaxFileSize = settingsService.getInt("FILE.upload.maxFileSize", DEFAULT_UPLOAD_MAX_FILE_SIZE_MB) * 1024 * 1024; + + for(MultipartFile multipartFile: multipartFiles){ + + if (multipartFile != null && multipartFile.getSize() > 0 && multipartFile.getSize() <= uploadMaxFileSize) { + logger.info("file size : "+ multipartFile.getSize()); + File file = new File(); + file.setFilename(multipartFile.getOriginalFilename()); + // file.setMimetype(multipartFile.getContentType()); + file.setMimetype(FileUtils.guessMimetype(file.getFilename())); + file.setFilesize(multipartFile.getSize()); + file.setDescription(ServletRequestUtils.getTrimmedStringParameter(request, "description")); + + FileBlob fileBlob = new FileBlob(); + fileBlob.setBytes(multipartFile.getBytes()); + + FileRef fileRef = new FileRef(); + fileRef.setRefId(refId); + fileRef.setRefType(refType); + fileRef.setRefCode(refCode); + + // get height and width if mimetype is png or jpeg + if (AbstractView.CONTENT_TYPE_PNG.equals(file.getMimetype()) || AbstractView.CONTENT_TYPE_JPEG.equals(file.getMimetype())) { + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + if (image != null) { + file.setImageHeight(image.getHeight()); + file.setImageWidth(image.getWidth()); + } + } + + if (OVERWRITE_SAME_FILENAME) { + // search for existing file(s) with the same refType, refId, and filename + List> existingFiles = fileService.searchFiles( + MapUtils.toHashMap("refType", refType, "refId", refId, "filename", file.getFilename())); + + // delete them if found + for (Map existingFile : existingFiles) { + fileService.deleteFile((Integer) existingFile.get("id"), (Integer) existingFile.get("refId"), + (String) existingFile.get("refType"), (String) existingFile.get("skey")); + } + } + + // create UserFile + file.setSkey(RandomStringUtils.randomAlphanumeric(16)); + fileService.saveFile(file); + + // create UserFileBlob + fileBlob.setFileId(file.getId()); + fileService.saveFileBlob(fileBlob); + + // create UserFileRef + fileRef.setFileId(file.getId()); + fileService.saveFileRef(fileRef); + + if(refType.equals(FileRefType.ORDER)){ + orderService.log(LogUtils.ACTION_CREATE, + refId, + MapUtils.toHashMap("photoFileId", file.getId(), "filename",file.getFilename())); + } + logger.info("file done : "+ multipartFile.getName()); + + }else{ + model.addAttribute(Params.SUCCESS, false); + return JsonView.NAME; + } + + } + + model.addAttribute(Params.SUCCESS, true); + + return JsonView.NAME; + } + + @RequestMapping(value = "/measurement-sheet/ul", method = RequestMethod.POST) + public String uploadMeasurementSheetFile(HttpServletRequest request, Model model, + @RequestParam int orderId, @RequestParam MultipartFile multipartFile) throws Exception { + + Order order = orderService.find(orderId); + String refType = FileRefType.MEASUREMENT_SHEET; + String refCode = order.getCustId() + ""; + Integer refId = orderId; + + // get file upload max file size setting + int uploadMaxFileSize = settingsService.getInt("FILE.upload.maxFileSize", DEFAULT_UPLOAD_MAX_FILE_SIZE_MB) * 1024 * 1024; + + Boolean success = Boolean.TRUE; + + // only proceed if multipartFile is not null, and has file size + if (multipartFile != null && multipartFile.getSize() > 0 && multipartFile.getSize() <= uploadMaxFileSize) { + + // DEBUG LOG + logger.info("multipartFile.getSize() = " + multipartFile.getSize()); + + File file = new File(); + file.setFilename(multipartFile.getOriginalFilename()); + // file.setMimetype(multipartFile.getContentType()); + file.setMimetype(FileUtils.guessMimetype(file.getFilename())); + file.setFilesize(multipartFile.getSize()); + file.setDescription(ServletRequestUtils.getTrimmedStringParameter(request, "description")); + + FileBlob fileBlob = new FileBlob(); + fileBlob.setBytes(multipartFile.getBytes()); + + FileRef fileRef = new FileRef(); + fileRef.setRefId(refId); + fileRef.setRefType(refType); + fileRef.setRefCode(refCode); + + // get height and width if mimetype is png or jpeg + if (AbstractView.CONTENT_TYPE_PNG.equals(file.getMimetype()) || AbstractView.CONTENT_TYPE_JPEG.equals(file.getMimetype())) { + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + if (image != null) { + file.setImageHeight(image.getHeight()); + file.setImageWidth(image.getWidth()); + } + } + + if (OVERWRITE_SAME_FILENAME) { + // search for existing file(s) with the same refType, refId, and filename + List> existingFiles = fileService.searchFiles( + MapUtils.toHashMap("refType", refType, "refId", refId, "filename", file.getFilename())); + + // delete them if found + for (Map existingFile : existingFiles) { + fileService.deleteFile((Integer) existingFile.get("id"), (Integer) existingFile.get("refId"), + (String) existingFile.get("refType"), (String) existingFile.get("skey")); + } + } + + // create UserFile + file.setSkey(RandomStringUtils.randomAlphanumeric(16)); + fileService.saveFile(file); + + // create UserFileBlob + fileBlob.setFileId(file.getId()); + fileService.saveFileBlob(fileBlob); + + // create UserFileRef + fileRef.setFileId(file.getId()); + fileService.saveFileRef(fileRef); + + order.setFileId(file.getId()); + orderService.saveOrUpdate(order); + orderService.log(LogUtils.ACTION_CREATE, + order.getId(), + MapUtils.toHashMap("fileId", order.getFileId(), "filename", file.getFilename())); + } else { + success = Boolean.FALSE; + + // if not success, return msg to client + model.addAttribute(Params.MSG, getMessageSourceAccessor().getMessage("Upload Failed")); + } + + model.addAttribute(Params.SUCCESS, success); + + return JsonView.NAME; + } + + @RequestMapping(value = "/band/icon/ul", method = { RequestMethod.GET, RequestMethod.POST }) + public String uploadBandIconFile(HttpServletRequest request, Model model, + @RequestParam int bandId, @RequestParam MultipartFile multipartFile) throws Exception { + + MaterialBand band = materialService.findBand(bandId); + String refType = FileRefType.BAND_ICON; + Integer refId = bandId; + + // get file upload max file size setting + int uploadMaxFileSize = settingsService.getInt("FILE.upload.maxFileSize", DEFAULT_UPLOAD_MAX_FILE_SIZE_MB) * 1024 * 1024; + + Boolean success = Boolean.TRUE; + + // only proceed if multipartFile is not null, and has file size + if (multipartFile != null && multipartFile.getSize() > 0 && multipartFile.getSize() <= uploadMaxFileSize) { + + // DEBUG LOG + logger.info("multipartFile.getSize() = " + multipartFile.getSize()); + + File file = new File(); + file.setFilename(multipartFile.getOriginalFilename()); + // file.setMimetype(multipartFile.getContentType()); + file.setMimetype(FileUtils.guessMimetype(file.getFilename())); + file.setFilesize(multipartFile.getSize()); + file.setDescription(ServletRequestUtils.getTrimmedStringParameter(request, "description")); + + FileBlob fileBlob = new FileBlob(); + fileBlob.setBytes(multipartFile.getBytes()); + + FileRef fileRef = new FileRef(); + fileRef.setRefId(refId); + fileRef.setRefType(refType); + + // get height and width if mimetype is png or jpeg + if (AbstractView.CONTENT_TYPE_PNG.equals(file.getMimetype()) || AbstractView.CONTENT_TYPE_JPEG.equals(file.getMimetype())) { + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + if (image != null) { + file.setImageHeight(image.getHeight()); + file.setImageWidth(image.getWidth()); + } + } + + + // search for existing file(s) with the same refType, refId, and filename + List> existingFiles = fileService.searchFiles( + MapUtils.toHashMap("refType", refType, "refId", refId)); + + // delete them if found + for (Map existingFile : existingFiles) { + fileService.deleteFile((Integer) existingFile.get("id"), (Integer) existingFile.get("refId"), + (String) existingFile.get("refType"), (String) existingFile.get("skey")); + } + + + // create UserFile + file.setSkey(RandomStringUtils.randomAlphanumeric(16)); + fileService.saveFile(file); + + // create UserFileBlob + fileBlob.setFileId(file.getId()); + fileService.saveFileBlob(fileBlob); + + // create UserFileRef + fileRef.setFileId(file.getId()); + fileService.saveFileRef(fileRef); + + band.setFileId(file.getId()); + materialService.saveOrUpdateBand(band); + } else { + success = Boolean.FALSE; + + // if not success, return msg to client + model.addAttribute(Params.MSG, getMessageSourceAccessor().getMessage("Upload Failed")); + } + + model.addAttribute(Params.SUCCESS, success); + + return JsonView.NAME; + } + + @RequestMapping(value = "/load-image", method = { RequestMethod.GET, RequestMethod.POST }) + private String loadImage(){ + + List> custList = fileService.getCustImageList(); + List> orderList = fileService.getOrderImageList(); + + String ignored = ""; + + for(Map item: custList ){ + int custId = NumberUtils.intValue(item.get("id"), 0); + if(custId == 0) { + ignored = ignored+"\n CustId:"+item.get("id")+", photo:"+item.get("cust_photo"); + continue; + } + + String[] photos = item.get("cust_photo").toString().trim().split("::"); + for(String filename: photos){ + String path = this.getClass().getClassLoader().getResource("").getPath() + "../report/"+filename; + if(path != null){ + java.io.File file = new java.io.File(path); + try { + createFile(custId, FileRefType.CUSTOMER, file, filename); + } catch (IOException e) { + ignored = ignored+"\n CustId:"+item.get("id")+", photo:"+filename; + } + } + } + } + + for(Map item: orderList){ + int orderId = NumberUtils.intValue(item.get("id"), 0); + if(orderId == 0) { + ignored = ignored+"\n OrderId:"+item.get("id")+", photo:"+item.get("order_photo"); + continue; + } + + String[] ophotos = item.get("order_photo").toString().trim().split("::"); + for(String filename: ophotos){ + String path = this.getClass().getClassLoader().getResource("").getPath() + "../report/"+filename; + if(path != null){ + java.io.File file = new java.io.File(path); + try { + createFile(orderId, FileRefType.ORDER, file, filename); + } catch (IOException e) { + ignored = ignored+"\n OrderId:"+item.get("id")+", photo:"+filename; + } + } + } + } + + logger.info(ignored); + + return JsonView.NAME; + } + + private void createFile(int refId, String refType, java.io.File f, String filename) throws IOException{ + byte[] fileContent = Files.readAllBytes(f.toPath()); + + File file = new File(); + file.setFilename(filename); + // file.setMimetype(multipartFile.getContentType()); + file.setMimetype(FileUtils.guessMimetype(filename)); + file.setFilesize(fileContent.length); + + FileBlob fileBlob = new FileBlob(); + fileBlob.setBytes(fileContent); + + FileRef fileRef = new FileRef(); + fileRef.setRefId(refId); + fileRef.setRefType(refType); + + // get height and width if mimetype is png or jpeg + if (AbstractView.CONTENT_TYPE_PNG.equals(file.getMimetype()) || AbstractView.CONTENT_TYPE_JPEG.equals(file.getMimetype())) { + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + if (image != null) { + file.setImageHeight(image.getHeight()); + file.setImageWidth(image.getWidth()); + } + } + + // search for existing file(s) with the same refType, refId, and filename + List> existingFiles = fileService.searchFiles( + MapUtils.toHashMap("refType", refType, "refId", refId)); + + // delete them if found + for (Map existingFile : existingFiles) { + fileService.deleteFile((Integer) existingFile.get("id"), (Integer) existingFile.get("refId"), + (String) existingFile.get("refType"), (String) existingFile.get("skey")); + } + + // create UserFile + file.setSkey(RandomStringUtils.randomAlphanumeric(16)); + fileService.saveFile(file); + + // create UserFileBlob + fileBlob.setFileId(file.getId()); + fileService.saveFileBlob(fileBlob); + + // create UserFileRef + fileRef.setFileId(file.getId()); + fileService.saveFileRef(fileRef); + } + + +} diff --git a/src/main/java/com/ffii/tls/log/LogUtils.java b/src/main/java/com/ffii/tls/log/LogUtils.java new file mode 100644 index 0000000..1b266f4 --- /dev/null +++ b/src/main/java/com/ffii/tls/log/LogUtils.java @@ -0,0 +1,83 @@ +package com.ffii.tbms.log; + +import java.math.BigDecimal; +import java.util.HashMap; +import java.util.Map; + +import com.fasterxml.jackson.databind.ObjectMapper; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; + + +public class LogUtils{ + + public static final String DIFF = "diff"; + public static final String ADD = "add"; + public static final String DEL = "del"; + public static final String SAME = "same"; + + public static final String ACTION_CREATE = "Create"; + public static final String ACTION_UPDATE = "Update"; + public static final String ACTION_DELETE = "Delete"; + + public static Map objectToMap(Object obj){ + ObjectMapper mapper = new ObjectMapper(); + Map map = mapper.convertValue(obj, Map.class); + return map; + } + + public static Map compare(Object newObj, Object oldObj){ + Map diff = new HashMap<>(); + Map add = new HashMap<>(); + Map same = new HashMap<>(); + + Map newMap = filter(objectToMap(newObj)); + Map oldMap = filter(objectToMap(oldObj)); + + for (Map.Entry entry : newMap.entrySet()){ + if(oldMap.containsKey(entry.getKey())){ + if(isNullDiff(entry.getValue(), oldMap.get(entry.getKey()))){ + if(isBigDecimalDiff(entry.getValue(), oldMap.get(entry.getKey()))){ + diff.put(entry.getKey(), entry.getValue()); + }else{ + same.put(entry.getKey(), entry.getValue()); + } + }else{ + same.put(entry.getKey(), entry.getValue()); + } + oldMap.remove(entry.getKey()); + }else{ + add.put(entry.getKey(), entry.getValue()); + } + } + return MapUtils.toHashMap(DIFF, diff, + ADD, add, + DEL, oldMap, + SAME, same); + } + + private static boolean isBigDecimalDiff(Object newObj, Object oldObj){ + if(newObj instanceof BigDecimal){ + BigDecimal n = NumberUtils.toDecimal(newObj); + BigDecimal o = NumberUtils.toDecimal(oldObj); + return n.compareTo(o) != 0; + } + return true; + } + + private static boolean isNullDiff(Object newObj, Object oldObj){ + if(oldObj == null && newObj == null) return false; + if(oldObj == null || newObj == null) return true; + return !oldObj.equals(newObj); + } + + public static Map filter(Map map){ + map.remove("created"); + map.remove("modified"); + map.remove("createdBy"); + map.remove("modifiedBy"); + map.remove("versionId"); + return map; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/log/ScheduledTaskLog.java b/src/main/java/com/ffii/tls/log/ScheduledTaskLog.java new file mode 100644 index 0000000..db24679 --- /dev/null +++ b/src/main/java/com/ffii/tls/log/ScheduledTaskLog.java @@ -0,0 +1,93 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.log; + +import java.util.Date; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "scheduled_task_log") +public class ScheduledTaskLog extends BaseEntity { + + private static final long serialVersionUID = -7423670833004156679L; + + @Column(columnDefinition = "varchar(40)", nullable = false) + private String module; + + @Column(columnDefinition = "varchar(50)", nullable = false) + private String task; + + @Column(columnDefinition = "datetime", nullable = false) + private Date startDateTime; + + @Column(columnDefinition = "datetime", nullable = false) + private Date endDateTime; + + @Column(columnDefinition = "varchar(10)", nullable = false) + private String result; + + @Column(columnDefinition = "TEXT") + private String remarks; + + public String getModule() { + return module; + } + + public void setModule(String module) { + this.module = module; + } + + public String getTask() { + return task; + } + + public void setTask(String task) { + this.task = task; + } + + public Date getStartDateTime() { + return startDateTime; + } + + public void setStartDateTime(Date startDateTime) { + this.startDateTime = startDateTime; + } + + public Date getEndDateTime() { + return endDateTime; + } + + public void setEndDateTime(Date endDateTime) { + this.endDateTime = endDateTime; + } + + public String getResult() { + return result; + } + + public void setResult(String result) { + this.result = result; + } + + public String getRemarks() { + return remarks; + } + + public void setRemarks(String remarks) { + this.remarks = remarks; + } + +} diff --git a/src/main/java/com/ffii/tls/log/UsageLog.java b/src/main/java/com/ffii/tls/log/UsageLog.java new file mode 100644 index 0000000..12792a0 --- /dev/null +++ b/src/main/java/com/ffii/tls/log/UsageLog.java @@ -0,0 +1,17 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.log; + +public class UsageLog { + + public static final String TYPE_REPORT = "report"; + +} diff --git a/src/main/java/com/ffii/tls/log/dao/ScheduledTaskLogDao.java b/src/main/java/com/ffii/tls/log/dao/ScheduledTaskLogDao.java new file mode 100644 index 0000000..9459f0c --- /dev/null +++ b/src/main/java/com/ffii/tls/log/dao/ScheduledTaskLogDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.log.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.log.ScheduledTaskLog; + +@Repository +public class ScheduledTaskLogDao extends HibernateDao { + + @Autowired + public ScheduledTaskLogDao(SessionFactory sessionFactory) { + super(ScheduledTaskLog.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/log/service/AuditLogService.java b/src/main/java/com/ffii/tls/log/service/AuditLogService.java new file mode 100644 index 0000000..61d4229 --- /dev/null +++ b/src/main/java/com/ffii/tls/log/service/AuditLogService.java @@ -0,0 +1,99 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.log.service; + +import java.util.Date; +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.BaseEntity; +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.web.AbstractService; + +/** + * @author Patrick + */ +@Service +public class AuditLogService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + private static final String SQL_INSERT_AUDIT_LOG = "INSERT INTO audit_log " + +" (`tableName`, `recordId`, `modifiedBy`, `modified`, `actionStr`, `dataStr`, `refId`, `refType`) " + + "VALUES (:tableName, :recordId, :modifiedBy, :modified, :actionStr, :dataStr, :refId, :refType)"; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int save(String tableName, int recordId, Integer modifiedBy, Date modified, String actionStr, String dataStr) { + return jdbcDao.executeUpdate(SQL_INSERT_AUDIT_LOG, + MapUtils.toHashMap("tableName", tableName, "recordId", recordId, + "modifiedBy", modifiedBy, "modified", modified, + "actionStr", actionStr, "dataStr", dataStr, + "refId",null, "refType", null)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int save(String tableName, int recordId, Integer modifiedBy, Date modified, String actionStr, + String dataStr, int refId, String refType) { + return jdbcDao.executeUpdate(SQL_INSERT_AUDIT_LOG, + MapUtils.toHashMap("tableName", tableName, "recordId", recordId, + "modifiedBy", modifiedBy, "modified", modified, + "actionStr", actionStr, "dataStr", dataStr, + "refId",refId, "refType", refType)); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> searchOrderLog(Map args) { + + final StringBuilder sql = new StringBuilder(" SELECT ad.*, " + +" u.fullname AS userName " + +" FROM audit_log ad " + +" LEFT JOIN users u ON u.id = ad.modifiedBy " + +" WHERE (ad.tableName = 'orders' AND ad.recordId = :orderId) " + +" OR (ad.refType = 'orders' AND ad.refId = :orderId ) "); + + if(args != null){ + if(args.containsKey("action")) sql.append(" AND ad.actionStr = :action "); + } + + sql.append(" ORDER BY ad.modified DESC "); + + if (args != null) { + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> search(String tableName, Integer recordId) { + + String sql = "SELECT * FROM audit_log WHERE tableName = :tableName AND recordId = :recordId ORDER BY modified"; + + return jdbcDao.queryForList(sql, MapUtils.toHashMap("tableName", tableName, "recordId", recordId)); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> getTables() { + return jdbcDao.queryForList("SELECT DISTINCT tableName FROM audit_log;", null); + } + + + +} diff --git a/src/main/java/com/ffii/tls/log/service/ScheduledTaskLogService.java b/src/main/java/com/ffii/tls/log/service/ScheduledTaskLogService.java new file mode 100644 index 0000000..78979a1 --- /dev/null +++ b/src/main/java/com/ffii/tls/log/service/ScheduledTaskLogService.java @@ -0,0 +1,86 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.log.service; + +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.log.ScheduledTaskLog; +import com.ffii.tbms.log.dao.ScheduledTaskLogDao; + +@Service +public class ScheduledTaskLogService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private ScheduledTaskLogDao scheduledTaskLogDao; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(ScheduledTaskLog instance) { + return scheduledTaskLogDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public ScheduledTaskLog find(Integer id) { + return scheduledTaskLogDao.find(id); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " *" + + " FROM scheduled_task_log" + + " WHERE deleted = 0"); + + handleSearchArgs(sql, args); + + sql.append(" ORDER BY startDateTime DESC"); + + if (args != null) { + if (args.containsKey("start") && args.containsKey("limit")) sql.append(" LIMIT :start, :limit"); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map searchTotalCount(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " COUNT(*) AS count" + + " FROM scheduled_task_log" + + " WHERE deleted = 0"); + + handleSearchArgs(sql, args); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + public void handleSearchArgs(StringBuilder sql, Map args) { + if (args != null) { + if (args.containsKey("module")) sql.append(" AND module = :module"); + if (args.containsKey("task")) sql.append(" AND task LIKE :task"); + if (args.containsKey("dateFrom")) sql.append(" AND startDateTime >= :dateFrom"); + if (args.containsKey("dateTo")) sql.append(" AND startDateTime < :dateTo"); + if (args.containsKey("result")) sql.append(" AND result = :result"); + } + } +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/log/service/UsageLogService.java b/src/main/java/com/ffii/tls/log/service/UsageLogService.java new file mode 100644 index 0000000..4d397ff --- /dev/null +++ b/src/main/java/com/ffii/tls/log/service/UsageLogService.java @@ -0,0 +1,43 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.log.service; + +import java.util.Date; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.web.AbstractService; + +/** + * @author Patrick + */ +@Service +public class UsageLogService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + private static final String SQL_INSERT_USAGE_LOG = "INSERT INTO usage_log (`type`, `name`, `userId`, `datetime`, `params`)" + + " VALUES (:type, :name, :userId, :datetime, :params)"; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int save(String type, String name, int userId, Date datetime, String params) { + return jdbcDao.executeUpdate(SQL_INSERT_USAGE_LOG, + MapUtils.toHashMap("type", type, "name", name, "userId", userId, + "datetime", datetime, "params", params)); + } + +} diff --git a/src/main/java/com/ffii/tls/log/web/AuditLogController.java b/src/main/java/com/ffii/tls/log/web/AuditLogController.java new file mode 100644 index 0000000..fb867d1 --- /dev/null +++ b/src/main/java/com/ffii/tls/log/web/AuditLogController.java @@ -0,0 +1,59 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.log.web; + +import java.util.HashMap; +import java.util.Map; + +import javax.persistence.criteria.CriteriaBuilder; +import javax.servlet.http.HttpServletRequest; + +import org.hibernate.Criteria; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.log.service.AuditLogService; + +@Controller +@RequestMapping(value = "/common/log") +public class AuditLogController extends AbstractController { + + @Autowired + private AuditLogService service; + + @RequestMapping(value = "/order.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String orderLogList(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER")) { + Map args = new HashMap<>(); + CriteriaUtils.addInteger(request, args, "orderId"); + CriteriaUtils.addStringExact(request, args, "action"); + + CriteriaUtils.addInteger(request, args, "start"); + CriteriaUtils.addInteger(request, args, "limit"); + + model.addAttribute(Params.RECORDS, service.searchOrderLog(args)); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.MSG, "No Auth"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } +} diff --git a/src/main/java/com/ffii/tls/log/web/ScheduledTaskLogController.java b/src/main/java/com/ffii/tls/log/web/ScheduledTaskLogController.java new file mode 100644 index 0000000..3daa4e5 --- /dev/null +++ b/src/main/java/com/ffii/tls/log/web/ScheduledTaskLogController.java @@ -0,0 +1,67 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.log.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.log.service.ScheduledTaskLogService; + +@Controller +@RequestMapping(value = "/admin/scheduled-task-log") +public class ScheduledTaskLogController extends AbstractController { + + @Autowired + private ScheduledTaskLogService scheduledTaskLogService; + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String jsonList(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("ADMIN")) { + Map args = new HashMap(); + CriteriaUtils.addString(request, args, "module"); + CriteriaUtils.addStringLike(request, args, "task"); + CriteriaUtils.addDate(request, args, "dateFrom"); + CriteriaUtils.addDateTo(request, args, "dateTo"); + CriteriaUtils.addString(request, args, "result"); + + CriteriaUtils.addInteger(request, args, "start"); + CriteriaUtils.addInteger(request, args, "limit"); + + List> records = scheduledTaskLogService.search(args); + Map countData = scheduledTaskLogService.searchTotalCount(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("total", countData.get("count")); + model.addAttribute(Params.SUCCESS, records != null); + } else { + model.addAttribute(Params.MSG, "No Auth"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/mail/MailUtils.java b/src/main/java/com/ffii/tls/mail/MailUtils.java new file mode 100644 index 0000000..766a8b8 --- /dev/null +++ b/src/main/java/com/ffii/tls/mail/MailUtils.java @@ -0,0 +1,31 @@ +package com.ffii.tbms.mail; + +public class MailUtils { + + public static final String TEMP_SUBJECT = "[INVOICE] Order No.: {$orderNo}"; + public static final String TEMP_BODY = + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "Dear Customer,

" + + "
" + + "
" + +"" + +" Order No.: {$orderNo}
" + +"
" + +" Order Date: {$orderDate}
" + +"
" + +" Order Amount: {$amount}
" + +"

Please find attached invoice for " + +"more details, Thank you.

" + + "Yours faithfully,

" + + "{$companyName}
" + + " " + + " "; + +} diff --git a/src/main/java/com/ffii/tls/mail/service/MailService.java b/src/main/java/com/ffii/tls/mail/service/MailService.java new file mode 100644 index 0000000..492daed --- /dev/null +++ b/src/main/java/com/ffii/tls/mail/service/MailService.java @@ -0,0 +1,111 @@ +/******************************************************************************* + * Copyright 2018 2Fi Business Solutions Ltd. + * + * This code is part of the KONE project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.mail.service; + +import java.io.File; +import java.io.UnsupportedEncodingException; +import java.util.Map; +import javax.mail.internet.InternetAddress; + +import com.ffii.core.Settings; +import com.ffii.core.engine.MailEngine; +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.user.service.SysGroupService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.core.io.InputStreamSource; +import org.springframework.scheduling.annotation.Async; +import org.springframework.stereotype.Service; + +@Service +public class MailService extends AbstractService { + public static InternetAddress FIX_RECIPIENT = null; + + @Autowired + private SettingsService settingsService; + + @Autowired + private MailEngine mailEngine; + + @Autowired + private SysGroupService sysGroupService; + + static { + FIX_RECIPIENT = null; // new InternetAddress("netpluto@gmail.com", "Jason Chuang"); + } + + @Async + public void sendSystemMail(int sysGroupId,InternetAddress recipient, String subject, String contentTemplate, Map contentModel) throws UnsupportedEncodingException { + this.sendSystemMail(sysGroupId, getFromAddress(sysGroupId), null, FIX_RECIPIENT != null ? FIX_RECIPIENT : recipient, subject, contentTemplate, contentModel); + } + + public InternetAddress getFromAddress(int sysGroupId) throws UnsupportedEncodingException{ + Map sysGroup = sysGroupService.find(sysGroupId); + return new InternetAddress(sysGroup.get("smtp_username")+"", sysGroup.get("companyName")+""); + } + + @Async + public void sendSystemMail(int sysGroupId, InternetAddress sender, InternetAddress replyTo, InternetAddress recipient, String subject, String contentTemplate, + Map contentModel) { + if (FIX_RECIPIENT != null) + logger.info("sendSystemMail() start, from: " + sender + ", to: " + FIX_RECIPIENT.getAddress() + ",Subject: " + subject); + else + logger.info("sendSystemMail() start, from: " + sender + ", to: " + recipient.getAddress() + ",Subject: " + subject); + mailEngine.sendFreeMarkerHtmlMail(sysGroupId, sender, replyTo, new InternetAddress[] { FIX_RECIPIENT != null ? FIX_RECIPIENT : recipient }, subject, contentTemplate, + contentModel); + logger.info("sendSystemMail() end"); + } + + @Async + public void sendSystemMail(int sysGroupId,InternetAddress sender, InternetAddress replyTo, InternetAddress recipient, String subject, String contentTemplate, + Map contentModel, String attachmentFilename, File file) { + if (FIX_RECIPIENT != null) + logger.info("sendSystemMail() start, from: " + sender + ", to: " + FIX_RECIPIENT.getAddress() + ",Subject: " + subject); + else + logger.info("sendSystemMail() start, from: " + sender + ", to: " + recipient.getAddress() + ",Subject: " + subject); + mailEngine.sendFreeMarkerHtmlMail(sysGroupId, sender, replyTo, new InternetAddress[] { FIX_RECIPIENT != null ? FIX_RECIPIENT : recipient }, subject, contentTemplate, + contentModel, attachmentFilename, file); + logger.info("sendSystemMail() end"); + } + + @Async + public void sendSystemMail(int sysGroupId, InternetAddress sender, InternetAddress replyTo, InternetAddress recipient, String subject, String contentTemplate, + Map contentModel, String attachmentFilename, InputStreamSource file) { + if (FIX_RECIPIENT != null) + logger.info("sendSystemMail() start, from: " + sender + ", to: " + FIX_RECIPIENT.getAddress() + ",Subject: " + subject); + else + logger.info("sendSystemMail() start, from: " + sender + ", to: " + recipient.getAddress() + ",Subject: " + subject); + mailEngine.sendFreeMarkerHtmlMail(sysGroupId, sender, replyTo, new InternetAddress[] { FIX_RECIPIENT != null ? FIX_RECIPIENT : recipient }, subject, contentTemplate, + contentModel, attachmentFilename, file); + logger.info("sendSystemMail() end"); + } + + @Async + public void sendSystemMail(int sysGroupId, InternetAddress sender, InternetAddress replyTo, InternetAddress[] recipients, String subject, String contentTemplate, + Map contentModel) { + sendSystemMail(sysGroupId, sender, replyTo, recipients, subject, contentTemplate, contentModel, null, null); + } + + @Async + public void sendSystemMail(int sysGroupId, InternetAddress sender, InternetAddress replyTo, InternetAddress[] recipients, String subject, String contentTemplate, + Map contentModel, String attachmentFilename, InputStreamSource file) { + if (FIX_RECIPIENT != null) + logger.info("sendSystemMail() start, from: " + sender + ", to: " + FIX_RECIPIENT.getAddress() + ",Subject: " + subject); + else + logger.info("sendSystemMail() start, from: " + sender + ", to: " + recipients.toString() + ",Subject: " + subject); + mailEngine.sendFreeMarkerHtmlMail(sysGroupId, sender, replyTo, FIX_RECIPIENT != null ? new InternetAddress[] { FIX_RECIPIENT } : recipients, subject, contentTemplate, + contentModel, attachmentFilename, file); + logger.info("sendSystemMail() end"); + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/meeting/Meeting.java b/src/main/java/com/ffii/tls/meeting/Meeting.java new file mode 100644 index 0000000..04f6ae6 --- /dev/null +++ b/src/main/java/com/ffii/tls/meeting/Meeting.java @@ -0,0 +1,104 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.meeting; + +import java.util.Date; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "meeting") +public class Meeting extends BaseEntity { + + public static final int TYPE_COMMISSION = 0; + public static final int TYPE_FITTING = 1; + public static final int TYPE_PICKUP = 2; + public static final int TYPE_NEW = 3; + + + private static final long serialVersionUID = 490716054903883090L; + + @Column(columnDefinition = "datetime") + private Date date; + + @Column(columnDefinition = "int(11)") + private Integer custId; + + @Column(columnDefinition = "int(11)") + private Integer orderId; + + @Column(columnDefinition = "int(11)") + private Integer type; + + @Column(columnDefinition = "varchar(255)") + private String remarks; + + @Column(columnDefinition = "varchar(45)") + private String staffName; + + public Meeting() { + } + + public Date getDate() { + return date; + } + + public void setDate(Date date) { + this.date = date; + } + + public Integer getCustId() { + return custId; + } + + public void setCustId(Integer custId) { + this.custId = custId; + } + + public Integer getOrderId() { + return orderId; + } + + public void setOrderId(Integer orderId) { + this.orderId = orderId; + } + + public Integer getType() { + return type; + } + + public void setType(Integer type) { + this.type = type; + } + + public String getRemarks() { + return remarks; + } + + public void setRemarks(String remarks) { + this.remarks = remarks; + } + + public String getStaffName() { + return staffName; + } + + public void setStaffName(String staffName) { + this.staffName = staffName; + } + + + +} diff --git a/src/main/java/com/ffii/tls/meeting/dao/MeetingDao.java b/src/main/java/com/ffii/tls/meeting/dao/MeetingDao.java new file mode 100644 index 0000000..3c55964 --- /dev/null +++ b/src/main/java/com/ffii/tls/meeting/dao/MeetingDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.meeting.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.meeting.Meeting; + +@Repository +public class MeetingDao extends HibernateDao { + + @Autowired + public MeetingDao(SessionFactory sessionFactory) { + super(Meeting.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/meeting/service/MeetingService.java b/src/main/java/com/ffii/tls/meeting/service/MeetingService.java new file mode 100644 index 0000000..de2ed34 --- /dev/null +++ b/src/main/java/com/ffii/tls/meeting/service/MeetingService.java @@ -0,0 +1,181 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.meeting.service; + +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.BooleanUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.meeting.Meeting; +import com.ffii.tbms.meeting.dao.MeetingDao; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * @author Patrick + */ +@Service +public class MeetingService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private MeetingDao meetingDao; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(Meeting instance) { + return meetingDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Meeting find(Integer id) { + return meetingDao.find(id); + } + + private String getSearchCriteriaString(Map args) { + StringBuilder sql = new StringBuilder(""); + + if (args != null) { + if (args.containsKey("fromDate")) + sql.append(" AND DATE(m.date) >= DATE(:fromDate) "); + if (args.containsKey("toDate")) + sql.append(" AND DATE(m.date) < :toDate "); + if (args.containsKey("custId")) + sql.append(" AND m.custId = :custId "); + if (args.containsKey("orderId")) + sql.append(" AND m.orderId = :orderId "); + + if (args.containsKey(Params.ID)) + sql.append(" AND m.id = :id"); + + if(args.containsKey("sysGroupId")){ + sql.append(" AND m.sysGroupId = :sysGroupId "); + } + } + + return sql.toString(); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder(" SELECT " + + " m.*, " + + " concat_ws(' / ', c.phone1, c.phone2) AS phone, " + + " c.email, " + + " concat(o.type,' ',o.code) AS orderNo , " + + " CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + + " IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + + " IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName " + + " FROM meeting m " + + " LEFT JOIN customer c ON c.id = m.custId " + + " LEFT JOIN orders o ON o.id = m.orderId " + + " WHERE m.deleted = 0 "); + + sql.append(getSearchCriteriaString(args)); + + if(args.containsKey("sysGroupId")){ + sql.append(" AND m.sysGroupId = :sysGroupId "); + } + + if (args.containsKey("meetingDate")) { + sql.append(" AND DATE(m.date) = :meetingDate"); + } + + if (args.containsKey("isDESC") && BooleanUtils.isTrue(args.get("isDESC"))) { + sql.append(" ORDER BY m.date DESC, m.id DESC "); + }else{ + sql.append(" ORDER BY m.date ASC, m.id ASC "); + } + + if (args != null) { + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit"); + } + logger.info(sql.toString()); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map countSearch(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder(" SELECT count(*) AS count FROM meeting m WHERE m.deleted = 0 "); + + sql.append(getSearchCriteriaString(args)); + if(args.containsKey("sysGroupId")){ + sql.append(" AND m.sysGroupId = :sysGroupId "); + } + if (args.containsKey("meetingDate")) { + sql.append(" AND m.date = :meetingDate"); + } + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map queryForMap(Integer id) { + + Map args = MapUtils.toHashMap(Params.ID, id); + SecurityUtils.authArgs(args); + + String sql = "SELECT * FROM meeting m WHERE m.id = :id"; + + if(args.containsKey("sysGroupId")){ + sql+=" AND m.sysGroupId = :sysGroupId "; + } + + return jdbcDao.queryForMap(sql, args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchForCalendar(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder("SELECT Date(m.date) as date, " + + " SUM(IF(type = " + Meeting.TYPE_COMMISSION + ", 1, 0)) AS commission, " + + " SUM(IF(type = " + Meeting.TYPE_FITTING + ", 1, 0)) AS fitting, " + + " SUM(IF(type = " + Meeting.TYPE_PICKUP + ", 1, 0)) AS pickup, " + + " SUM(IF(type = " + Meeting.TYPE_NEW + ", 1, 0)) AS new " + + " FROM meeting m " + + " WHERE m.deleted = 0 "); + + if(args.containsKey("sysGroupId")){ + sql.append(" AND m.sysGroupId = :sysGroupId "); + } + + sql.append(getSearchCriteriaString(args)); + + sql.append(" GROUP BY DATE(m.date) ORDER BY DATE(m.date) DESC "); + + logger.info("searchForCalendar:"+sql.toString()); + logger.info("args:"+args); + + return jdbcDao.queryForList(sql.toString(), args); + } + + public void addActionLog(int refId, String table, String recordStr){ + + } + +} diff --git a/src/main/java/com/ffii/tls/meeting/web/MeetingController.java b/src/main/java/com/ffii/tls/meeting/web/MeetingController.java new file mode 100644 index 0000000..ec6dd54 --- /dev/null +++ b/src/main/java/com/ffii/tls/meeting/web/MeetingController.java @@ -0,0 +1,204 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.meeting.web; + +import java.util.ArrayList; +import java.util.Calendar; +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.DateUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.meeting.Meeting; +import com.ffii.tbms.meeting.service.MeetingService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +@Controller +@RequestMapping(value = "/meeting") +public class MeetingController extends AbstractController { + + @Autowired + private MeetingService meetingService; + + @RequestMapping(value = "/save", method = RequestMethod.POST) + public String save(Model model, HttpServletRequest request, @RequestParam(defaultValue = "-1") Integer id) + throws Exception { + + if (SecurityUtils.isGranted("MEETING_MAINTAIN")) { + Meeting instance; + if (id > 0) { + instance = meetingService.find(id); + } else { + instance = new Meeting(); + } + + ServletRequestUtils.doBind(request, instance, null); + id = meetingService.saveOrUpdate(instance); + + model.addAttribute(Params.ID, id); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/delete", method = RequestMethod.POST) + public String delete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("MEETING_MAINTAIN") && SecurityUtils.isGranted("MEETING_DELETE")) { + + // find, mark delete, and save + Meeting instance = meetingService.find(id); + instance.setDeleted(true); + meetingService.saveOrUpdate(instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + model.addAttribute(Params.AUTH, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String load(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("MEETING_MAINTAIN")) { + Map data = meetingService.queryForMap(id); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("MEETING_MAINTAIN") || SecurityUtils.isGranted("CALENDAR_VIEW") + || SecurityUtils.isGranted("CUSTOMER_MAINTAIN")) { + Map args = new HashMap(); + + CriteriaUtils.addStringLike(request, args, Params.QUERY); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addInteger(request, args, "custId"); + CriteriaUtils.addInteger(request, args, "orderId"); + CriteriaUtils.addDate(request, args, "fromDate"); + CriteriaUtils.addDateTo(request, args, "toDate"); + CriteriaUtils.addDate(request, args, "meetingDate"); + CriteriaUtils.addBoolean(request, args, "isDESC"); + + CriteriaUtils.addInteger(request, args, "start"); + CriteriaUtils.addInteger(request, args, "limit"); + + List> records = meetingService.search(args); + Map count = meetingService.countSearch(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("total", NumberUtils.intValue(count.get("count"))); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/calendar.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String calendarsJson(Model model, HttpServletRequest request, @RequestParam int month, + @RequestParam int year) throws Exception { + + Calendar monthCalendar = Calendar.getInstance(); + monthCalendar.setTime(DateUtils.truncate(new Date(), Calendar.DAY_OF_MONTH)); + monthCalendar.set(Calendar.DAY_OF_MONTH, 1); + monthCalendar.set(Calendar.MONTH, month - 1); + monthCalendar.set(Calendar.YEAR, year); + + Date firstDateOfMonth = DateUtils.getFirstDateOfMonthByYearAndMonth(year, month); + Date lastDateOfMonth = DateUtils.getLastDateOfMonthByYearAndMonth(year, month); + + List> meetingData = meetingService + .searchForCalendar(MapUtils.toHashMap("fromDate", firstDateOfMonth, "toDate", lastDateOfMonth)); + + logger.info("meetingData:"+meetingData); + + List> monthRecord = new ArrayList<>(); + int weekIdx = 1; // row index + while (monthCalendar.getTime().before(lastDateOfMonth)) { + Map weekRecord = new HashMap<>(); + + for (int i = 1; i <= 7; i++) { // column index + Integer day = null; + if (monthCalendar.get(Calendar.DAY_OF_WEEK) == i && monthCalendar.get(Calendar.MONTH) < month + && monthCalendar.get(Calendar.YEAR) == year) { + day = monthCalendar.get(Calendar.DAY_OF_MONTH); + + for (Map data : meetingData) { + Date meetingDate = (Date) data.get("date"); + if (meetingDate.equals(monthCalendar.getTime())) { + weekRecord.put("col_" + i + "_commission", data.get("commission")); + weekRecord.put("col_" + i + "_fitting", data.get("fitting")); + weekRecord.put("col_" + i + "_pickup", data.get("pickup")); + weekRecord.put("col_" + i + "_new", data.get("new")); + } + } + + weekRecord.put("col_" + i, monthCalendar.getTime()); + weekRecord.put("col_" + i + "_clickable", true); + monthCalendar.add(Calendar.DAY_OF_MONTH, 1); + } else { + weekRecord.put("col_" + i, null); + weekRecord.put("col_" + i + "_clickable", false); + } + weekRecord.put("col_" + i + "_day", day); + } + weekRecord.put("id", weekIdx++); + monthRecord.add(weekRecord); + } + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + model.addAttribute(Params.RECORDS, monthRecord); + return JsonView.NAME; + } + + @RequestMapping(value = "/calendar-type", method = { RequestMethod.GET, RequestMethod.POST }) + public String requestMethodName(Model model, HttpServletRequest request, @RequestParam int param, + @RequestParam int year) { + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/message/Message.java b/src/main/java/com/ffii/tls/message/Message.java new file mode 100644 index 0000000..97b72c0 --- /dev/null +++ b/src/main/java/com/ffii/tls/message/Message.java @@ -0,0 +1,75 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.message; + +import java.util.Date; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +/** + * Message - carries user to user message. + * + * @see MessageThread + * @see MessageContent + * @see MessageRef + * + * @author Patrick + */ +@Entity +@Table(name = "message") +public class Message extends BaseEntity { + + private static final long serialVersionUID = 6336248318304156664L; + + + @Column(columnDefinition = "int") + private int orderId; + + @Column(columnDefinition = "varchar(255)") + private String content; + + @Column(columnDefinition = "datetime") + private Date readTime; + + /** Default constructor */ + public Message() { + + } + + public int getOrderId() { + return orderId; + } + + public void setOrderId(int orderId) { + this.orderId = orderId; + } + + public String getContent() { + return content; + } + + public void setContent(String content) { + this.content = content; + } + + public Date getReadTime() { + return readTime; + } + + public void setReadTime(Date readTime) { + this.readTime = readTime; + } + +} diff --git a/src/main/java/com/ffii/tls/message/dao/MessageDao.java b/src/main/java/com/ffii/tls/message/dao/MessageDao.java new file mode 100644 index 0000000..2c90cb9 --- /dev/null +++ b/src/main/java/com/ffii/tls/message/dao/MessageDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.message.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.message.Message; + +@Repository +public class MessageDao extends HibernateDao { + + @Autowired + public MessageDao(SessionFactory sessionFactory) { + super(Message.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/message/service/MessageService.java b/src/main/java/com/ffii/tls/message/service/MessageService.java new file mode 100644 index 0000000..7d18d19 --- /dev/null +++ b/src/main/java/com/ffii/tls/message/service/MessageService.java @@ -0,0 +1,86 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.message.service; + +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.BooleanUtils; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.message.Message; +import com.ffii.tbms.message.dao.MessageDao; + +@Service +public class MessageService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private MessageDao messageDao; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Message find(Integer id) { + return messageDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(Message instance) { + return messageDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder(" SELECT m.* " + +" FROM message m " + +" WHERE m.deleted = 0 "); + if (args != null) { + if (args.containsKey("unRead") && BooleanUtils.isTrue(args.get("unRead"))) + sql.append(" AND readTime IS NULL "); + + if(args.containsKey("query")) sql.append(" AND m.content LIKE :query "); + if(args.containsKey("sysGroupId")) sql.append(" AND m.sysGroupId = :sysGroupId "); + } + sql.append(" ORDER BY m.created DESC "); + if (args != null) { + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map searchCount(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder(" SELECT count(m.id) AS count " + +" FROM message m " + +" WHERE m.deleted = 0 "); + if (args != null) { + if (args.containsKey("unRead") && BooleanUtils.isTrue(args.get("unRead"))) + sql.append(" AND readTime IS NULL "); + + if(args.containsKey("query")) sql.append(" AND m.content LIKE :query "); + if(args.containsKey("sysGroupId")) sql.append(" AND m.sysGroupId = :sysGroupId "); + } + return jdbcDao.queryForMap(sql.toString(), args); + } + +} diff --git a/src/main/java/com/ffii/tls/message/web/MessageController.java b/src/main/java/com/ffii/tls/message/web/MessageController.java new file mode 100644 index 0000000..8cca4f2 --- /dev/null +++ b/src/main/java/com/ffii/tls/message/web/MessageController.java @@ -0,0 +1,94 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.message.web; + +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.message.Message; +import com.ffii.tbms.message.service.MessageService; + +/** + * Message Controller + * + * @author Patrick + */ +@Controller +@RequestMapping(value = "/message") +public class MessageController extends AbstractController { + + @Autowired + private MessageService messageService; + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String threadList(Model model, HttpServletRequest request, + @RequestParam(defaultValue = "false") Boolean unRead) throws Exception { + + Map args = new HashMap<>(); + CriteriaUtils.addInteger(request, args,"start"); + CriteriaUtils.addInteger(request, args,"limit"); + CriteriaUtils.addStringLike(request, args,"query"); + args.put("unRead", unRead); + + List> records = messageService.search(args); + Map count = messageService.searchCount(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("total", NumberUtils.intValue(count.get("count"))); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "/new", method = { RequestMethod.GET, RequestMethod.POST }) + public String getNewCount(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap<>(); + args.put("unRead", true); + + Map count = messageService.searchCount(args); + + model.addAttribute("new", NumberUtils.intValue(count.get("count"))); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "/update-readtime.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String markReadTime(Model model, HttpServletRequest request) throws Exception { + + int[] ids = ServletRequestUtils.getIntParameters(request, "ids"); + if (ids != null) { + for (int id : ids) { + Message instance = messageService.find(id); + instance.setReadTime(new Date()); + messageService.saveOrUpdate(instance); + } + } + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } +} diff --git a/src/main/java/com/ffii/tls/order/Order.java b/src/main/java/com/ffii/tls/order/Order.java new file mode 100644 index 0000000..6b3f6e8 --- /dev/null +++ b/src/main/java/com/ffii/tls/order/Order.java @@ -0,0 +1,247 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order; + +import java.util.Date; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "orders") +public class Order extends BaseEntity { + + private static final long serialVersionUID = -6977390008376019654L; + + public static final Integer STATUS_IGNORE = -2; + public static final Integer STATUS_CANCELLED = -1; + public static final Integer STATUS_ON_HAND = 0; + public static final Integer STATUS_COMPLETED = 1; + + public static final Integer WS_STATUS_BLANK = null; + public static final Integer WS_STATUS_PENDING = 1; + public static final Integer WS_STATUS_RECEIVED = 2; + public static final Integer WS_STATUS_COMPLETED = 3; + + public static final Integer WS_WORK_STATUS_PENDING = 0; + public static final Integer WS_WORK_STATUS_COMPLETED = 1; + + public static final Integer IN_OUT_STATUS_BLANK = null; + public static final Integer IN_OUT_STATUS_PENDING = 1; + public static final Integer IN_OUT_STATUS_RECEIVED = 2; + + @Column(columnDefinition = "varchar(50)") + private String code; + + @Column(columnDefinition = "varchar(50)") + private String type; + + @Column(columnDefinition = "int(11)") + private Integer custId; + + @Column(columnDefinition = "int(11)") + private Integer fileId; + + @Column(columnDefinition = "int(11)") + private Integer ref; + + @Column(columnDefinition = "varchar(100)") + private String refNo; + + @Column(columnDefinition = "date") + private Date date; + + @Column(columnDefinition = "varchar(255)") + private String remarks; + + @Column(columnDefinition = "int(11)") + private Integer status; + + @Column(columnDefinition = "date") + private Date outDate; + + @Column(columnDefinition = "date") + private Date inDate; + + @Column(columnDefinition = "varchar(255)") + private String outRemark; + + @Column(columnDefinition = "varchar(255)") + private String inRemark; + + @Column(columnDefinition = "tinyint(1)") + private Boolean ignoreC; + + @Column(columnDefinition = "int(11)") + private Integer workshopStatus; + + @Column(columnDefinition = "date") + private Date targetCompleteDate; + + @Column(columnDefinition = "int(11)") + private Integer inStatus; + + @Column(columnDefinition = "int(11)") + private Integer outStatus; + + public Order() { + } + + public String getCode() { + return code; + } + + public void setCode(String code) { + this.code = code; + } + + public String getType() { + return type; + } + + public void setType(String type) { + this.type = type; + } + + public Integer getCustId() { + return custId; + } + + public void setCustId(Integer custId) { + this.custId = custId; + } + + public Integer getFileId() { + return fileId; + } + + public void setFileId(Integer fileId) { + this.fileId = fileId; + } + + public Integer getRef() { + return ref; + } + + public void setRef(Integer ref) { + this.ref = ref; + } + + public String getRefNo() { + return refNo; + } + + public void setRefNo(String refNo) { + this.refNo = refNo; + } + + public Date getDate() { + return date; + } + + public void setDate(Date date) { + this.date = date; + } + + public String getRemarks() { + return remarks; + } + + public void setRemarks(String remarks) { + this.remarks = remarks; + } + + public Integer getStatus() { + return status; + } + + public void setStatus(Integer status) { + this.status = status; + } + + public Date getOutDate() { + return outDate; + } + + public void setOutDate(Date outDate) { + this.outDate = outDate; + } + + public Date getInDate() { + return inDate; + } + + public void setInDate(Date inDate) { + this.inDate = inDate; + } + + public String getOutRemark() { + return outRemark; + } + + public void setOutRemark(String outRemark) { + this.outRemark = outRemark; + } + + public String getInRemark() { + return inRemark; + } + + public void setInRemark(String inRemark) { + this.inRemark = inRemark; + } + + public Boolean getIgnoreC() { + return ignoreC; + } + + public void setIgnoreC(Boolean ignoreC) { + this.ignoreC = ignoreC; + } + + public Integer getWorkshopStatus() { + return workshopStatus; + } + + public void setWorkshopStatus(Integer workshopStatus) { + this.workshopStatus = workshopStatus; + } + + public Date getTargetCompleteDate() { + return targetCompleteDate; + } + + public void setTargetCompleteDate(Date targetCompleteDate) { + this.targetCompleteDate = targetCompleteDate; + } + + public Integer getInStatus() { + return inStatus; + } + + public void setInStatus(Integer inStatus) { + this.inStatus = inStatus; + } + + public Integer getOutStatus() { + return outStatus; + } + + public void setOutStatus(Integer outStatus) { + this.outStatus = outStatus; + } + + + +} diff --git a/src/main/java/com/ffii/tls/order/OrderItem.java b/src/main/java/com/ffii/tls/order/OrderItem.java new file mode 100644 index 0000000..41cc89b --- /dev/null +++ b/src/main/java/com/ffii/tls/order/OrderItem.java @@ -0,0 +1,66 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order; + +import java.math.BigDecimal; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "order_item") +public class OrderItem extends BaseEntity { + + private static final long serialVersionUID = -6277924152608761522L; + + + @Column(columnDefinition = "varchar(255)") + private String name; + + @Column(columnDefinition = "int(11)") + private Integer orderId; + + @Column(columnDefinition = "decimal(18,4)") + private BigDecimal price; + + public OrderItem() { + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public Integer getOrderId() { + return orderId; + } + + public void setOrderId(Integer orderId) { + this.orderId = orderId; + } + + public BigDecimal getPrice() { + return price; + } + + public void setPrice(BigDecimal price) { + this.price = price; + } + + + +} diff --git a/src/main/java/com/ffii/tls/order/Payment.java b/src/main/java/com/ffii/tls/order/Payment.java new file mode 100644 index 0000000..99fcc80 --- /dev/null +++ b/src/main/java/com/ffii/tls/order/Payment.java @@ -0,0 +1,95 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order; + +import java.math.BigDecimal; +import java.util.Date; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "payment") +public class Payment extends BaseEntity { + + public static final String TYPE_OTHER = "Other"; + public static final String TYPE_AE = "AE"; + public static final String TYPE_CASH = "Cash"; + public static final String TYPE_CHEQUE = "Cheque"; + public static final String TYPE_CHQ = "Chq"; + public static final String TYPE_CUP = "Cup"; + public static final String TYPE_MASTER = "Master"; + public static final String TYPE_VISA = "Visa"; + + private static final long serialVersionUID = -9086502074352482840L; + + @Column(columnDefinition = "int(11)") + private Integer orderId; + + @Column(columnDefinition = "date") + private Date date; + + @Column(columnDefinition = "decimal(18,4)") + private BigDecimal amount; + + @Column(columnDefinition = "varchar(30)") + private String method; + + @Column(columnDefinition = "varchar(255)") + private String refNo; + + public Payment() { + } + + public Integer getOrderId() { + return orderId; + } + + public void setOrderId(Integer orderId) { + this.orderId = orderId; + } + + public BigDecimal getAmount() { + return amount; + } + + public void setAmount(BigDecimal amount) { + this.amount = amount; + } + + public String getMethod() { + return method; + } + + public void setMethod(String method) { + this.method = method; + } + + public String getRefNo() { + return refNo; + } + + public void setRefNo(String refNo) { + this.refNo = refNo; + } + + public Date getDate() { + return date; + } + + public void setDate(Date date) { + this.date = date; + } + +} diff --git a/src/main/java/com/ffii/tls/order/dao/OrderDao.java b/src/main/java/com/ffii/tls/order/dao/OrderDao.java new file mode 100644 index 0000000..fc0d48c --- /dev/null +++ b/src/main/java/com/ffii/tls/order/dao/OrderDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.order.Order; + +@Repository +public class OrderDao extends HibernateDao { + + @Autowired + public OrderDao(SessionFactory sessionFactory) { + super(Order.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/order/dao/OrderItemDao.java b/src/main/java/com/ffii/tls/order/dao/OrderItemDao.java new file mode 100644 index 0000000..ba076cd --- /dev/null +++ b/src/main/java/com/ffii/tls/order/dao/OrderItemDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.order.OrderItem; + +@Repository +public class OrderItemDao extends HibernateDao { + + @Autowired + public OrderItemDao(SessionFactory sessionFactory) { + super(OrderItem.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/order/dao/PaymentDao.java b/src/main/java/com/ffii/tls/order/dao/PaymentDao.java new file mode 100644 index 0000000..385a2f5 --- /dev/null +++ b/src/main/java/com/ffii/tls/order/dao/PaymentDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.order.Payment; + +@Repository +public class PaymentDao extends HibernateDao { + + @Autowired + public PaymentDao(SessionFactory sessionFactory) { + super(Payment.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/order/service/InvoiceService.java b/src/main/java/com/ffii/tls/order/service/InvoiceService.java new file mode 100644 index 0000000..fbf1821 --- /dev/null +++ b/src/main/java/com/ffii/tls/order/service/InvoiceService.java @@ -0,0 +1,281 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.service; + +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.math.BigDecimal; +import java.nio.charset.Charset; +import java.nio.charset.StandardCharsets; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.Paths; +import java.text.SimpleDateFormat; +import java.util.ArrayList; +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.file.FileBlob; +import com.ffii.tbms.user.service.SysGroupService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; +import org.springframework.util.Assert; + +import freemarker.template.utility.SecurityUtilities; +import net.sf.jasperreports.engine.JREmptyDataSource; +import net.sf.jasperreports.engine.JRException; +import net.sf.jasperreports.engine.JasperCompileManager; +import net.sf.jasperreports.engine.JasperFillManager; +import net.sf.jasperreports.engine.JasperPrint; +import net.sf.jasperreports.engine.JasperReport; +import net.sf.jasperreports.engine.JasperRunManager; +import net.sf.jasperreports.engine.data.JRBeanCollectionDataSource; +import net.sf.jasperreports.engine.export.JRPdfExporter; +import net.sf.jasperreports.engine.type.WhenNoDataTypeEnum; +import net.sf.jasperreports.export.SimpleExporterInput; +import net.sf.jasperreports.export.SimpleOutputStreamExporterOutput; + + +@Service +public class InvoiceService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private SysGroupService sysGroupService; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map search(int orderId) { + StringBuilder sql = new StringBuilder( + " SELECT o.id, " + +" o.date As orderDate, " + +" concat(o.type,o.code) As orderNo, " + +" concat_ws(' ', c.firstName, c.surname, c.nameCh) AS custName, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" c.firstName, " + +" c.surname, " + +" c.nameCh, " + +" c.phone1, " + +" c.phone2, " + +" c.email " + +" FROM orders o " + +" LEFT JOIN customer c ON c.id = o.custId " + +" WHERE o.id = "+orderId + ); + + return jdbcDao.queryForMap(sql.toString(), null); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> getOrderItems(int orderId) { + StringBuilder sql = new StringBuilder( + " SELECT " + + " name AS description, " + + " price AS amount " + + " FROM " + + " order_item oi " + + " WHERE " + + " oi.deleted = 0 AND oi.orderId = "+orderId + ); + + return jdbcDao.queryForList(sql.toString(), null); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map getOrderItemTotalAmount(int orderId) { + StringBuilder sql = new StringBuilder( + " SELECT " + + " sum(oi.price) As totalAmount " + + " FROM " + + " order_item oi " + + " WHERE " + + " oi.deleted = 0 AND oi.orderId = "+orderId + ); + + return jdbcDao.queryForMap(sql.toString(), null); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map getPaymentTotal(int orderId) { + StringBuilder sql = new StringBuilder( + " select sum(p.amount) As totalPayment from payment p where p.deleted = 0 and p.orderId = "+orderId); + return jdbcDao.queryForMap(sql.toString(), null); + } + + public Map getInvoicePdfParams(int orderId){ + Map params = search(orderId); + + + //For Ricky + /* + String path = this.getClass().getClassLoader().getResource("").getPath() + "../report/dream_bespoke_icon.png"; + */ + + FileBlob blob = sysGroupService.getIconBlob(); + Map sysGroup = sysGroupService.find(SecurityUtils.getUser().getSysGroupId()); + + params.put("companyIcon", blob==null?null:blob.getBytes()); + params.put("companyName", sysGroup== null?"": sysGroup.get("companyName")); + + String contactStr = ""; + if(sysGroup != null){ + int count = 0; + if(sysGroup.get("address")!=null && !sysGroup.get("address").toString().isBlank()){ + contactStr = sysGroup.get("address").toString(); + count++; + } + if(sysGroup.get("phone")!=null && !sysGroup.get("phone").toString().isBlank()){ + contactStr += (count%2==1?"
":"")+ "Tel:"+sysGroup.get("phone").toString(); + count++; + } + if(sysGroup.get("fax")!=null && !sysGroup.get("fax").toString().isBlank()){ + contactStr += (count%2==1?"
":"")+(count > 0 && count%2==0?"   ":"")+"Fax:"+sysGroup.get("fax").toString(); + count++; + } + if(sysGroup.get("email")!=null && !sysGroup.get("email").toString().isBlank()){ + contactStr += (count%2==1?"
":"")+(count > 0 && count%2==0?"   ":"")+"Email:"+sysGroup.get("email").toString(); + } + } + + params.put("contactStr", contactStr); + + BigDecimal total = (BigDecimal) getOrderItemTotalAmount(orderId).get("totalAmount"); + BigDecimal payment = (BigDecimal)getPaymentTotal(orderId).get("totalPayment"); + BigDecimal deposit = total; + if(payment != null) + deposit = total.subtract(payment); + + params.put("payment", payment==null?BigDecimal.ZERO: payment); + params.put("total", total == null?BigDecimal.ZERO: total); + params.put("deposit", deposit== null? BigDecimal.ZERO:deposit); + + SimpleDateFormat sdf = new SimpleDateFormat("MMMMM d, yyyy"); + if(params.get("orderDate") != null) + params.put("date", sdf.format(params.get("orderDate"))); + else + params.put("date", new Date()); + + params.put("format", "pdf"); + + return params; + } + + + public byte[] genInvoice(int orderId) throws IOException, JRException, IllegalStateException { + + Map params = getInvoicePdfParams(orderId); + + List> list = getOrderItems(orderId); + if(list == null || list.size()==0){ + for(int i =0; i<12; i++) + list.add(new HashMap()); + }else{ + int line = 12-list.size(); + for(int i = 0; i()); + } + + InputStream templateInputStream = this.getServletContext().getResourceAsStream("WEB-INF/report/invoiceTemp.jrxml"); + ByteArrayOutputStream byteOut = new ByteArrayOutputStream(); + + JasperReport jasperReport = JasperCompileManager.compileReport(templateInputStream); + jasperReport.setWhenNoDataType(WhenNoDataTypeEnum.ALL_SECTIONS_NO_DETAIL); + JasperPrint jasperPrint = JasperFillManager.fillReport(jasperReport, params, new JRBeanCollectionDataSource(list)); + + JRPdfExporter exporter = new JRPdfExporter(); + exporter.setExporterInput(new SimpleExporterInput(jasperPrint)); + exporter.setExporterOutput(new SimpleOutputStreamExporterOutput(byteOut)); + exporter.exportReport(); + + return byteOut.toByteArray(); + + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void updateTemplateBody(String body){ + /* + Path path = Paths.get(this.getServletContext().getRealPath("WEB-INF/mail/invoiceTemplateMail.ftl")); + Charset charset = StandardCharsets.UTF_8; + String content = new String(Files.readAllBytes(path), charset); + String oldBody = getTemplateBody(content); + content = content.replace(oldBody, body); + + Files.write(path, content.getBytes(charset)); + */ + + jdbcDao.executeUpdate( + " UPDATE sys_groups sg SET mailBody = :mailBody WHERE id = :id ", + MapUtils.toHashMap( + "mailBody", body, + "id", SecurityUtils.getUser().getSysGroupId() + )); + + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void updateTemplateSubject(String subject){ + jdbcDao.executeUpdate( + " UPDATE sys_groups sg SET mailSubject = :mailSubject WHERE id = :id ", + MapUtils.toHashMap( + "mailSubject", subject, + "id", SecurityUtils.getUser().getSysGroupId() + )); + //jdbcDao.executeUpdate(" UPDATE settings SET value = :value WHERE name = 'MAIL.temp.subject' ", MapUtils.toHashMap("value", subject)); + } + + + public String getTemplateBody(String content) throws IOException{ + logger.info("content : "+content); + logger.info("index: "+content.indexOf("")); + logger.info("content : "+content.substring(content.indexOf(""))); + logger.info("index-last : "+content.indexOf("")); + return content.substring(content.indexOf("")+"".length(), content.indexOf("")); + } +/* + public String getTemplateBody() throws IOException{ + Path path = Paths.get(this.getServletContext().getRealPath("WEB-INF/mail/invoiceTemplateMail.ftl")); + Charset charset = StandardCharsets.UTF_8; + String content = new String(Files.readAllBytes(path), charset); + return getTemplateBody(content); + } + */ + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public String getTemplateBody() throws IOException{ + + Map body = jdbcDao.queryForMap( + "SELECT mailBody FROM sys_groups WHERE id = :id ", + MapUtils.toHashMap("id", SecurityUtils.getUser().getSysGroupId()) + ); + + return body==null || body.get("mailBody") == null?"":body.get("mailBody").toString(); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public String getTemplateSubject() throws IOException{ + + Map subject = jdbcDao.queryForMap( + "SELECT mailSubject FROM sys_groups WHERE id = :id ", + MapUtils.toHashMap("id", SecurityUtils.getUser().getSysGroupId()) + ); + return subject==null||subject.get("mailSubject")== null? "":subject.get("mailSubject").toString(); + } + +} diff --git a/src/main/java/com/ffii/tls/order/service/OrderItemService.java b/src/main/java/com/ffii/tls/order/service/OrderItemService.java new file mode 100644 index 0000000..6fc507d --- /dev/null +++ b/src/main/java/com/ffii/tls/order/service/OrderItemService.java @@ -0,0 +1,176 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.service; + +import java.math.BigDecimal; +import java.text.DecimalFormat; +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import com.fasterxml.jackson.core.JsonProcessingException; +import com.fasterxml.jackson.databind.ObjectMapper; +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.log.service.AuditLogService; +import com.ffii.tbms.message.Message; +import com.ffii.tbms.message.service.MessageService; +import com.ffii.tbms.order.Order; +import com.ffii.tbms.order.OrderItem; +import com.ffii.tbms.order.dao.OrderItemDao; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; +import org.springframework.web.bind.ServletRequestBindingException; + +/** + * @author Patrick + */ +@Service +public class OrderItemService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private OrderItemDao orderItemDao; + + @Autowired + private OrderService orderService; + + @Autowired + private MessageService messageService; + + @Autowired + private AuditLogService auditLogService; + + DecimalFormat df = new DecimalFormat("#,##0.00"); + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(OrderItem instance) { + return orderItemDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public OrderItem find(Integer id) { + return orderItemDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + StringBuilder sql = new StringBuilder( + " SELECT " + +" oi.id, " + +" oi.orderId, " + +" oi.name, " + +" oi.price " + +" FROM order_item oi " + +" WHERE oi.deleted = 0 "); + + if (args != null) { + if (args.containsKey("orderId")) + sql.append(" AND oi.orderId = :orderId "); + } + sql.append(" ORDER BY oi.id "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map queryForMap(Integer id) { + String sql = "SELECT * FROM order_item oi WHERE oi.id = :id"; + + return jdbcDao.queryForMap(sql, MapUtils.toHashMap(Params.ID, id)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void compare(OrderItem item, HttpServletRequest request)throws ServletRequestBindingException { + String priceStr = ServletRequestUtils.getTrimmedStringParameter(request, "price"); + BigDecimal price = new BigDecimal(priceStr); + if(price.compareTo(item.getPrice())!=0){ + Order order = orderService.find(item.getOrderId()); + Message message = new Message(); + message.setOrderId(item.getOrderId()); + message.setContent("Amount changed: \n("+order.getType()+order.getCode()+") " + +item.getName()+"\nAmount: "+df.format(item.getPrice())+" -> (New) "+df.format(price)); + messageService.saveOrUpdate(message); + } + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, OrderItem newRecord, OrderItem oldRecord)throws JsonProcessingException { + Map data = new HashMap<>(); + Map compare = LogUtils.compare(newRecord, oldRecord); + data = (Map)compare.get(LogUtils.DIFF); + log(action, id, data, newRecord); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, Map data, OrderItem newRecord)throws JsonProcessingException { + if(data.size()<=0) return; + ObjectMapper mapper = new ObjectMapper(); + auditLogService.save("order_item", + id, + SecurityUtils.getUser().getId(), + new Date(), + action, + mapper.writeValueAsString(data), + newRecord.getOrderId(), + "orders"); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, OrderItem newRecord)throws JsonProcessingException { + Map data = LogUtils.filter(LogUtils.objectToMap(newRecord)); + log(action, id, data, newRecord); + } + + // For API + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, int userId, Map data, OrderItem newRecord)throws JsonProcessingException { + if(data.size()<=0) return; + ObjectMapper mapper = new ObjectMapper(); + auditLogService.save("order_item", + id, + userId, + new Date(), + action, + mapper.writeValueAsString(data), + newRecord.getOrderId(), + "orders"); + } + + //For API + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, int userId, OrderItem newRecord, OrderItem oldRecord)throws JsonProcessingException { + Map data = new HashMap<>(); + Map compare = LogUtils.compare(newRecord, oldRecord); + data = (Map)compare.get(LogUtils.DIFF); + log(action, id, userId, data, newRecord); + } + + // For API + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, int userId, OrderItem newRecord)throws JsonProcessingException { + Map data = LogUtils.filter(LogUtils.objectToMap(newRecord)); + log(action, id, userId, data, newRecord); + } + +} diff --git a/src/main/java/com/ffii/tls/order/service/OrderService.java b/src/main/java/com/ffii/tls/order/service/OrderService.java new file mode 100644 index 0000000..7c0f9c2 --- /dev/null +++ b/src/main/java/com/ffii/tls/order/service/OrderService.java @@ -0,0 +1,539 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.service; + +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import com.fasterxml.jackson.core.JsonProcessingException; +import com.fasterxml.jackson.databind.ObjectMapper; +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.BooleanUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.log.service.AuditLogService; +import com.ffii.tbms.order.Order; +import com.ffii.tbms.order.dao.OrderDao; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * @author Patrick + */ +@Service +public class OrderService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private OrderDao orderDao; + + @Autowired + private AuditLogService auditLogService; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(final Order instance) { + return orderDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Order find(final Integer id) { + return orderDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchForCombo(Map args) { + + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + + StringBuilder sql = new StringBuilder( + " SELECT o.type, " + +" o.code, " + +" o.status, " + +" o.id, " + +" o.inDate, " + +" o.inRemark, " + +" o.outRemark, " + +" o.outDate, " + +" o.custId, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName " + +" FROM orders o " + +" LEFT JOIN customer c ON c.id = o.custId " + +" WHERE o.deleted = 0 "); + + if(args != null){ + if(args.containsKey("query")){ + sql.append(" AND (concat(o.type, o.code) LIKE :query " + +" OR " + +" ( ( concat_ws(' ', c.firstName ,c.surname, c.nameCh) LIKE :query " + +" OR concat_ws(' ', c.surname, c.firstName, c.nameCh) LIKE :query )) " + +" )"); + } + if(args.containsKey("sysGroupId")) sql.append(" AND o.sysGroupId = :sysGroupId "); + if(args.containsKey("id"))sql.append(" AND o.id = :id "); + if(args.containsKey("custId"))sql.append(" AND o.custId = :custId "); + if(args.containsKey("status"))sql.append(" AND o.status IN (:status) "); + } + + sql.append(" ORDER BY concat(o.type, o.code) ASC "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + private String getSearchCriteriaString(final Map args) { + final StringBuilder sql = new StringBuilder(""); + + if (args != null) { + if (args.containsKey(Params.ID)) + sql.append(" AND o.id = :id"); + if (args.containsKey("orderType")) + sql.append(" AND o.type = :orderType "); + if (args.containsKey("orderCode")) + sql.append(" AND o.code LIKE :orderCode "); + if (args.containsKey("orderNoStr")){ + sql.append(args.get("orderNoStr")); + } + + /* + if(args.containsKey("orderNo")){ + //sql.append(" AND ( concat(o.type, o.code) LIKE :orderNo OR o.refNo LIKE :orderNo ) "); + String str = args.get("orderNo").toString().trim(); + String[] array = str.split(",| "); + str = ""; + for(String orderNo: array){ + if(!str.equals("")){ + str = str + " OR "; + } + str = str+" concat(o.type, o.code) LIKE '%"+orderNo.trim()+"%' "; + } + sql.append(" AND ( "+str+" ) "); + } + */ + + if (args.containsKey("targetCompleteDateFrom")) + sql.append(" AND o.targetCompleteDate >= :targetCompleteDateFrom "); + + if (args.containsKey("targetCompleteDateTo")) + sql.append(" AND o.targetCompleteDate < :targetCompleteDateTo "); + + if (args.containsKey("workshopTargetDateFrom")) + sql.append(" AND DATE_ADD(o.targetCompleteDate, INTERVAL -2 day) >= :workshopTargetDateFrom "); + + if (args.containsKey("workshopTargetDateTo")) + sql.append(" AND DATE_ADD(o.targetCompleteDate, INTERVAL -2 day) < :workshopTargetDateTo "); + + + if (args.containsKey("fromOutDate")) + sql.append(" AND o.outDate >= :fromOutDate "); + if (args.containsKey("toOutDate")) + sql.append(" AND o.outDate < :toOutDate "); + if (args.containsKey("fromDate")) + sql.append(" AND o.date >= :fromDate "); + if (args.containsKey("toDate")) + sql.append(" AND o.date < :toDate "); + /* + if (args.containsKey("showIgnored")){ + if(BooleanUtils.isTrue(args.get("showIgnored"))== true) + sql.append(" "); + else + //sql.append(" AND o.ignoreC <> 1 "); + } + */ + if (args.containsKey("custId")) + sql.append(" AND o.custId = :custId "); + + if (args.containsKey("firstName")) + sql.append(" AND c.firstName LIKE :firstName "); + if (args.containsKey("nameCh")) + sql.append(" AND c.nameCh LIKE :nameCh "); + if (args.containsKey("surname")) + sql.append(" AND c.surname LIKE :surname "); + if (args.containsKey("emailPhone")) + sql.append(" AND (c.email LIKE :emailPhone OR c.phone1 LIKE :emailPhone OR c.phone2 LIKE :emailPhone ) "); + + if (args.containsKey("status")) + sql.append(" AND o.status = :status "); + if (args.containsKey("workshopStatus")) + sql.append(" AND o.workshopStatus = :workshopStatus "); + if (args.containsKey("itemName")) + sql.append(" AND _oi.itemName LIKE :itemName "); + if (args.containsKey("balance") && BooleanUtils.isTrue(args.get("balance"))) + sql.append(" AND IF(_p.paymentAmount IS NULL, 0, _p.paymentAmount) < _oi.orderAmount "); + } + + return sql.toString(); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map find(final Map args) { + + final StringBuilder sql = new StringBuilder( + " SELECT " + +" o.code, " + +" o.id, " + +" o.type, " + +" CONCAT(o.type,o.code) AS orderNo, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName " + +" FROM orders o " + +" LEFT JOIN customer c ON c.id = o.custId " + +" WHERE o.id = :orderId "); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(final Map args) { + + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + + final StringBuilder sql = new StringBuilder( + " SELECT " + +" o.id, " + +" o.code, " + +" o.type, " + +" o.ref, " + +" o.refNo, " + +" o.status, " + +" o.date, " + +" o.custId, " + +" o.fileId, " + +" o.remarks, " + +" o.outDate, " + +" o.inDate, " + +" o.outRemark, " + +" o.inRemark, " + +" o.workshopStatus, " + //+" o.ignoreC, " + +" o.targetCompleteDate, " + +" o.targetCompleteDate, " + +" o.inStatus, " + +" o.outStatus, " + +" c.email, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" concat_ws(' ', c.firstName ,c.surname, c.nameCh) AS customerName, " + +" _p.paymentAmount, " + +" IF(_p.paymentAmount IS NULL, false, true) AS havePayment, " + +" _oi.orderAmount " + +" FROM orders o " + +" LEFT JOIN customer c ON c.id = o.custId " + +" LEFT JOIN (SELECT oi.orderId, SUM(oi.price) AS orderAmount, " + +" GROUP_CONCAT(oi.name SEPARATOR ' ') AS itemName " + +" FROM order_item oi WHERE oi.deleted = 0 " + +" GROUP BY oi.orderId) _oi ON _oi.orderId = o.id " + +" LEFT JOIN ( " + +" SELECT " + +" SUM(p.amount) AS paymentAmount, " + +" p.orderId " + +" FROM payment p " + +" WHERE p.deleted = 0 " + +" GROUP BY p.orderId) _p ON _p.orderId = o.id " + +" WHERE o.deleted = 0 "); + + sql.append(getSearchCriteriaString(args)); + + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId "); + } + + if(args.containsKey("orderNoStr")){ + sql.append(" ORDER BY o.type ASC, o.code ASC, o.id ASC "); + }else{ + sql.append(" ORDER BY o.date DESC, o.type ASC, o.id DESC "); + } + + if (args != null) { + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + + logger.info("orderSerach : "+sql.toString()); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map countSearch(final Map args) { + + + + StringBuilder sql = new StringBuilder( + " SELECT " + +" COUNT(o.id) AS count " + +" FROM orders o " + +" LEFT JOIN customer c ON c.id = o.custId " + +" LEFT JOIN (SELECT oi.orderId, SUM(oi.price) AS orderAmount, " + +" GROUP_CONCAT(oi.name SEPARATOR ' ') AS itemName " + +" FROM order_item oi WHERE oi.deleted = 0 " + +" GROUP BY oi.orderId) _oi ON _oi.orderId = o.id " + +" LEFT JOIN ( " + +" SELECT " + +" SUM(p.amount) AS paymentAmount, " + +" p.orderId " + +" FROM payment p " + +" WHERE p.deleted = 0 " + +" GROUP BY p.orderId) _p ON _p.orderId = o.id " + +" WHERE o.deleted = 0 "); + + sql.append(getSearchCriteriaString(args)); + + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId "); + } + + logger.info("sql: "+sql.toString()); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map sumTotalAmount(final Map args) { + + StringBuilder sql = new StringBuilder( + " SELECT " + +" SUM(_oi.orderAmount) AS totalAmount " + +" FROM orders o " + +" LEFT JOIN customer c ON c.id = o.custId " + +" LEFT JOIN (SELECT oi.orderId, SUM(oi.price) AS orderAmount, " + +" GROUP_CONCAT(oi.name SEPARATOR ' ') AS itemName " + +" FROM order_item oi WHERE oi.deleted = 0 " + +" GROUP BY oi.orderId) _oi ON _oi.orderId = o.id " + +" LEFT JOIN ( " + +" SELECT " + +" SUM(p.amount) AS paymentAmount, " + +" p.orderId " + +" FROM payment p " + +" WHERE p.deleted = 0 " + +" GROUP BY p.orderId) _p ON _p.orderId = o.id " + +" WHERE o.deleted = 0 "); + + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId "); + } + + sql.append(getSearchCriteriaString(args)); + + + logger.info("sql: "+sql.toString()); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchForWorkShop(final Map args) { + + final StringBuilder sql = new StringBuilder( + " SELECT " + +" o.id, " + +" o.code, " + +" o.type, " + +" o.ref, " + +" o.refNo, " + +" o.status, " + +" o.date, " + +" o.custId, " + +" o.fileId, " + +" o.remarks, " + +" o.outDate, " + +" o.inDate, " + +" o.outRemark, " + +" o.inRemark, " + //+" o.ignoreC, " + +" o.workshopStatus, " + +" o.inStatus, " + +" o.outStatus, " + +" DATE_ADD(o.targetCompleteDate, INTERVAL -2 day) AS targetCompleteDate, " + +" c.email, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" concat_ws(' ', c.firstName ,c.surname, c.nameCh) AS customerName " + +" FROM orders o " + +" LEFT JOIN customer c ON c.id = o.custId " + +" WHERE o.deleted = 0 AND o.workshopStatus IS NOT NULL "); + + sql.append(getSearchCriteriaString(args)); + + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId "); + } + + if(args.containsKey("stockInStatus")) + sql.append(" AND o.outStatus = :stockInStatus "); + + sql.append(" ORDER BY o.outDate DESC, o.id DESC "); + + if (args != null) { + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map countSearchForWorkshop(final Map args) { + + StringBuilder sql = new StringBuilder( + " SELECT " + +" COUNT(o.id) AS count " + +" FROM orders o " + +" LEFT JOIN customer c ON c.id = o.custId " + +" WHERE o.deleted = 0 AND o.workshopStatus IS NOT NULL "); + + sql.append(getSearchCriteriaString(args)); + + args.put("sysGroupId", SecurityUtils.getUser().getSysGroupId()); + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId "); + } + + if(args.containsKey("stockInStatus")) + sql.append(" AND o.outStatus = :stockInStatus "); + + logger.info("sql: "+sql.toString()); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map queryForMap(final Integer id) { + final String sql = "SELECT o.*, concat(o.type, o.code) As orderNo FROM orders o WHERE o.id = :id"; + + return jdbcDao.queryForMap(sql, MapUtils.toHashMap(Params.ID, id)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void insertLog (String tableName, int recordId, Integer modifiedBy, Date modified, String oldData, String newData) { + + final String sql = "INSERT INTO audit_log (`tableName`, `recordId`, `modifiedBy`, `modified`, `oldData`, `newData`) " + + "VALUES (:tableName, :recordId, :modifiedBy, :modified, :oldData, :newData)"; + + jdbcDao.queryForMap(sql, MapUtils.toHashMap("tableName", tableName, + "recordId", recordId, + "modifiedBy", modifiedBy, + "modified", modified, + "oldData", oldData, + "newData", newData)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void updateChildOrder(final Order parentOrder) throws JsonProcessingException { + int id = parentOrder.getId(); + String orderNo = parentOrder.getType()+parentOrder.getCode(); + int status = parentOrder.getStatus(); + + List> childList = findChild(id); + for(Map child: childList){ + Map diff = new HashMap(); + if(!child.get("status").equals(status)) diff.put("status", status); + if(!child.get("refNo").equals(orderNo)) diff.put("refNo", orderNo); + if(!child.get("ref").equals(id)) diff.put("ref", id); + if(diff.size()>0){ + log(LogUtils.ACTION_UPDATE, NumberUtils.toInt(child.get("id"),-1), diff); + } + } + + final String sql = "UPDATE orders o SET " + +" o.refNo = :orderNo, " + +" o.targetCompleteDate = IF( '"+Order.STATUS_COMPLETED+"' = :status , NULL, o.targetCompleteDate), " + +" o.status = :status " + +" WHERE o.ref = :orderId "; + jdbcDao.executeUpdate(sql, + MapUtils.toHashMap( + "orderId", id, + "orderNo", orderNo, + "status", status)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> findChild(int parentOrderId) { + final String sql = " SELECT o.* FROM orders o WHERE o.ref = :orderId "; + return jdbcDao.queryForList(sql,MapUtils.toHashMap("orderId", parentOrderId)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public List> apiSearch(final Map args){ + //@formatter:off + final StringBuilder sql = new StringBuilder(); + //@formatter:on + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void deletedOrder(Integer id) throws JsonProcessingException{ + Order instance = find(id); + instance.setDeleted(true); + saveOrUpdate(instance); + log(LogUtils.ACTION_DELETE, id, instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, Order newRecord, Order oldRecord)throws JsonProcessingException { + Map data = new HashMap<>(); + Map compare = LogUtils.compare(newRecord, oldRecord); + data = (Map)compare.get(LogUtils.DIFF); + log(action, id, data); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, Map data)throws JsonProcessingException { + if(data.size()<=0) return; + ObjectMapper mapper = new ObjectMapper(); + auditLogService.save("orders", + id, + SecurityUtils.getUser().getId(), + new Date(), + action, + mapper.writeValueAsString(data)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(int userId, String action, int id, Map data)throws JsonProcessingException { + if(data.size()<=0) return; + ObjectMapper mapper = new ObjectMapper(); + auditLogService.save("orders", + id, + userId, + new Date(), + action, + mapper.writeValueAsString(data)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, Order newRecord)throws JsonProcessingException { + Map data = LogUtils.filter(LogUtils.objectToMap(newRecord)); + log(action, id, data); + } + + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchOrderByTypeNCode(Map args) { + + final StringBuilder sql = new StringBuilder( + " SELECT * FROM orders o WHERE o.deleted = 0 AND o.status NOT IN("+Order.STATUS_IGNORE +", "+Order.STATUS_CANCELLED+") AND o.type = :type AND o.code = :code AND o.id != :id"); + + return jdbcDao.queryForList(sql.toString(), args); + } + +} diff --git a/src/main/java/com/ffii/tls/order/service/PaymentService.java b/src/main/java/com/ffii/tls/order/service/PaymentService.java new file mode 100644 index 0000000..81ad3be --- /dev/null +++ b/src/main/java/com/ffii/tls/order/service/PaymentService.java @@ -0,0 +1,116 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.service; + +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import com.fasterxml.jackson.core.JsonProcessingException; +import com.fasterxml.jackson.databind.ObjectMapper; +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.log.service.AuditLogService; +import com.ffii.tbms.order.Payment; +import com.ffii.tbms.order.dao.PaymentDao; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * @author Patrick + */ +@Service +public class PaymentService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private PaymentDao paymentDao; + + @Autowired + private AuditLogService auditLogService; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(Payment instance) { + return paymentDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Payment find(Integer id) { + return paymentDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + StringBuilder sql = new StringBuilder( + " SELECT p.id, " + +" p.orderId, " + +" p.date, " + +" p.amount, " + +" p.method, " + +" p.refNo " + +" FROM payment p " + +" WHERE p.deleted = 0 "); + + if (args != null) { + if (args.containsKey("orderId")) + sql.append(" AND p.orderId = :orderId "); + } + + sql.append(" ORDER BY p.id "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map queryForMap(Integer id) { + String sql = "SELECT * FROM payment p WHERE p.id = :id"; + + return jdbcDao.queryForMap(sql, MapUtils.toHashMap(Params.ID, id)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, Payment newRecord, Payment oldRecord)throws JsonProcessingException { + Map data = new HashMap<>(); + Map compare = LogUtils.compare(newRecord, oldRecord); + data = (Map)compare.get(LogUtils.DIFF); + log(action, id, data, newRecord); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, Map data, Payment newRecord)throws JsonProcessingException { + if(data.size()<=0) return; + ObjectMapper mapper = new ObjectMapper(); + auditLogService.save("payment", + id, + SecurityUtils.getUser().getId(), + new Date(), + action, + mapper.writeValueAsString(data), + newRecord.getOrderId(), + "orders"); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public void log(String action, int id, Payment newRecord)throws JsonProcessingException { + Map data = LogUtils.filter(LogUtils.objectToMap(newRecord)); + log(action, id, data, newRecord); + } + +} diff --git a/src/main/java/com/ffii/tls/order/web/InvoiceController.java b/src/main/java/com/ffii/tls/order/web/InvoiceController.java new file mode 100644 index 0000000..3f10aa8 --- /dev/null +++ b/src/main/java/com/ffii/tls/order/web/InvoiceController.java @@ -0,0 +1,186 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.web; + +import java.io.IOException; +import java.io.UnsupportedEncodingException; +import java.math.BigDecimal; +import java.text.DateFormat; +import java.text.DecimalFormat; +import java.text.SimpleDateFormat; +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.mail.internet.InternetAddress; +import javax.script.ScriptEngine; +import javax.script.ScriptEngineManager; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.jboss.jandex.UnsupportedVersion; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.core.io.ByteArrayResource; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.servlet.ModelAndView; + +import net.sf.jasperreports.engine.JRException; +import net.sf.jasperreports.engine.data.JRBeanCollectionDataSource; + +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.customer.service.CustomerService; +import com.ffii.tbms.file.FileBlob; +import com.ffii.tbms.mail.service.MailService; +import com.ffii.tbms.order.service.InvoiceService; +import com.ffii.tbms.order.service.OrderService; +import com.ffii.tbms.user.service.SysGroupService; +import com.ffii.tbms.user.service.UserService; + + +@Controller +@RequestMapping(value = "/order/invoice") +public class InvoiceController extends AbstractController { + @Autowired + private InvoiceService invoiceService; + + @Autowired + private MailService mailService; + + @Autowired + private SysGroupService sysGroupService; + + + + @RequestMapping(value = "/send", method = { RequestMethod.GET, RequestMethod.POST }) + public String sendInvoice(Model model, HttpServletRequest request, @RequestParam int orderId, + @RequestParam String subject, @RequestParam String body) + throws ServletRequestBindingException, IllegalStateException, IOException, JRException { + + Map order = invoiceService.search(orderId); + + if (order.get("email") == null || order.get("email").toString().isEmpty()) { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + model.addAttribute(Params.MSG, "Email Invalid."); + return JsonView.NAME; + } + + InternetAddress recipient = null; + try { + recipient = new InternetAddress(order.get("Email").toString(),""); + //recipient = new InternetAddress("hmiufong@gmail.com", ""); + } catch (UnsupportedVersion e) { + // omg wtf cannot create InternetAddress + e.printStackTrace(); + } catch (UnsupportedEncodingException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + + if (recipient != null) { + + mailService.sendSystemMail( + SecurityUtils.getUser().getSysGroupId(), + mailService.getFromAddress(SecurityUtils.getUser().getSysGroupId()), + MailService.FIX_RECIPIENT, + recipient, + subject, + "mail/contentMail.ftl", + MapUtils.toHashMap("content",body), + "invoice.pdf", + new ByteArrayResource(invoiceService.genInvoice(orderId))); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + + @RequestMapping(value = "/get-cust-contact", method = { RequestMethod.GET, RequestMethod.POST }) + public String getCustContact(Model model, HttpServletRequest request, @RequestParam int orderId) throws ServletRequestBindingException, IllegalStateException, IOException, JRException { + + SimpleDateFormat df = new SimpleDateFormat("dd MMMM yyyy"); + DecimalFormat decimalFormat = new DecimalFormat("#,##0.00"); + + Map data = invoiceService.search(orderId); + BigDecimal amount = (BigDecimal)invoiceService.getOrderItemTotalAmount(orderId).get("totalAmount"); + amount = amount == null? BigDecimal.ZERO: amount; + String subject = invoiceService.getTemplateSubject(); + subject = subject.replaceAll("\\{\\$orderNo\\}",data.get("orderNo").toString()); + subject = subject.replaceAll("\\{\\$orderDate\\}",df.format(data.get("orderDate"))); + subject = subject.replaceAll("\\{\\$amount\\}","\\$ "+decimalFormat.format(amount)); + subject = subject.replaceAll("\\{\\$today\\}",df.format(new Date())); + subject = subject.replaceAll("\\{\\$nameCh\\}",data.get("nameCh")==null?"":data.get("nameCh").toString()); + subject = subject.replaceAll("\\{\\$firstName\\}",data.get("firstName")==null?"":data.get("firstName").toString()); + subject = subject.replaceAll("\\{\\$surname\\}",data.get("surname")==null?"":data.get("surname").toString()); + data.put("subject", subject); + String body = invoiceService.getTemplateBody(); + body = body.replaceAll("\\{\\$orderNo\\}",data.get("orderNo").toString()); + body = body.replaceAll("\\{\\$orderDate\\}",df.format(data.get("orderDate"))); + body = body.replaceAll("\\{\\$amount\\}","\\$ "+decimalFormat.format(amount)); + body = body.replaceAll("\\{\\$today\\}",df.format(new Date())); + body = body.replaceAll("\\{\\$nameCh\\}",data.get("nameCh")==null?"":data.get("nameCh").toString()); + body = body.replaceAll("\\{\\$firstName\\}",data.get("firstName")==null?"":data.get("firstName").toString()); + body = body.replaceAll("\\{\\$surname\\}",data.get("surname")==null?"":data.get("surname").toString()); + data.put("body", body); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.AUTH, Boolean.TRUE); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + + @RequestMapping(value = "/invoice.pdf", method = { RequestMethod.GET,RequestMethod.POST }) + public ModelAndView DreamBespokeInvoice(Model model, HttpServletRequest request, HttpServletResponse response, + @RequestParam int orderId) throws Exception { + + Map params = invoiceService.getInvoicePdfParams(orderId); + + List> list = invoiceService.getOrderItems(orderId); + + if(list == null || list.size()==0){ + for(int i =0; i<12; i++) + list.add(new HashMap()); + }else{ + int line = 12-list.size(); + for(int i = 0; i()); + } + + params.put("dataSource", new JRBeanCollectionDataSource(list)); + + + ScriptEngineManager manager = new ScriptEngineManager(); + ScriptEngine engine = manager.getEngineByName("js"); + Object result = engine.eval("4.0*5"); + + return new ModelAndView("invoiceTemp", params); + } + + +} diff --git a/src/main/java/com/ffii/tls/order/web/OrderController.java b/src/main/java/com/ffii/tls/order/web/OrderController.java new file mode 100644 index 0000000..65d5c2d --- /dev/null +++ b/src/main/java/com/ffii/tls/order/web/OrderController.java @@ -0,0 +1,700 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.web; + +import java.math.BigDecimal; +import java.util.ArrayList; +import java.util.Date; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.apache.commons.lang3.SerializationUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.security.crypto.password.StandardPasswordEncoder; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.customer.Customer; +import com.ffii.tbms.customer.service.CustomerService; +import com.ffii.tbms.file.FileRefType; +import com.ffii.tbms.file.service.FileService; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.log.service.AuditLogService; +import com.ffii.tbms.order.Order; +import com.ffii.tbms.order.service.OrderService; + +@Controller +@RequestMapping(value = "/order") +public class OrderController extends AbstractController { + + @Autowired + private OrderService orderService; + + @Autowired + private FileService fileService; + + @Autowired + private CustomerService customerService; + + @Autowired + private StandardPasswordEncoder passwordEncoder; + + @RequestMapping(value = "/save", method = RequestMethod.POST) + public String save(final Model model, final HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") || SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + Order instance; + Order oldRecord = new Order(); + if (id > 0) { + instance = orderService.find(id); + oldRecord = SerializationUtils.clone(instance); + } else { + instance = new Order(); + } + + ServletRequestUtils.doBind(request, instance, null); + if(instance.getStatus() != Order.STATUS_ON_HAND){ + instance.setTargetCompleteDate(null); + } + + id = orderService.saveOrUpdate(instance); + + if(oldRecord.getId() != null){ + orderService.log(LogUtils.ACTION_UPDATE, id, instance, oldRecord); + }else{ + orderService.log(LogUtils.ACTION_CREATE, id, instance); + } + + orderService.updateChildOrder(instance); + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/delete", method = RequestMethod.POST) + public String delete(final Model model, final HttpServletRequest request, @RequestParam final Integer id) + throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + + // find, mark delete, and save + orderService.deletedOrder(id); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String load(final Model model, final HttpServletRequest request, @RequestParam final Integer id) + throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") || SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + final Map data = orderService.queryForMap(id); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/combo.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String comboJson(final Model model, final HttpServletRequest request) throws Exception { + + final Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addInteger(request, args, "custId"); + CriteriaUtils.addStringLike(request, args, Params.QUERY); + + final List> records = orderService.searchForCombo(args); + + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(final Model model, final HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") || SecurityUtils.isGranted("CUSTOMER_MAINTAIN")) { + final Map args = new HashMap(); + + CriteriaUtils.addStringLike(request, args, Params.QUERY); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addString(request, args, "orderType"); + CriteriaUtils.addStringLike(request, args, "orderCode"); + CriteriaUtils.addStringLike(request, args, "firstName"); + CriteriaUtils.addStringLike(request, args, "surname"); + CriteriaUtils.addStringLike(request, args, "nameCh"); + CriteriaUtils.addStringLike(request, args, "emailPhone"); + CriteriaUtils.addDate(request, args, "fromDate"); + CriteriaUtils.addDateTo(request, args, "toDate"); + CriteriaUtils.addStringLike(request, args, "itemName"); + CriteriaUtils.addInteger(request, args, "custId"); + CriteriaUtils.addInteger(request, args, "status"); + CriteriaUtils.addBoolean(request, args, "balance"); + //CriteriaUtils.addBoolean(request, args, "showIgnored"); + CriteriaUtils.addDate(request, args, "targetCompleteDateFrom"); + CriteriaUtils.addDateTo(request, args, "targetCompleteDateTo"); + CriteriaUtils.addInteger(request, args, "start"); + CriteriaUtils.addInteger(request, args, "limit"); + + + String orderNos = ServletRequestUtils.getStringParameter(request, "orderNo"); + String orderNoStr = getSearchOrderString(orderNos); + if((orderNos!=null && !orderNos.equals("")) + && (orderNoStr==null || orderNoStr.equals(""))){ + model.addAttribute(Params.RECORDS, new ArrayList<>()); + model.addAttribute("total", 0); + model.addAttribute("totalAmount",0); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + }else if(orderNos!=null && !orderNos.equals("")){ + args.put("orderNoStr", orderNoStr); + } + List> records = orderService.search(args); + Map count = orderService.countSearch(args); + Map totalAmount = orderService.sumTotalAmount(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("total", NumberUtils.intValue(count.get("count"))); + model.addAttribute("totalAmount", NumberUtils.toDecimal(totalAmount.get("totalAmount"),BigDecimal.ZERO)); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + private String getSearchOrderString(String orderNoStr){ + if(orderNoStr==null) return ""; + String str = ""; + String[] orderArray = orderNoStr.trim().split(","); + for(String orderNo: orderArray){ + if(!str.equals("")){ + str = str + " OR "; + } + String[] orderRange = orderNo.trim().split("to"); + if(orderRange.length>1){ + String[] from = orderRange[0].trim().split("[^A-Za-z0-9]+|(?<=[A-Za-z])(?=[0-9])|(?<=[0-9])(?=[A-Za-z])"); + String[] to = orderRange[1].trim().split("[^A-Za-z0-9]+|(?<=[A-Za-z])(?=[0-9])|(?<=[0-9])(?=[A-Za-z])"); + Integer fromCode, toCode; + String type; + if(from.length<2) return ""; + + type = from[0]+"-"; + fromCode = NumberUtils.toInt(from[1], null); + if(fromCode == null) return ""; + + if(to.length==0) + return ""; + if(to.length==1) + toCode = NumberUtils.toInt(to[0], null); + else + toCode = NumberUtils.toInt(to[1], null); + if(toCode == null) return ""; + + str = str+" (o.type ='"+type+"' AND o.code >="+fromCode+" AND o.code <= "+toCode+") "; + }else{ + String[] orderTypeCode = orderNo.trim().split("[^A-Za-z0-9]+|(?<=[A-Za-z])(?=[0-9])|(?<=[0-9])(?=[A-Za-z])"); + if(orderTypeCode.length>1){ + str = str+" (o.type ='"+orderTypeCode[0]+"-' AND o.code = "+orderTypeCode[1]+") "; + }else if(NumberUtils.toInt(orderTypeCode[0], null)!= null){ + str = str+" o.code = "+orderTypeCode[0]+" "; + }else{ + str = str+" o.type = '"+orderTypeCode[0]+"-' "; + } + + } + } + + logger.info("orderNoStr : "+str); + + return " AND ( "+str+" ) "; + } + + @RequestMapping(value = "/list-for-workshop.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listForWorkshopJson(final Model model, final HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + final Map args = new HashMap(); + + CriteriaUtils.addStringLike(request, args, Params.QUERY); + + CriteriaUtils.addInteger(request, args, Params.ID); + + CriteriaUtils.addStringLike(request, args, "firstName"); + CriteriaUtils.addStringLike(request, args, "surname"); + CriteriaUtils.addStringLike(request, args, "nameCh"); + CriteriaUtils.addStringLike(request, args, "emailPhone"); + CriteriaUtils.addDate(request, args, "fromOutDate"); + CriteriaUtils.addDateTo(request, args, "toOutDate"); + CriteriaUtils.addInteger(request, args, "workshopStatus"); + CriteriaUtils.addInteger(request, args, "stockInStatus"); + //CriteriaUtils.addBoolean(request, args, "showIgnored"); + CriteriaUtils.addDate(request, args, "workshopTargetDateFrom"); + CriteriaUtils.addDateTo(request, args, "workshopTargetDateTo"); + + CriteriaUtils.addInteger(request, args, "start"); + CriteriaUtils.addInteger(request, args, "limit"); + + //args.put("showIgnored", true); + + + String orderNos = ServletRequestUtils.getStringParameter(request, "orderNo"); + String orderNoStr = getSearchOrderString(orderNos); + if((orderNos!=null && !orderNos.equals("")) + && (orderNoStr==null || orderNoStr.equals(""))){ + model.addAttribute(Params.RECORDS, new ArrayList<>()); + model.addAttribute("total", 0); + model.addAttribute("totalAmount",0); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + }else if(orderNos!=null && !orderNos.equals("")){ + args.put("orderNoStr", orderNoStr); + } + final List> records = orderService.searchForWorkShop(args); + final Map count = orderService.countSearchForWorkshop(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("total", NumberUtils.intValue(count.get("count"))); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/list/on-hand", method = RequestMethod.POST) + public String onHandOrders(final Model model, final HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + final int[] ids = ServletRequestUtils.getIntParameters(request, "ids"); + if (ids != null) { + for (int id : ids) { + final Order instance = orderService.find(id); + instance.setStatus(Order.STATUS_ON_HAND); + id = orderService.saveOrUpdate(instance); + orderService.log(LogUtils.ACTION_UPDATE, + id, + MapUtils.toHashMap("statue", Order.STATUS_ON_HAND)); + orderService.updateChildOrder(instance); + } + } + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/list/complete", method = RequestMethod.POST) + public String completeOrders(final Model model, final HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + final int[] ids = ServletRequestUtils.getIntParameters(request, "ids"); + if (ids != null) { + for (int id : ids) { + final Order instance = orderService.find(id); + instance.setStatus(Order.STATUS_COMPLETED); + instance.setTargetCompleteDate(null); + id = orderService.saveOrUpdate(instance); + orderService.log(LogUtils.ACTION_UPDATE, + id, + MapUtils.toHashMap("statue", Order.STATUS_COMPLETED)); + orderService.updateChildOrder(instance); + } + } + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/list/cancel", method = RequestMethod.POST) + public String cancelOrders(final Model model, final HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") && SecurityUtils.isGranted("ORDER_CANCEL")) { + final int[] ids = ServletRequestUtils.getIntParameters(request, "ids"); + if (ids != null) { + for (int id : ids) { + final Order instance = orderService.find(id); + instance.setStatus(Order.STATUS_CANCELLED); + instance.setTargetCompleteDate(null); + id = orderService.saveOrUpdate(instance); + orderService.log(LogUtils.ACTION_UPDATE, + id, + MapUtils.toHashMap("statue", Order.STATUS_CANCELLED)); + orderService.updateChildOrder(instance); + } + } + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + model.addAttribute(Params.AUTH, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/list/ignore", method = RequestMethod.POST) + public String ignoreOrders(final Model model, final HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") && SecurityUtils.isGranted("ORDER_CANCEL")) { + final int[] ids = ServletRequestUtils.getIntParameters(request, "ids"); + if (ids != null) { + for (int id : ids) { + final Order instance = orderService.find(id); + instance.setStatus(Order.STATUS_IGNORE); + instance.setTargetCompleteDate(null); + id = orderService.saveOrUpdate(instance); + orderService.log(LogUtils.ACTION_UPDATE, + id, + MapUtils.toHashMap("statue", Order.STATUS_IGNORE)); + orderService.updateChildOrder(instance); + } + } + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + model.addAttribute(Params.AUTH, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/complete", method = RequestMethod.POST) + public String complete(final Model model, final HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + Order instance; + instance = orderService.find(id); + instance.setStatus(Order.STATUS_COMPLETED); + id = orderService.saveOrUpdate(instance); + instance.setTargetCompleteDate(null); + orderService.updateChildOrder(instance); + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/workshop/list/complete", method = RequestMethod.POST) + public String workshopComplete(final Model model, final HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") || SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + final int[] ids = ServletRequestUtils.getIntParameters(request, "ids"); + if (ids != null) { + for (int id : ids) { + final Order instance = orderService.find(id); + instance.setWorkshopStatus(Order.WS_WORK_STATUS_COMPLETED); + id = orderService.saveOrUpdate(instance); + orderService.log(LogUtils.ACTION_UPDATE, + id, + MapUtils.toHashMap("workshopStatus", Order.WS_WORK_STATUS_COMPLETED)); + orderService.updateChildOrder(instance); + } + } + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/workshop/change-status", method = RequestMethod.POST) + public String workshopChangeStatus(final Model model, final HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id, Integer workshopStatus) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")|| SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + Integer outStatus = NumberUtils.toInt(ServletRequestUtils.getStringParameter(request, "outStatus"), null); + + final Order instance = orderService.find(id); + instance.setWorkshopStatus(workshopStatus); + instance.setOutStatus(outStatus); + + id = orderService.saveOrUpdate(instance); + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/cancel", method = RequestMethod.POST) + public String cancel(final Model model, final HttpServletRequest request, + @RequestParam(defaultValue = "-1") Integer id) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + final Order instance = orderService.find(id); + instance.setStatus(Order.STATUS_CANCELLED); + instance.setTargetCompleteDate(null); + id = orderService.saveOrUpdate(instance); + orderService.updateChildOrder(instance); + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/image-list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String imageListJson(final Model model, final HttpServletRequest request, @RequestParam final Integer id) + throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") || SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + final Map args = new HashMap(); + args.put("refType", FileRefType.ORDER); + args.put("refId", id); + + final List> records = fileService.searchFiles(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/get-current-ms.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String getCurrentMS(Model model, HttpServletRequest request, + @RequestParam(required = false) Integer orderId) { + + Order order = orderService.find(orderId); + + Map args = new HashMap(); + List> records = new ArrayList<>(); + if (order != null && order.getFileId() != null && order.getFileId() > 0) { + args.put("fileId", order.getFileId()); + args.put("refType", FileRefType.MEASUREMENT_SHEET); + records = fileService.searchFiles(args); + } + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "/updateindate", method = { RequestMethod.GET, RequestMethod.POST }) + public String updateInDate(Model model, HttpServletRequest request ) throws Exception { + + Integer orderId = ServletRequestUtils.getIntParameter(request, "id"); + Date inDate = ServletRequestUtils.getDateParameter(request, "inDate"); + String inRemark = ServletRequestUtils.getStringParameter(request, "inRemark"); + Integer inStatus = NumberUtils.toInt(ServletRequestUtils.getStringParameter(request, "inStatus"), null); + + Order instance = orderService.find(orderId); + ServletRequestUtils.doBind(request, instance, null); + if(Order.IN_OUT_STATUS_RECEIVED == inStatus){ + instance.setWorkshopStatus(null); + } + orderService.saveOrUpdate(instance); + + orderService.log(LogUtils.ACTION_UPDATE, + orderId, + MapUtils.toHashMap( + "inDate", instance.getInDate(), + "inRemark",instance.getInRemark(), + "workshopStatus", instance.getWorkshopStatus(), + "inStatus", instance.getInStatus() + )); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "/updateoutdate", method = { RequestMethod.GET, RequestMethod.POST }) + public String updateOutDate(Model model, HttpServletRequest request) throws Exception { + + Integer orderId = ServletRequestUtils.getIntParameter(request, "id"); + Date outDate = ServletRequestUtils.getDateParameter(request, "outDate"); + String outRemark = ServletRequestUtils.getStringParameter(request, "outRemark"); + Integer outStatus = NumberUtils.toInt(ServletRequestUtils.getStringParameter(request, "outStatus"), null); + + + Order instance = orderService.find(orderId); + ServletRequestUtils.doBind(request, instance, null); + instance.setInDate(null); + instance.setInRemark(null); + instance.setInStatus(null); + Map diff = MapUtils.toHashMap( + "outDate", instance.getOutDate(), + "outRemark", instance.getOutRemark(), + "outStatus", instance.getOutStatus(), + "inDate", instance.getInDate(), + "inRemark",instance.getInRemark(), + "inStatus",instance.getInStatus() + ); + if(instance.getWorkshopStatus() == null){ + instance.setWorkshopStatus(Order.WS_WORK_STATUS_PENDING); + diff.put("workshopStatus", instance.getWorkshopStatus()); + } + orderService.saveOrUpdate(instance); + + orderService.log(LogUtils.ACTION_UPDATE, orderId, diff); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "/workshop/updateindate", method = { RequestMethod.GET, RequestMethod.POST }) + public String updateWorkshopInDate(Model model, HttpServletRequest request ) throws Exception { + + Integer orderId = ServletRequestUtils.getIntParameter(request, "id"); + //order out = workshop in + Integer outStatus = NumberUtils.toInt(ServletRequestUtils.getStringParameter(request, "outStatus"), null); + + Order instance = orderService.find(orderId); + instance.setOutStatus(outStatus); + orderService.saveOrUpdate(instance); + + orderService.log(LogUtils.ACTION_UPDATE, + orderId, + MapUtils.toHashMap( + "outStatus", instance.getOutStatus() + )); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "/workshop/updateoutdate", method = { RequestMethod.GET, RequestMethod.POST }) + public String updateWorkshopOutDate(Model model, HttpServletRequest request) throws Exception { + + Integer orderId = ServletRequestUtils.getIntParameter(request, "id"); + + //order in = workshop out + Date inDate = ServletRequestUtils.getDateParameter(request, "inDate"); + String inRemark = ServletRequestUtils.getStringParameter(request, "inRemark"); + Integer inStatus = NumberUtils.toInt(ServletRequestUtils.getStringParameter(request, "inStatus"), null); + + + Order instance = orderService.find(orderId); + instance.setInDate(inDate); + instance.setInRemark(inRemark); + instance.setInStatus(inStatus); + + Map diff = MapUtils.toHashMap( + "inDate", instance.getInDate(), + "inRemark",instance.getInRemark(), + "inStatus",instance.getInStatus() + ); + orderService.saveOrUpdate(instance); + + orderService.log(LogUtils.ACTION_UPDATE, orderId, diff); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "/create-cust", method = { RequestMethod.GET, RequestMethod.POST }) + public String quickCreateCust(Model model, HttpServletRequest request) throws Exception { + if (SecurityUtils.isGranted("ORDER_MAINTAIN") || SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + Customer instance = new Customer(); + + ServletRequestUtils.doBind(request, instance, null); + + int id = customerService.saveOrUpdate(instance); + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + + @RequestMapping(value = "/check-order-no", method = { RequestMethod.GET, RequestMethod.POST }) + public String checkValidOrderNo(Model model, HttpServletRequest request) throws Exception { + if (SecurityUtils.isGranted("ORDER_MAINTAIN") || SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + + Map args = new HashMap(); + + CriteriaUtils.addString(request, args, "type"); + CriteriaUtils.addString(request, args, "code"); + CriteriaUtils.addInteger(request, args, "id"); + + if(!args.containsKey("id")){ + args.put("id", 0); + } + + List> orders = orderService.searchOrderByTypeNCode(args); + + model.addAttribute(Params.SUCCESS, orders == null ||orders.size()==0); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/get-auth", method = { RequestMethod.POST }) + public String getDeleteAuth(Model model, HttpServletRequest request, @RequestParam String v) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + + if(passwordEncoder.matches(v, SecurityUtils.getUser().getPassword())) + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + else + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + +} diff --git a/src/main/java/com/ffii/tls/order/web/OrderItemController.java b/src/main/java/com/ffii/tls/order/web/OrderItemController.java new file mode 100644 index 0000000..fef84ca --- /dev/null +++ b/src/main/java/com/ffii/tls/order/web/OrderItemController.java @@ -0,0 +1,129 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.apache.commons.lang3.SerializationUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.order.OrderItem; +import com.ffii.tbms.order.service.OrderItemService; + + +@Controller +@RequestMapping(value = "/order/item") +public class OrderItemController extends AbstractController { + + @Autowired + private OrderItemService orderItemService; + + @RequestMapping(value = "/save", method = RequestMethod.POST) + public String save(Model model, HttpServletRequest request, @RequestParam(defaultValue = "-1") Integer id) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + OrderItem instance; + OrderItem oldRecord = new OrderItem(); + if (id > 0) { + instance = orderItemService.find(id); + orderItemService.compare(instance, request); + oldRecord = SerializationUtils.clone(instance); + } else { + instance = new OrderItem(); + } + + ServletRequestUtils.doBind(request, instance, null); + id = orderItemService.saveOrUpdate(instance); + + if(oldRecord.getId() != null){ + orderItemService.log(LogUtils.ACTION_UPDATE, id, instance, oldRecord); + }else{ + orderItemService.log(LogUtils.ACTION_CREATE, id, instance); + } + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/delete", method = RequestMethod.POST) + public String delete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") && SecurityUtils.isGranted("ORDER_ITEM_DELETE")) { + + // find, mark delete, and save + OrderItem instance = orderItemService.find(id); + instance.setDeleted(true); + orderItemService.saveOrUpdate(instance); + + orderItemService.log("Delete", id, instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String load(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") || SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + Map data = orderItemService.queryForMap(id); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN") || SecurityUtils.isGranted("WORKSHOP_MAINTAIN")) { + Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, "orderId"); + + List> records = orderItemService.search(args); + + model.addAttribute(Params.RECORDS, records); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/order/web/PaymentController.java b/src/main/java/com/ffii/tls/order/web/PaymentController.java new file mode 100644 index 0000000..1c935b7 --- /dev/null +++ b/src/main/java/com/ffii/tls/order/web/PaymentController.java @@ -0,0 +1,130 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.order.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.apache.commons.lang3.SerializationUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.log.LogUtils; +import com.ffii.tbms.order.Payment; +import com.ffii.tbms.order.service.PaymentService; + + +@Controller +@RequestMapping(value = "/order/payment") +public class PaymentController extends AbstractController { + + @Autowired + private PaymentService paymentService; + + @RequestMapping(value = "/save", method = RequestMethod.POST) + public String save(Model model, HttpServletRequest request, @RequestParam(defaultValue = "-1") Integer id) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + Payment instance; + Payment oldRecord = new Payment(); + if (id > 0) { + instance = paymentService.find(id); + oldRecord = SerializationUtils.clone(instance); + } else { + instance = new Payment(); + } + + ServletRequestUtils.doBind(request, instance, null); + id = paymentService.saveOrUpdate(instance); + + if(oldRecord.getId()!= null){ + paymentService.log(LogUtils.ACTION_UPDATE, id, instance, oldRecord); + }else{ + paymentService.log(LogUtils.ACTION_CREATE, id, instance); + } + + model.addAttribute(Params.ID, id); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/delete", method = RequestMethod.POST) + public String delete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + + // find, mark delete, and save + Payment instance = paymentService.find(id); + instance.setDeleted(true); + paymentService.saveOrUpdate(instance); + + paymentService.log(LogUtils.ACTION_DELETE, id, instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String load(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + Map data = paymentService.queryForMap(id); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("ORDER_MAINTAIN")) { + Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, "orderId"); + + List> records = paymentService.search(args); + + model.addAttribute(Params.RECORDS, records); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/reports/service/AuditLogExportService.java b/src/main/java/com/ffii/tls/reports/service/AuditLogExportService.java new file mode 100644 index 0000000..81228c4 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/service/AuditLogExportService.java @@ -0,0 +1,52 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.service; + +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; + +/** + * @author fung + */ +@Service +public class AuditLogExportService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " al.*," + + " (SELECT name FROM users WHERE id = al.modifiedBy) 'modifiedUser'" + + " FROM audit_log al" + + " WHERE true"); + if (args != null) { + if (args.containsKey("tableName")) sql.append(" AND al.tableName = :tableName"); + if (args.containsKey("dateFrom")) sql.append(" AND al.modified >= :dateFrom"); + if (args.containsKey("dateTo")) sql.append(" AND al.modified < :dateTo"); + } + + sql.append(" ORDER BY al.modified DESC"); + + return jdbcDao.queryForList(sql.toString(), args); + } +} diff --git a/src/main/java/com/ffii/tls/reports/service/CustomerFirstOrderReportService.java b/src/main/java/com/ffii/tls/reports/service/CustomerFirstOrderReportService.java new file mode 100644 index 0000000..56cb3dc --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/service/CustomerFirstOrderReportService.java @@ -0,0 +1,106 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.service; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; + + +@Service +public class CustomerFirstOrderReportService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> search() { + + Map args = new HashMap(); + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder(" SELECT o.id AS orderId, " + +" o.custId, " + +" minOrderDate.minDate, " + +" CONCAT(o.type, o.code) AS orderNo, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName, " + +" c.phone1, " + +" c.phone2, " + +" c.email, " + +" c.address, " + +" c.companyName, " + +" c.companyAddress, " + +" c.companyEmail, " + +" c.companyPhone, " + +" c.remarks " + +" FROM orders o " + +" JOIN (SELECT MIN(_o.date) AS minDate, " + +" _o.custId FROM orders _o GROUP BY _o.custId) minOrderDate " + +" ON o.date = minOrderDate.minDate AND minOrderDate.custId = o.custId " + +" LEFT JOIN customer c ON c.id = o.custId " + +" WHERE 1=1 " + ); + + if(args != null){ + if(args.containsKey("sysGroupId")) + sql.append(" AND o.sysGroupId = :sysGroupId AND c.sysGroupId = :sysGroupId "); + } + + sql.append(" GROUP BY o.date, o.custId " + +" ORDER BY o.date , o.custId "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> searchNoOrderCustomer() { + + Map args = new HashMap(); + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder( " Select *, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) AS customerName " + +" From customer c where c.id not in ( " + +" SELECT " + +" o.custId " + +" FROM orders o " + +" JOIN (SELECT MIN(_o.date) AS minDate, " + +" _o.custId FROM orders _o GROUP BY _o.custId) minOrderDate " + +" ON o.date = minOrderDate.minDate AND minOrderDate.custId = o.custId "); + + if(args != null){ + if(args.containsKey("sysGroupId")) + sql.append(" AND o.sysGroupId = :sysGroupId "); + } + + sql.append( " GROUP BY o.date, o.custId " + +" ORDER BY o.date , o.custId " + +" ) "); + + return jdbcDao.queryForList(sql.toString(), args); + } + + +} diff --git a/src/main/java/com/ffii/tls/reports/service/CustomerReportService.java b/src/main/java/com/ffii/tls/reports/service/CustomerReportService.java new file mode 100644 index 0000000..52a4526 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/service/CustomerReportService.java @@ -0,0 +1,77 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.service; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; + + +@Service +public class CustomerReportService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder( " SELECT " + + " c.created, " + +" CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' '))) AS customerName, " + + " c.nameCh, " + + " c.phone1, " + + " c.phone2, " + + " c.email, " + + " c.address, " + + " c.remarks, " + + " co.orderAmount AS orderAmount " + + " FROM " + + " customer c " + + " LEFT JOIN " + + " (SELECT " + + " o.custId, SUM(oi.price) AS orderAmount " + + " FROM " + + " orders o " + + " LEFT JOIN order_item oi ON o.id = oi.orderId " + + " WHERE " + + " o.deleted = 0 AND oi.deleted = 0 " + + " AND (o.status = 0 OR o.status = 1) " + + " GROUP BY o.custId) co ON co.custId = c.id " + + " WHERE " + + " c.deleted = 0 " + + ); + + if(args != null){ + if(args.containsKey("sysGroupId")) + sql.append(" AND c.sysGroupId = :sysGroupId "); + } + + sql.append(" GROUP BY c.id " + + " ORDER BY c.created "); + + return jdbcDao.queryForList(sql.toString(), args); + } + +} diff --git a/src/main/java/com/ffii/tls/reports/service/OrderReportService.java b/src/main/java/com/ffii/tls/reports/service/OrderReportService.java new file mode 100644 index 0000000..9261ade --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/service/OrderReportService.java @@ -0,0 +1,114 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.service; + +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; + +/** + * @author fung + */ +@Service +public class OrderReportService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + SecurityUtils.authArgs(args); + StringBuilder sql = new StringBuilder( + " SELECT o.id, " + +" o.type, " + +" o.code, " + +" CONCAT(o.type, o.code) AS orderNo, " + +" o.date, " + +" o.status, " + +" o.remarks, " + +" o.refNo, " + +" o.custId, " + //+" o.ignoreC, " + +" c.email, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" concat_ws(' ', c.firstName ,c.surname, c.nameCh) AS customerName, " + +" _oi.orderAmount, " + +" _oi.item, " + +" _p.paymentAmount, " + +" IFNULL(_oi.orderAmount, 0) - IFNULL(_p.paymentAmount, 0) AS outstanding " + +" FROM orders o " + +" LEFT JOIN customer c ON o.custId = c.id " + +" LEFT JOIN (SELECT oi.orderId, SUM(oi.price) AS orderAmount, " + +" GROUP_CONCAT(CONCAT(oi.name, '|;', oi.price) SEPARATOR '||;') AS item " + +" FROM order_item oi WHERE oi.deleted = 0 " + +" GROUP BY oi.orderId) _oi ON _oi.orderId = o.id " + +" LEFT JOIN (SELECT p.orderId, SUM(p.amount) AS paymentAmount " + +" FROM payment p WHERE p.deleted = 0 " + +" GROUP BY p.orderId) _p ON _p.orderId = o.id " + +" WHERE o.deleted = 0 "); + + if(args != null){ + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId "); + } + + if(args.containsKey("dateFrom")) sql.append(" AND o.date >= :dateFrom "); + if(args.containsKey("dateTo")) sql.append(" AND o.date <= :dateTo "); + if(args.containsKey("orderNo")) sql.append(" AND CONCAT(o.type, o.code) Like :orderNo "); + if(args.containsKey("custName")) + sql.append(" AND CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) Like :custName "); + } + + sql.append(" ORDER BY o.date , o.id "); + + if(args != null){ + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map count(Map args) { + SecurityUtils.authArgs(args); + StringBuilder sql = new StringBuilder( + " SELECT count(o.id) AS count " + +" FROM orders o " + +" LEFT JOIN customer c ON o.custId = c.id " + +" WHERE o.deleted = 0 "); + if (args != null) { + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId "); + } + if(args.containsKey("dateFrom")) sql.append(" AND o.date >= :dateFrom "); + if(args.containsKey("dateTo")) sql.append(" AND o.date <= :dateTo "); + if(args.containsKey("orderNo")) sql.append(" AND CONCAT(o.type, o.code) Like :orderNo "); + if(args.containsKey("custName")) + sql.append(" AND CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) Like :custName "); + }; + + return jdbcDao.queryForMap(sql.toString(), args); + } + +} diff --git a/src/main/java/com/ffii/tls/reports/service/OutstandingReportService.java b/src/main/java/com/ffii/tls/reports/service/OutstandingReportService.java new file mode 100644 index 0000000..69ff4b2 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/service/OutstandingReportService.java @@ -0,0 +1,119 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.service; + +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.order.Order; + +/** + * @author fung + */ +@Service +public class OutstandingReportService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder( + " SELECT " + +" o.id AS orderId, " + +" o.custId, " + +" c.email, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" concat_ws(' ', c.firstName ,c.surname, c.nameCh) AS customerName, " + +" o.type, " + +" o.code, " + +" CONCAT(o.type, o.code) AS orderNo, " + +" o.date, " + +" o.status, " + //+" o.ignoreC, " + +" IFNULL(_oi.orderAmount, 0) AS orderAmount, " + +" IFNULL(_p.paymentAmount, 0) AS paymentAmount, " + +" IFNULL(_oi.orderAmount, 0) - IFNULL(_p.paymentAmount, 0) AS outstanding " + +" FROM customer c " + +" LEFT JOIN orders o ON o.custId = c.id " + +" LEFT JOIN (SELECT oi.orderId, SUM(oi.price) AS orderAmount " + +" FROM order_item oi WHERE oi.deleted = 0 " + +" GROUP BY oi.orderId) _oi ON _oi.orderId = o.id " + +" LEFT JOIN (SELECT p.orderId, SUM(p.amount) AS paymentAmount " + +" FROM payment p WHERE p.deleted = 0 " + +" GROUP BY p.orderId) _p ON _p.orderId = o.id " + +" WHERE o.deleted = 0 AND o.ref IS NULL AND o.status != "+Order.STATUS_CANCELLED+" " + +" AND (IFNULL(_oi.orderAmount, 0) != IFNULL(_p.paymentAmount, 0) OR o.status="+Order.STATUS_ON_HAND+" ) "); + + if(args != null){ + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId AND c.sysGroupId = :sysGroupId "); + } + if(args.containsKey("orderNo")) sql.append(" AND CONCAT(o.type, o.code) Like :orderNo "); + if(args.containsKey("custName")) + sql.append(" AND CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) Like :custName "); + } + + sql.append(" ORDER BY o.date , o.id "); + if(args != null){ + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map count(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder( + " SELECT count(*) AS count " + +" FROM customer c " + +" LEFT JOIN orders o ON o.custId = c.id " + +" LEFT JOIN (SELECT oi.orderId, SUM(oi.price) AS orderAmount " + +" FROM order_item oi WHERE oi.deleted = 0 " + +" GROUP BY oi.orderId) _oi ON _oi.orderId = o.id " + +" LEFT JOIN (SELECT p.orderId, SUM(p.amount) AS paymentAmount " + +" FROM payment p WHERE p.deleted = 0 " + +" GROUP BY p.orderId) _p ON _p.orderId = o.id " + +" WHERE o.deleted = 0 AND o.ref IS NULL AND o.status != "+Order.STATUS_CANCELLED+" " + +" AND ( IFNULL(_oi.orderAmount, 0) != IFNULL(_p.paymentAmount, 0) OR o.status="+Order.STATUS_ON_HAND+" ) "); + if (args != null) { + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId "); + } + if(args.containsKey("orderNo")) sql.append(" AND CONCAT(o.type, o.code) Like :orderNo "); + if(args.containsKey("custName")) + sql.append(" AND CONCAT(IF(c.firstName IS NULL, '', CONCAT(c.firstName, ' ')), " + +" IF(c.surname IS NULL, '', CONCAT(c.surname, ' ')), " + +" IF(c.nameCh IS NULL, '', c.nameCh)) Like :custName "); + }; + + return jdbcDao.queryForMap(sql.toString(), args); + } + +} diff --git a/src/main/java/com/ffii/tls/reports/service/PaymentReportService.java b/src/main/java/com/ffii/tls/reports/service/PaymentReportService.java new file mode 100644 index 0000000..8b1572a --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/service/PaymentReportService.java @@ -0,0 +1,122 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.service; + +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.order.Order; + +/** + * @author fung + */ +@Service +public class PaymentReportService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder( + " SELECT o.id AS orderId, " + +" p.id AS paymentId, " + +" o.date AS orderDate, " + +" MAX(p.date) AS paymentDate, " + +" o.type, " + +" o.code, " + +" CONCAT(o.type, o.code) AS orderNo, " + +" o.refNo AS orderRef, " + +" c.id AS custId, " + +" c.email, " + +" concat_ws(' / ', c.phone1, c.phone2) AS phone, " + +" concat_ws(' ', c.firstName ,c.surname, c.nameCh) AS customerName, " + +" o.status AS orderStatus, " + +" _o.orderAmount, " + +" SUM(p.amount) AS paymentAmount " + +" FROM payment p " + +" LEFT JOIN orders o ON p.orderId = o.id " + +" LEFT JOIN customer c ON c.id = o.custId " + +" LEFT JOIN (SELECT oi.orderId, " + +" SUM(oi.price) AS orderAmount " + +" FROM order_item oi WHERE oi.deleted = 0 " + +" GROUP BY oi.orderId) _o ON _o.orderId = o.id " + +" WHERE o.deleted = 0 AND p.deleted = 0 AND o.id IS NOT NULL AND o.status >= "+Order.STATUS_CANCELLED+" "); + if (args != null) { + if (args.containsKey("dateFrom")) sql.append(" AND p.date >= :dateFrom "); + if (args.containsKey("dateTo")) sql.append(" AND p.date <= :dateTo "); + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId AND p.sysGroupId = :sysGroupId "); + } + } + + sql.append(" GROUP BY o.id ORDER BY paymentDate ASC, o.id ASC "); + + if(args != null){ + if (args.containsKey("start") && args.containsKey("limit")) + sql.append(" LIMIT :start, :limit "); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map count(Map args) { + + SecurityUtils.authArgs(args); + StringBuilder sql = new StringBuilder( + " SELECT count(distinct o.id) As count " + +" FROM payment p " + +" LEFT JOIN orders o ON p.orderId = o.id " + +" WHERE o.deleted = 0 AND p.deleted = 0 AND o.id IS NOT NULL AND o.status >= "+Order.STATUS_CANCELLED+" "); + if (args != null) { + if (args.containsKey("dateFrom")) sql.append(" AND p.date >= :dateFrom "); + if (args.containsKey("dateTo")) sql.append(" AND p.date <= :dateTo "); + if(args.containsKey("sysGroupId")){ + sql.append(" AND o.sysGroupId = :sysGroupId AND p.sysGroupId = :sysGroupId "); + } + }; + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map searchCurrentPayment(int orderId) { + + Map args = MapUtils.toHashMap("orderId", orderId); + SecurityUtils.authArgs(args); + + StringBuilder sql = new StringBuilder( + " SELECT SUM(p.amount) AS currentPayment FROM payment p WHERE p.deleted = 0 AND p.orderId = :orderId "); + + if (args != null) { + if(args.containsKey("sysGroupId")){ + sql.append(" AND p.sysGroupId = :sysGroupId "); + } + }; + + return jdbcDao.queryForMap(sql.toString(), args); + } + + +} diff --git a/src/main/java/com/ffii/tls/reports/view/AuditLogExportExcelView.java b/src/main/java/com/ffii/tls/reports/view/AuditLogExportExcelView.java new file mode 100644 index 0000000..d13a2ff --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/view/AuditLogExportExcelView.java @@ -0,0 +1,118 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.view; + +import java.util.Date; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import com.ffii.core.utils.ExcelUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.view.document.AbstractExcelView; + +import org.apache.poi.ss.usermodel.Cell; +import org.apache.poi.ss.usermodel.CellStyle; +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; + +/** + * @author fung + */ +public class AuditLogExportExcelView extends AbstractExcelView { + + protected Date printDate; + protected final String REPORT_CODE = "NEW Report"; + protected final String REPORT_NAME = "Audit Log Export"; + + protected CellStyle normalStyle; + protected CellStyle wrapTextStyle; + + @SuppressWarnings("unchecked") + @Override + protected void buildExcelDocument(Map model, Workbook workbook, HttpServletRequest request, + HttpServletResponse response) throws Exception { + printDate = new Date(); + response.setHeader("Content-Disposition", + "attachment; filename=\"" + response.encodeURL(REPORT_CODE + " - " + REPORT_NAME + "_") + ".xlsx\""); + Sheet sheet = workbook.getSheetAt(0); + // CommonReportUtils.setPageForAllColWidth(sheet, Boolean.FALSE); + createStyle(workbook); + + // get Data + List> records = (List>) model.get(Params.RECORDS); + + int rowIndex = 1; + for (int i = 0; i < records.size(); i++) { + Map record = records.get(i); + int colIndex = 0; + + setCellValue(sheet, rowIndex, colIndex++, record.get("tableName"), normalStyle); + setCellValue(sheet, rowIndex, colIndex++, record.get("recordId"), normalStyle); + setCellValue(sheet, rowIndex, colIndex++, record.get("modifiedBy"), normalStyle); + setCellValue(sheet, rowIndex, colIndex++, record.get("modifiedUser"), normalStyle); + // setCellValue(sheet, rowIndex, colIndex++, + // CommonReportUtils.getDatetimeStr((Date) record.get("modified")), + // normalStyle); + + int nRowIndex = printFields(sheet, (String) record.get("newData"), rowIndex, colIndex++); + int oRowIndex = printFields(sheet, (String) record.get("oldData"), rowIndex, colIndex++); + + rowIndex = nRowIndex > oRowIndex ? nRowIndex : oRowIndex; + rowIndex++; + } + } + + protected void createStyle(Workbook workbook) { + normalStyle = workbook.createCellStyle(); + wrapTextStyle = workbook.createCellStyle(); + + // Font font = workbook.createFont(); + // font.setFontHeightInPoints(CommonReportUtils.TEXT_SIZE); + // font.setFontName(CommonReportUtils.TEXT_FONT_NAME); + // normalStyle.setFont(font); + + // wrapTextStyle.setFont(font); + wrapTextStyle.setWrapText(Boolean.TRUE); + } + + protected int printFields(Sheet sheet, String jsonStr, int rowIndex, final int COL_INDEX) { + // if (StringUtils.isNotBlank(jsonStr)) { + // try { + // Map map = JsonUtils.fromJsonString(jsonStr, Map.class); + // for (String k : map.keySet()) { + // if ("created".equals(k)||"modified".equals(k)) { + + // }else { + + // } + // setCellValue(sheet, rowIndex, COL_INDEX, k + ": " + + // CommonReportUtils.getValue(map.get(k)), wrapTextStyle); + // sheet.getRow(rowIndex++).setHeight((short) -1); + // } + // } catch (Exception e) { + // setCellValue(sheet, rowIndex, COL_INDEX, "json error: " + jsonStr, wrapTextStyle); + // sheet.getRow(rowIndex++).setHeight((short) -1); + // } + // } + return rowIndex; + } + + protected void setCellValue(Sheet sheet, int rowIndex, int colIndex, Object value, CellStyle style) { + if (style != null) { + Cell cell = ExcelUtils.getCell(sheet, rowIndex, colIndex); + cell.setCellStyle(style); + ExcelUtils.setCellValue(cell, value); + } else { + ExcelUtils.setCellValue(sheet, rowIndex, colIndex, value); + } + } +} diff --git a/src/main/java/com/ffii/tls/reports/view/CustomerFirstOrderReportExcelView.java b/src/main/java/com/ffii/tls/reports/view/CustomerFirstOrderReportExcelView.java new file mode 100644 index 0000000..7426e99 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/view/CustomerFirstOrderReportExcelView.java @@ -0,0 +1,122 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.view; + +import java.util.Date; +import java.util.List; +import java.util.Map; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; +import com.ffii.core.utils.ExcelUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.view.document.AbstractExcelView; +import com.ibm.icu.text.SimpleDateFormat; + +import org.apache.poi.hssf.usermodel.HSSFHeader; +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; + +public class CustomerFirstOrderReportExcelView extends AbstractExcelView { + + protected Date printDate; + protected final String REPORT_NAME = "Customer First Order Report"; + + @SuppressWarnings("unchecked") + @Override + protected void buildExcelDocument(Map model, Workbook workbook, HttpServletRequest request, + HttpServletResponse response) throws Exception { + printDate = new Date(); + String pattern = "yyyy-MM-dd"; + SimpleDateFormat simpleDateFormat = new SimpleDateFormat(pattern); + String todayStr = simpleDateFormat.format(printDate); + response.setHeader("Content-Disposition", + "attachment; filename=\"" + response.encodeURL(REPORT_NAME + "_"+todayStr) + ".xlsx\""); + Sheet sheet = workbook.getSheetAt(0); + // get Data + List> records = (List>) model.get(Params.RECORDS); + String reportHeader = (String)model.get("reportHeader"); + + sheet.getHeader().setCenter(HSSFHeader.font("Calibri", "bold")+(reportHeader==null?"":reportHeader)+"\n"+REPORT_NAME); + + + int rowIndex = 1; + for (int i = 0; i < records.size(); i++) { + Map record = records.get(i); + int colIndex = 0; + + if(rowIndex>1){ + ExcelUtils.copyAndInsertRow(workbook, sheet, 1, rowIndex); + } + + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, i+1); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("minDate")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("orderNo")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("customerName")); + String phone = ""; + if(record.get("phone1") != null ){ + phone = record.get("phone1").toString().trim(); + } + if(record.get("phone2") != null ){ + phone = phone.equals("")?record.get("phone2").toString():"/"+record.get("phone2").toString(); + } + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, phone); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("email")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("address")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("companyName")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("companyPhone")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("companyEmail")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("companyAddress")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("remarks")); + sheet.getRow(rowIndex).setHeightInPoints(-1); + rowIndex++; + } + + List> noOrderList = (List>) model.get("noOrderList"); + + if(noOrderList == null || noOrderList.size()<=0) return; + + for (int i = 0; i < noOrderList.size(); i++) { + Map record = noOrderList.get(i); + int colIndex = 0; + + if(i==0){ + rowIndex++; + ExcelUtils.copyAndInsertRow(workbook, sheet, 1, rowIndex); + ExcelUtils.addMergedRegion(sheet, rowIndex-1, rowIndex-1, 0, 3); + ExcelUtils.setCellValue(sheet, rowIndex-1, 0, "Not Order Yet"); + }else{ + ExcelUtils.copyAndInsertRow(workbook, sheet, 1, rowIndex); + } + + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, i+1); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, "--"); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, "--"); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("customerName")); + String phone = ""; + if(record.get("phone1") != null ){ + phone = record.get("phone1").toString().trim(); + } + if(record.get("phone2") != null ){ + phone = phone.equals("")?record.get("phone2").toString():"/"+record.get("phone2").toString(); + } + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, phone); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("email")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("address")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("companyName")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("companyPhone")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("companyEmail")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("companyAddress")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("remarks")); + sheet.getRow(rowIndex).setHeightInPoints(-1); + rowIndex++; + } + + + } +} diff --git a/src/main/java/com/ffii/tls/reports/view/CustomerReportExcelView.java b/src/main/java/com/ffii/tls/reports/view/CustomerReportExcelView.java new file mode 100644 index 0000000..f328c39 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/view/CustomerReportExcelView.java @@ -0,0 +1,85 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.view; + +import java.util.Date; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import com.ffii.core.utils.ExcelUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.view.document.AbstractExcelView; +import com.ffii.tbms.order.Order; +import com.ibm.icu.text.SimpleDateFormat; + +import org.apache.poi.hssf.usermodel.HSSFHeader; +import org.apache.poi.ss.usermodel.CellStyle; +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; + +public class CustomerReportExcelView extends AbstractExcelView { + + protected Date printDate; + protected final String REPORT_NAME = "Customer Report"; + + protected CellStyle normalStyle; + protected CellStyle wrapTextStyle; + + @SuppressWarnings("unchecked") + @Override + protected void buildExcelDocument(Map model, Workbook workbook, HttpServletRequest request, + HttpServletResponse response) throws Exception { + + SecurityUtils.getUser(); + printDate = new Date(); + String pattern = "yyyy-MM-dd"; + SimpleDateFormat simpleDateFormat = new SimpleDateFormat(pattern); + String todayStr = simpleDateFormat.format(printDate); + response.setHeader("Content-Disposition", + "attachment; filename=\"" + response.encodeURL(REPORT_NAME + "_"+todayStr) + ".xlsx\""); + Sheet sheet = workbook.getSheetAt(0); + // get Data + List> records = (List>) model.get(Params.RECORDS); + String reportHeader = (String)model.get("reportHeader"); + Map map = (Map) model.get("map"); + + sheet.getHeader().setCenter(HSSFHeader.font("Calibri", "bold")+(reportHeader==null?"":reportHeader)+"\n"+REPORT_NAME+" (" + +simpleDateFormat.format(map.get("dateFrom"))+" - " + +simpleDateFormat.format(map.get("dateTo"))+")"); + + int rowIndex = 1; + for (int i = 0; i < records.size(); i++) { + Map record = records.get(i); + int colIndex = 0; + + if(rowIndex>1){ + ExcelUtils.copyAndInsertRow(workbook, sheet, 1, rowIndex); + } + + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, i+1); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("created")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("customerName")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("nameCh")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("phone1")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("phone2")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("email")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("address")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("remarks")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("orderAmount")); + + rowIndex++; + } + } + +} diff --git a/src/main/java/com/ffii/tls/reports/view/OrderReportExcelView.java b/src/main/java/com/ffii/tls/reports/view/OrderReportExcelView.java new file mode 100644 index 0000000..1eeed4c --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/view/OrderReportExcelView.java @@ -0,0 +1,102 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.view; + +import java.math.BigDecimal; +import java.util.Date; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import com.ffii.core.utils.ExcelUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.view.document.AbstractExcelView; +import com.ffii.tbms.order.Order; +import com.ibm.icu.text.DecimalFormat; +import com.ibm.icu.text.SimpleDateFormat; + +import org.apache.poi.hssf.usermodel.HSSFHeader; +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; + +public class OrderReportExcelView extends AbstractExcelView { + + protected Date printDate; + protected final String REPORT_NAME = "Order Report"; + DecimalFormat df = new DecimalFormat("#,##0.00"); + + @SuppressWarnings("unchecked") + @Override + protected void buildExcelDocument(Map model, Workbook workbook, HttpServletRequest request, + HttpServletResponse response) throws Exception { + printDate = new Date(); + String pattern = "yyyy-MM-dd"; + SimpleDateFormat simpleDateFormat = new SimpleDateFormat(pattern); + String todayStr = simpleDateFormat.format(printDate); + response.setHeader("Content-Disposition", + "attachment; filename=\"" + response.encodeURL(REPORT_NAME + "_"+todayStr) + ".xlsx\""); + Sheet sheet = workbook.getSheetAt(0); + // get Data + List> records = (List>) model.get(Params.RECORDS); + Map map = (Map) model.get("map"); + String reportHeader = (String)model.get("reportHeader"); + + sheet.getHeader().setCenter(HSSFHeader.font("Calibri", "bold")+(reportHeader==null?"":reportHeader)+"\n"+REPORT_NAME+" ("+ + simpleDateFormat.format(map.get("dateFrom"))+" - "+simpleDateFormat.format(map.get("dateTo"))+")"); + + int rowIndex = 1; + for (int i = 0; i < records.size(); i++) { + Map record = records.get(i); + int colIndex = 0; + + if(rowIndex>1){ + ExcelUtils.copyAndInsertRow(workbook, sheet, 1, rowIndex); + } + + String itemStr = ""; + String priceStr = ""; + if(record.get("item") != null && !record.get("item").equals("")){ + String[] items = record.get("item").toString().split("\\|\\|;"); + for(String item:items){ + String name = item.split("\\|;")[0]; + BigDecimal price = NumberUtils.toDecimal(item.split("\\|;")[1], BigDecimal.ZERO); + itemStr = itemStr.equals("")?"":itemStr+"\n"; + itemStr = itemStr+name; + priceStr = priceStr.equals("")?"":priceStr+"\n"; + priceStr = priceStr+df.format(price); + } + } + + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, i+1); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("date")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("orderNo")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("refNo")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("customerName")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, getStatusStr(NumberUtils.intValue(record.get("status")))); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, itemStr); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, priceStr); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("orderAmount")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("remarks")); + + sheet.getRow(rowIndex).setHeightInPoints(-1); + + rowIndex++; + } + } + + public String getStatusStr(int status){ + if(status == Order.STATUS_COMPLETED) return "Completed"; + if(status == Order.STATUS_ON_HAND) return "On Hand"; + if(status == Order.STATUS_CANCELLED) return "Cancelled"; + return ""; + } +} diff --git a/src/main/java/com/ffii/tls/reports/view/OutstandingReportExcelView.java b/src/main/java/com/ffii/tls/reports/view/OutstandingReportExcelView.java new file mode 100644 index 0000000..56ae70a --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/view/OutstandingReportExcelView.java @@ -0,0 +1,78 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.view; + +import java.util.Date; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import com.ffii.core.utils.BooleanUtils; +import com.ffii.core.utils.ExcelUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.view.document.AbstractExcelView; +import com.ffii.tbms.order.Order; +import com.ibm.icu.text.SimpleDateFormat; + +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; + +public class OutstandingReportExcelView extends AbstractExcelView { + + protected Date printDate; + protected final String REPORT_NAME = "Outstanding Report"; + + @SuppressWarnings("unchecked") + @Override + protected void buildExcelDocument(Map model, Workbook workbook, HttpServletRequest request, + HttpServletResponse response) throws Exception { + printDate = new Date(); + String pattern = "yyyy-MM-dd"; + SimpleDateFormat simpleDateFormat = new SimpleDateFormat(pattern); + String todayStr = simpleDateFormat.format(printDate); + response.setHeader("Content-Disposition", + "attachment; filename=\"" + response.encodeURL(REPORT_NAME + "_"+todayStr) + ".xlsx\""); + Sheet sheet = workbook.getSheetAt(0); + // get Data + List> records = (List>) model.get(Params.RECORDS); + + int rowIndex = 1; + for (int i = 0; i < records.size(); i++) { + Map record = records.get(i); + int colIndex = 0; + + if(rowIndex>1){ + ExcelUtils.copyAndInsertRow(workbook, sheet, 1, rowIndex); + } + + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, i+1); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("date")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("orderNo")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, Order.STATUS_IGNORE.equals(record.get("status"))?"T":""); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("customerName")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, getStatusStr(NumberUtils.intValue(record.get("status")))); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("orderAmount")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("paymentAmount")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("outstanding")); + + rowIndex++; + } + } + + public String getStatusStr(int status){ + if(status == Order.STATUS_COMPLETED) return "Completed"; + if(status == Order.STATUS_ON_HAND) return "On Hand"; + if(status == Order.STATUS_CANCELLED) return "Cancelled"; + if(status == Order.STATUS_IGNORE) return "Ignore"; + return ""; + } +} diff --git a/src/main/java/com/ffii/tls/reports/view/PaymentReportExcelView.java b/src/main/java/com/ffii/tls/reports/view/PaymentReportExcelView.java new file mode 100644 index 0000000..0f20472 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/view/PaymentReportExcelView.java @@ -0,0 +1,88 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.view; + +import java.util.Date; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import com.ffii.core.utils.ExcelUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.view.document.AbstractExcelView; +import com.ffii.tbms.order.Order; +import com.ibm.icu.text.SimpleDateFormat; + +import org.apache.poi.hssf.usermodel.HSSFHeader; +import org.apache.poi.ss.usermodel.CellStyle; +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.usermodel.Workbook; + +public class PaymentReportExcelView extends AbstractExcelView { + + protected Date printDate; + protected final String REPORT_NAME = "Payment Report"; + + protected CellStyle normalStyle; + protected CellStyle wrapTextStyle; + + @SuppressWarnings("unchecked") + @Override + protected void buildExcelDocument(Map model, Workbook workbook, HttpServletRequest request, + HttpServletResponse response) throws Exception { + printDate = new Date(); + String pattern = "yyyy-MM-dd"; + SimpleDateFormat simpleDateFormat = new SimpleDateFormat(pattern); + String todayStr = simpleDateFormat.format(printDate); + response.setHeader("Content-Disposition", + "attachment; filename=\"" + response.encodeURL(REPORT_NAME + "_"+todayStr) + ".xlsx\""); + Sheet sheet = workbook.getSheetAt(0); + // get Data + List> records = (List>) model.get(Params.RECORDS); + Map map = (Map) model.get("map"); + String reportHeader = (String)model.get("reportHeader"); + + sheet.getHeader().setCenter(HSSFHeader.font("Calibri", "bold")+(reportHeader==null?"":reportHeader)+"\n"+REPORT_NAME+" (" + +simpleDateFormat.format(map.get("dateFrom"))+" - " + +simpleDateFormat.format(map.get("dateTo"))+")"); + + ExcelUtils.setCellValue(sheet, 0, 7, "Current Total Payment ("+todayStr+")"); + + int rowIndex = 1; + for (int i = 0; i < records.size(); i++) { + Map record = records.get(i); + int colIndex = 0; + + if(rowIndex>1){ + ExcelUtils.copyAndInsertRow(workbook, sheet, 1, rowIndex); + } + + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, i+1); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("paymentDate")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("orderNo")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("customerName")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, getStatusStr(NumberUtils.intValue(record.get("orderStatus")))); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("paymentAmount")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("orderAmount")); + ExcelUtils.setCellValue(sheet, rowIndex, colIndex++, record.get("currentPayment")); + + rowIndex++; + } + } + + public String getStatusStr(int status){ + if(status == Order.STATUS_COMPLETED) return "Completed"; + if(status == Order.STATUS_ON_HAND) return "On Hand"; + if(status == Order.STATUS_CANCELLED) return "Cancelled"; + return ""; + } +} diff --git a/src/main/java/com/ffii/tls/reports/web/AuditLogExportController.java b/src/main/java/com/ffii/tls/reports/web/AuditLogExportController.java new file mode 100644 index 0000000..8bac77b --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/web/AuditLogExportController.java @@ -0,0 +1,59 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractController; +import com.ffii.tbms.reports.service.AuditLogExportService; + +/** + * @author fung + */ +@Controller +@RequestMapping(value = "/report") +public class AuditLogExportController extends AbstractController { + + @Autowired + private AuditLogExportService auditLogExportService; + + @RequestMapping(value = "/audit-log-export/excel", method = { RequestMethod.GET, RequestMethod.POST }) + public String excel(Model model, HttpServletRequest request, HttpServletResponse response) throws ServletRequestBindingException { + Map args = new HashMap(); + CriteriaUtils.addDate(request, args, "dateFrom"); + CriteriaUtils.addDateTo(request, args, "dateTo"); + CriteriaUtils.addString(request, args, "tableName"); + + List> records = auditLogExportService.search(args); + + if (args.containsKey("dateFrom")) model.addAttribute("dateFrom", args.get("dateFrom")); + if (args.containsKey("dateTo")) model.addAttribute("dateTo", args.get("dateTo")); + if (args.containsKey("tableName")) model.addAttribute("tableName", args.get("tableName")); + + model.addAttribute(Params.RECORDS, records); + + return "auditLogExportExcelView"; + } +} diff --git a/src/main/java/com/ffii/tls/reports/web/CustomerFirstOrderReportController.java b/src/main/java/com/ffii/tls/reports/web/CustomerFirstOrderReportController.java new file mode 100644 index 0000000..ba6355d --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/web/CustomerFirstOrderReportController.java @@ -0,0 +1,47 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.web; + +import java.util.List; +import java.util.Map; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractController; +import com.ffii.tbms.reports.service.CustomerFirstOrderReportService; + + +@Controller +@RequestMapping(value = "/report/customer-first-order") +public class CustomerFirstOrderReportController extends AbstractController { + + @Autowired + private CustomerFirstOrderReportService service; + + @RequestMapping(value = "/excel", method = { RequestMethod.GET, RequestMethod.POST }) + public String excel(Model model, HttpServletRequest request, HttpServletResponse response) + throws ServletRequestBindingException { + + List> records = service.search(); + List> noOrderList = service.searchNoOrderCustomer(); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("noOrderList", noOrderList); + + return "customerFirstOrderReportExcelView"; + } +} diff --git a/src/main/java/com/ffii/tls/reports/web/CustomerReportController.java b/src/main/java/com/ffii/tls/reports/web/CustomerReportController.java new file mode 100644 index 0000000..02e45c4 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/web/CustomerReportController.java @@ -0,0 +1,89 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.reports.service.CustomerReportService; +import com.ffii.tbms.reports.service.PaymentReportService; + +/** + * @author fung + */ +@Controller +@RequestMapping(value = "/report/customer") +public class CustomerReportController extends AbstractController { + + @Autowired + private CustomerReportService service; + + @RequestMapping(value = "/excel", method = { RequestMethod.GET, RequestMethod.POST }) + public String excel(Model model, HttpServletRequest request, HttpServletResponse response) + throws ServletRequestBindingException { + + if (SecurityUtils.isGranted("CUSTOMER_REPORT")) { + Map args = new HashMap(); + CriteriaUtils.addDate(request, args, "dateFrom"); + CriteriaUtils.addDateTo(request, args, "dateTo"); + + List> records = service.search(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("map", args); + + return "customerReportExcelView"; + } else { + model.addAttribute(Params.AUTH, Boolean.FALSE); + return JsonView.NAME; + } + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap(); + CriteriaUtils.addDate(request, args, "dateFrom"); + CriteriaUtils.addDateTo(request, args, "dateTo"); + + //CriteriaUtils.addInteger(request, args, "start"); + //CriteriaUtils.addInteger(request, args, "limit"); + + List> records = service.search(args); + + //Map count = service.count(args); + //model.addAttribute("total", NumberUtils.intValue(count.get("count"))); + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + +} + + diff --git a/src/main/java/com/ffii/tls/reports/web/MeasurementSheetController.java b/src/main/java/com/ffii/tls/reports/web/MeasurementSheetController.java new file mode 100644 index 0000000..abc72bd --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/web/MeasurementSheetController.java @@ -0,0 +1,71 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.web; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.awt.image.BufferedImage; +import java.io.File; + +import javax.imageio.ImageIO; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.servlet.ModelAndView; + +import net.sf.jasperreports.engine.data.JRBeanCollectionDataSource; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.ZXingUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.tbms.order.service.OrderService; + +@Controller +@RequestMapping(value = "/report") +public class MeasurementSheetController extends AbstractController { + + @Autowired + private OrderService orderService; + + @RequestMapping(value = "/measurement-sheet.{format}", method = { RequestMethod.GET,RequestMethod.POST }) + public ModelAndView measurementSheet(Model model, HttpServletRequest request, HttpServletResponse response, + @RequestParam int orderId, + @PathVariable String format) throws Exception { + + List> list = new ArrayList<>(); + Map params = new HashMap<>(); + + Map data = orderService.find(MapUtils.toHashMap("orderId", orderId)); + + String path = this.getClass().getClassLoader().getResource("").getPath() + "../report/measurementSheetImage.jpeg"; + BufferedImage msImage = ImageIO.read(new File(path)); + list.add(MapUtils.toHashMap("msImage", msImage, + "codeImage", ZXingUtils.encodeToImageCode128("0"+data.get("id").toString(), 160, 50), + "custName", data.get("customerName"), + "orderNo", data.get("orderNo"))); + params.put("dataSource", new JRBeanCollectionDataSource(list)); + + if (format.equals("pdf") || format.equals("docx")) + params.put("format", format); + else + params.put("format", "pdf"); + + return new ModelAndView("measurementSheet", params); + } +} diff --git a/src/main/java/com/ffii/tls/reports/web/OrderReportController.java b/src/main/java/com/ffii/tls/reports/web/OrderReportController.java new file mode 100644 index 0000000..b3a49b6 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/web/OrderReportController.java @@ -0,0 +1,82 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.reports.service.OrderReportService; + + +@Controller +@RequestMapping(value = "/report/order") +public class OrderReportController extends AbstractController { + + @Autowired + private OrderReportService orderReportService; + + @RequestMapping(value = "/excel", method = { RequestMethod.GET, RequestMethod.POST }) + public String excel(Model model, HttpServletRequest request, HttpServletResponse response) + throws ServletRequestBindingException { + + Map args = new HashMap(); + CriteriaUtils.addStringLike(request, args, "custName"); + CriteriaUtils.addStringLike(request, args, "orderNo"); + CriteriaUtils.addDate(request, args, "dateFrom"); + CriteriaUtils.addDate(request, args, "dateTo"); + List> records = orderReportService.search(args); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("map", args); + + return "orderReportExcelView"; + } + + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap(); + CriteriaUtils.addStringLike(request, args, "custName"); + CriteriaUtils.addStringLike(request, args, "orderNo"); + CriteriaUtils.addDate(request, args, "dateFrom"); + CriteriaUtils.addDate(request, args, "dateTo"); + + CriteriaUtils.addInteger(request, args,"start"); + CriteriaUtils.addInteger(request, args,"limit"); + + List> records = orderReportService.search(args); + + Map count = orderReportService.count(args); + model.addAttribute("total", NumberUtils.intValue(count.get("count"))); + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/reports/web/OutstandingReportController.java b/src/main/java/com/ffii/tls/reports/web/OutstandingReportController.java new file mode 100644 index 0000000..aa3ecc7 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/web/OutstandingReportController.java @@ -0,0 +1,79 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.reports.service.OutstandingReportService; + +/** + * @author fung + */ +@Controller +@RequestMapping(value = "/report/outstanding") +public class OutstandingReportController extends AbstractController { + + @Autowired + private OutstandingReportService outstandingReportService; + + @RequestMapping(value = "/excel", method = { RequestMethod.GET, RequestMethod.POST }) + public String excel(Model model, HttpServletRequest request, HttpServletResponse response) + throws ServletRequestBindingException { + + Map args = new HashMap(); + CriteriaUtils.addStringLike(request, args, "custName"); + CriteriaUtils.addStringLike(request, args, "orderNo"); + List> records = outstandingReportService.search(args); + + model.addAttribute(Params.RECORDS, records); + + return "outstandingReportExcelView"; + } + + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap(); + CriteriaUtils.addStringLike(request, args, "custName"); + CriteriaUtils.addStringLike(request, args, "orderNo"); + + CriteriaUtils.addInteger(request, args,"start"); + CriteriaUtils.addInteger(request, args,"limit"); + + List> records = outstandingReportService.search(args); + + Map count = outstandingReportService.count(args); + model.addAttribute("total", NumberUtils.intValue(count.get("count"))); + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/reports/web/PaymentReportController.java b/src/main/java/com/ffii/tls/reports/web/PaymentReportController.java new file mode 100644 index 0000000..697faf3 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/web/PaymentReportController.java @@ -0,0 +1,92 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.ServletRequestBindingException; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.reports.service.PaymentReportService; + +/** + * @author fung + */ +@Controller +@RequestMapping(value = "/report/payment") +public class PaymentReportController extends AbstractController { + + @Autowired + private PaymentReportService paymentReportService; + + @RequestMapping(value = "/excel", method = { RequestMethod.GET, RequestMethod.POST }) + public String excel(Model model, HttpServletRequest request, HttpServletResponse response) + throws ServletRequestBindingException { + + if (SecurityUtils.isGranted("PAYMENT_REPORT")) { + Map args = new HashMap(); + CriteriaUtils.addDate(request, args, "dateFrom"); + CriteriaUtils.addDateTo(request, args, "dateTo"); + + List> records = paymentReportService.search(args); + for (Map record : records) { + record.putAll(paymentReportService.searchCurrentPayment(NumberUtils.intValue(record.get("orderId")))); + } + + model.addAttribute(Params.RECORDS, records); + model.addAttribute("map", args); + + return "paymentReportExcelView"; + } else { + model.addAttribute(Params.AUTH, Boolean.FALSE); + return JsonView.NAME; + } + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap(); + CriteriaUtils.addDate(request, args, "dateFrom"); + CriteriaUtils.addDateTo(request, args, "dateTo"); + + CriteriaUtils.addInteger(request, args, "start"); + CriteriaUtils.addInteger(request, args, "limit"); + + List> records = paymentReportService.search(args); + for (Map record : records) { + record.putAll(paymentReportService.searchCurrentPayment(NumberUtils.intValue(record.get("orderId")))); + } + + Map count = paymentReportService.count(args); + model.addAttribute("total", NumberUtils.intValue(count.get("count"))); + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/reports/web/PreviewController.java b/src/main/java/com/ffii/tls/reports/web/PreviewController.java new file mode 100644 index 0000000..03b2262 --- /dev/null +++ b/src/main/java/com/ffii/tls/reports/web/PreviewController.java @@ -0,0 +1,77 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.reports.web; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.awt.Image; +import java.awt.image.BufferedImage; +import java.io.ByteArrayInputStream; + +import javax.imageio.ImageIO; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.imgscalr.Scalr; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.servlet.ModelAndView; + +import net.sf.jasperreports.engine.data.JRBeanCollectionDataSource; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.tbms.file.FileBlob; +import com.ffii.tbms.file.service.FileService; + +@Controller +@RequestMapping(value = "/report") +public class PreviewController extends AbstractController { + + @Autowired + private FileService fileService; + + @RequestMapping(value = "preview.{format}", method = { RequestMethod.GET,RequestMethod.POST }) + public ModelAndView printJobSheet(Model model, HttpServletRequest request, HttpServletResponse response, + @RequestParam int[] fileIds, + @PathVariable String format) throws Exception { + + List> selectedList = new ArrayList<>(); + + Map params = new HashMap<>(); + + for(int fileId: fileIds){ + FileBlob fileBlob = fileService.findFileBlobByFileId(fileId); + BufferedImage image = ImageIO.read(new ByteArrayInputStream(fileBlob.getBytes())); + if(image.getWidth()>image.getHeight()){ + BufferedImage rotated = Scalr.rotate(image, Scalr.Rotation.CW_270, Scalr.OP_ANTIALIAS); + image = Scalr.resize(rotated, Scalr.Method.SPEED, Scalr.Mode.FIT_TO_HEIGHT, + image.getHeight(), image.getWidth(), Scalr.OP_ANTIALIAS); + } + selectedList.add(MapUtils.toHashMap("selectedImage", image)); + } + + params.put("dataSource", new JRBeanCollectionDataSource(selectedList)); + + if (format.equals("pdf") || format.equals("docx")) + params.put("format", format); + else + params.put("format", "pdf"); + + return new ModelAndView("tbmsPrintPreview", params); + } +} diff --git a/src/main/java/com/ffii/tls/root/web/HomeController.java b/src/main/java/com/ffii/tls/root/web/HomeController.java new file mode 100644 index 0000000..43423a5 --- /dev/null +++ b/src/main/java/com/ffii/tls/root/web/HomeController.java @@ -0,0 +1,58 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.root.web; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +import javax.servlet.http.HttpServletRequest; + +import com.ffii.core.Settings; +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.StringUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; + +@Controller +public class HomeController extends AbstractController { + + @Autowired + private SettingsService settingsService; + + @RequestMapping(value = "/", method = RequestMethod.GET) + public String root(Model model) throws Exception { + return "redirect:/home"; + } + + @RequestMapping(value = "/home", method = RequestMethod.GET) + public String home(Model model, HttpServletRequest request) throws Exception { + if (StringUtils.equals(request.getLocalAddr(), request.getRemoteAddr())) { + model.addAttribute("jsv", String.valueOf(System.currentTimeMillis())); + } else { + model.addAttribute("jsv", settingsService.getString(Settings.JS_VERSION, "1")); + } + return "root/home"; + } + + @RequestMapping(value = "/get-sys-time", method = { RequestMethod.GET, RequestMethod.POST }) + public String getSysTime(Model model) throws Exception { + model.addAttribute("sysTime", System.currentTimeMillis()); + return JsonView.NAME; + } + @RequestMapping(value = "/home/old-viewport", method = RequestMethod.GET) + public String newViewport(Model model) throws Exception { + return "root/oldhome"; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/root/web/IndexController.java b/src/main/java/com/ffii/tls/root/web/IndexController.java new file mode 100644 index 0000000..f669919 --- /dev/null +++ b/src/main/java/com/ffii/tls/root/web/IndexController.java @@ -0,0 +1,73 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.root.web; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import com.ffii.core.Session; +import com.ffii.core.Settings; +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.LocaleUtils; +import com.ffii.core.web.AbstractController; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +@Controller +public class IndexController extends AbstractController { + + @Autowired + private SettingsService settingsService; + + @RequestMapping(value = "/index", method = RequestMethod.GET) + public String index(Model model, HttpServletRequest request, HttpServletResponse response) { + + // get available locales and default locale from system settings + String[] availableLocales = settingsService.getString(Settings.SYS_AVAILABLE_LOCALES).split(","); + Session.setAttribute(request, Session.AVAILABLE_LOCALES, availableLocales); + + String defaultLocale = settingsService.getString(Settings.SYS_DEFAULT_LOCALE); + + // try to resolve current locale + String currentLocale = LocaleUtils.resolveLocaleString(request); + + // determine if current locale is available + boolean localeIsAvailable = false; + for (String availableLocale : availableLocales) { + if (availableLocale.equalsIgnoreCase(currentLocale)) { + localeIsAvailable = true; + } + } + + // use current locale if available, else use default locale + if (localeIsAvailable) { + LocaleUtils.setLocale(request, response, LocaleUtils.toLocale(currentLocale)); + } else { + LocaleUtils.setLocale(request, response, LocaleUtils.toLocale(defaultLocale)); + } + + // find username cookie + /* + Cookie[] cookies = request.getCookies(); + if (cookies != null) { + for (Cookie cookie : cookies) { + if ("username".equals(cookie.getName())) { + model.addAttribute("username", cookie.getValue()); + } + } + } + */ + + return "root/index"; + } +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/root/web/LocaleController.java b/src/main/java/com/ffii/tls/root/web/LocaleController.java new file mode 100644 index 0000000..2bbe659 --- /dev/null +++ b/src/main/java/com/ffii/tls/root/web/LocaleController.java @@ -0,0 +1,45 @@ +/******************************************************************************* + * Copyright 2016 2Fi Business Solutions Ltd. + * + * This code is part of the SPCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.root.web; + +import javax.servlet.http.HttpServletRequest; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.servlet.i18n.SessionLocaleResolver; +import org.springframework.web.util.WebUtils; + +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.core.utils.LocaleUtils; +import com.ffii.tbms.user.service.UserService; + +@Controller +public class LocaleController extends AbstractController { + @Autowired + private UserService userService; + + @RequestMapping(value = "/locale", method = RequestMethod.GET) + public String locale(Model model, HttpServletRequest request, @RequestParam String locale) { + WebUtils.setSessionAttribute(request, SessionLocaleResolver.LOCALE_SESSION_ATTRIBUTE_NAME, LocaleUtils.toLocale(locale)); + + if (SecurityUtils.getUser() != null) userService.changeLocale(SecurityUtils.getUser().getId(), locale); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/setting/web/SettingsController.java b/src/main/java/com/ffii/tls/setting/web/SettingsController.java new file mode 100644 index 0000000..1b54af4 --- /dev/null +++ b/src/main/java/com/ffii/tls/setting/web/SettingsController.java @@ -0,0 +1,120 @@ +package com.ffii.tbms.setting.web; + +import java.util.HashMap; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import com.ffii.core.Settings; +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.order.service.InvoiceService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +@Controller +@RequestMapping(value = "/setting") +public class SettingsController extends AbstractController { + + @Autowired + private SettingsService settingsService; + + @Autowired + private InvoiceService invoiceService; + + + @RequestMapping(value = "/mail/save", method = { RequestMethod.GET, RequestMethod.POST }) + public String saveMail(Model model, HttpServletRequest request, @RequestParam String subject, @RequestParam String body) throws Exception { + + if (SecurityUtils.isGranted("MATERIAL_MAIL_TEMPLATE")) { + + settingsService.resetSettingsCache(); + invoiceService.updateTemplateBody(body); + invoiceService.updateTemplateSubject(subject); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.MSG, "No Auth"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/mail/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String loadMail(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("MATERIAL_MAIL_TEMPLATE")) { + Map map = new HashMap<>(); + + map.put("subject", invoiceService.getTemplateSubject()); + map.put("body", invoiceService.getTemplateBody()); + + model.addAttribute(Params.DATA, map); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.MSG, "No Auth"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/cache-clear", method = { RequestMethod.GET, RequestMethod.POST }) + public String cacheClear(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("SUPERUSER")) { + settingsService.resetSettingsCache(); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.MSG, "No Auth"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/sys-user/details/save", method = { RequestMethod.GET, RequestMethod.POST }) + public String saveSysUserDetails(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("MATERIAL_MAIL_TEMPLATE")) { + Map map = new HashMap<>(); + + map.put("subject", invoiceService.getTemplateSubject()); + map.put("body", invoiceService.getTemplateBody()); + + model.addAttribute(Params.DATA, map); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.MSG, "No Auth"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/sys-user/details/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String loadSysUserDetails(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("MATERIAL_MAIL_TEMPLATE")) { + Map map = new HashMap<>(); + + map.put("subject", invoiceService.getTemplateSubject()); + map.put("body", invoiceService.getTemplateBody()); + + model.addAttribute(Params.DATA, map); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.MSG, "No Auth"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + +} diff --git a/src/main/java/com/ffii/tls/sjs/web/SjsController.java b/src/main/java/com/ffii/tls/sjs/web/SjsController.java new file mode 100644 index 0000000..0f7184f --- /dev/null +++ b/src/main/java/com/ffii/tls/sjs/web/SjsController.java @@ -0,0 +1,64 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.sjs.web; + +import java.util.Arrays; +import java.util.List; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.springframework.stereotype.Controller; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; + +import com.ffii.core.utils.StringUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.AbstractView; + +/** + * System JS Controller + */ +@Controller +@RequestMapping(value = "/sjs") +public class SjsController extends AbstractController { + + private static final List PATHS = Arrays.asList("controller", "store", "view"); + private static final List PATHS2 = Arrays.asList("combo", "widget", "report"); + + @RequestMapping(value = "/{path}/{name}", method = RequestMethod.GET) + public String js(HttpServletRequest request, HttpServletResponse response, @PathVariable String path, @PathVariable String name) + throws Exception { + + if (PATHS.contains(path) && StringUtils.endsWith(name, ".js")) { + response.setContentType(AbstractView.CONTENT_TYPE_JAVASCRIPT); + return String.format("sjs/%s/%s", path, name); + } else { + response.setStatus(HttpServletResponse.SC_NOT_FOUND); + return null; + } + } + + @RequestMapping(value = "/{path}/{path2}/{name}", method = RequestMethod.GET) + public String widgetJs(HttpServletRequest request, HttpServletResponse response, @PathVariable String path, + @PathVariable String path2, @PathVariable String name) + throws Exception { + + if (PATHS.contains(path) && PATHS2.contains(path2) && StringUtils.endsWith(name, ".js")) { + response.setContentType(AbstractView.CONTENT_TYPE_JAVASCRIPT); + return String.format("sjs/%s/%s/%s", path, path2, name); + } else { + response.setStatus(HttpServletResponse.SC_NOT_FOUND); + return null; + } + } +} diff --git a/src/main/java/com/ffii/tls/user/Group.java b/src/main/java/com/ffii/tls/user/Group.java new file mode 100644 index 0000000..e66b578 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/Group.java @@ -0,0 +1,52 @@ +/******************************************************************************* + * Copyright 2013 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.Table; + +import com.ffii.core.BaseEntity; + +@Entity +@Table(name = "groups") +public class Group extends BaseEntity { + + private static final long serialVersionUID = -2953359601975739303L; + + @Column(columnDefinition = "varchar(50)", nullable = false) + private String name; + + @Column(columnDefinition = "varchar(255)") + private String description; + + /** Default constructor */ + public Group() { + + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getDescription() { + return description; + } + + public void setDescription(String description) { + this.description = description; + } + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/user/UserSetting.java b/src/main/java/com/ffii/tls/user/UserSetting.java new file mode 100644 index 0000000..10ad9eb --- /dev/null +++ b/src/main/java/com/ffii/tls/user/UserSetting.java @@ -0,0 +1,82 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user; + +import java.io.Serializable; + +public class UserSetting implements Serializable { + + public static final String USER_lang = "USER.lang"; + public static final String USER_materialItemGroup = "USER.materialItemGroup"; + public static final String USER_showMaterialItemCost = "USER.showMaterialItemCost"; + + private static final long serialVersionUID = 3925955875238868120L; + + private int userId; + + private String category; + + private String type; + + private String name; + + private String value; + + /** default constructor */ + public UserSetting() { + + } + + public int getUserId() { + return userId; + } + + + + public void setUserId(int userId) { + this.userId = userId; + } + + + + public String getCategory() { + return category; + } + + public void setCategory(String category) { + this.category = category; + } + + public String getType() { + return type; + } + + public void setType(String type) { + this.type = type; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getValue() { + return value; + } + + public void setValue(String value) { + this.value = value; + } + +} diff --git a/src/main/java/com/ffii/tls/user/dao/GroupDao.java b/src/main/java/com/ffii/tls/user/dao/GroupDao.java new file mode 100644 index 0000000..9413bde --- /dev/null +++ b/src/main/java/com/ffii/tls/user/dao/GroupDao.java @@ -0,0 +1,29 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.dao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +import com.ffii.core.dao.HibernateDao; +import com.ffii.tbms.user.Group; + +@Repository +public class GroupDao extends HibernateDao { + + @Autowired + public GroupDao(SessionFactory sessionFactory) { + super(Group.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/user/dao/UserDao.java b/src/main/java/com/ffii/tls/user/dao/UserDao.java new file mode 100644 index 0000000..f73d3c5 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/dao/UserDao.java @@ -0,0 +1,27 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.dao; + +import com.ffii.core.User; +import com.ffii.core.dao.HibernateDao; + +import org.hibernate.SessionFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Repository; + +@Repository +public class UserDao extends HibernateDao { + + @Autowired + public UserDao(SessionFactory sessionFactory) { + super(User.class); + setSessionFactory(sessionFactory); + } + +} diff --git a/src/main/java/com/ffii/tls/user/service/AuthService.java b/src/main/java/com/ffii/tls/user/service/AuthService.java new file mode 100644 index 0000000..8e34e77 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/service/AuthService.java @@ -0,0 +1,111 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.service; + +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.web.AbstractService; + +/** + * Service for managing users authorities + * + * @author Patrick + */ +@Service +public class AuthService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(int userId) { + + /* + SELECT + a.module, + a.authority, + a.name, + EXISTS(SELECT 1 FROM users_authorities WHERE authority = a.authority AND userId = :userId) AS v + FROM authorities a + WHERE a.deleted = 0 + + ORDER BY a.id + */ + StringBuilder sql = new StringBuilder("SELECT" + + " a.module," + + " a.authority," + + " a.name," + + " EXISTS(SELECT 1 FROM users_authorities WHERE authority = a.authority AND userId = :userId) AS v" + + " FROM authorities a"); + + sql.append(" ORDER BY a.authority"); + + return jdbcDao.queryForList(sql.toString(), MapUtils.toHashMap("userId", userId)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int[] batchInsertUsersAuthorities(Map[] batchValues) { + + String sql = "INSERT IGNORE INTO users_authorities" + + " (userId, authority)" + + " VALUES" + + " (:userId, :authority)"; + + return jdbcDao.executeBatchUpdate(sql, batchValues); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int[] batchDeleteUsersAuthorities(Map[] batchValues) { + + String sql = "DELETE FROM users_authorities" + + " WHERE userId = :userId AND authority = :authority"; + + return jdbcDao.executeBatchUpdate(sql, batchValues); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public List> findUserWithAuth(Map args) { + + StringBuilder sql = new StringBuilder("SELECT * FROM users_authorities" + + " WHERE 1=1 "); + if (args != null) { + if (args.containsKey("authority")) sql.append(" AND authority = :authority "); + if (args.containsKey("ignoreUserId")) sql.append(" AND userId != :ignoreUserId "); + } + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> list() { + + /* + SELECT a.* + FROM + authorities a; + + */ + StringBuilder sql = new StringBuilder("SELECT" + + " a.*" + + " FROM authorities a"); + + sql.append(" ORDER BY a.authority"); + + return jdbcDao.queryForList(sql.toString(), null); + } + +} diff --git a/src/main/java/com/ffii/tls/user/service/GroupService.java b/src/main/java/com/ffii/tls/user/service/GroupService.java new file mode 100644 index 0000000..0eba754 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/service/GroupService.java @@ -0,0 +1,185 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.service; + +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.user.Group; +import com.ffii.tbms.user.dao.GroupDao; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +/** + * @author Patrick + */ +@Service +public class GroupService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private GroupDao groupDao; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(Group instance) { + return groupDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Group find(Integer id) { + return groupDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer delete(Group instance) { + if (instance.getId() != null) { + StringBuilder delGUSQL = new StringBuilder("DELETE FROM groups_users WHERE groupId = :groupId ;"); + StringBuilder delGASQL = new StringBuilder("DELETE FROM groups_authorities WHERE groupId = :groupId ;"); + Map args = MapUtils.toHashMap("groupId", instance.getId()); + + jdbcDao.executeUpdate(delGUSQL.toString(), args); + jdbcDao.executeUpdate(delGASQL.toString(), args); + } + instance.setDeleted(true); + return saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " g.*"); + + if (args.containsKey("userId")) sql.append(", EXISTS(SELECT 1 FROM groups_users WHERE groupId = g.id AND userId = :userId) AS v"); + + sql.append(" FROM groups g"); + + if (args.containsKey(Params.QUERY)) sql.append(" AND (g.name LIKE :query)"); + + if (args.containsKey(Params.ID)) sql.append(" AND g.id = :id"); + + if (args.containsKey(Params.NAME)) sql.append(" AND g.name LIKE :name"); + sql.append(" WHERE g.deleted = 0"); + + + sql.append(" ORDER BY g.name"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + public Map queryForMap(Integer id) { + String sql = "SELECT * FROM groups WHERE id = :id"; + + return jdbcDao.queryForMap(sql, MapUtils.toHashMap(Params.ID, id)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchForCombo(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " g.id," + + " g.name AS groupName" + + " FROM groups g" + + " WHERE g.deleted = 0"); + + if (args.containsKey(Params.QUERY)) sql.append(" AND (g.name LIKE :query)"); + + if (args.containsKey(Params.ID)) sql.append(" AND g.id = :id"); + + sql.append(" ORDER BY g.name"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + /* group's user */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> listGroupUser(Integer groupId) { + + StringBuilder sql = new StringBuilder("SELECT" + + " u.id," + + " u.username," + + " u.fullname" + + " FROM groups_users gu" + + " INNER JOIN users u ON gu.userId = u.id" + + " WHERE u.deleted = 0" + + " AND gu.groupId = :groupId" + + " ORDER BY u.username"); + + return jdbcDao.queryForList(sql.toString(), MapUtils.toHashMap("groupId", groupId)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int[] addGroupUser(Map[] batchValues) { + + String sql = "INSERT IGNORE INTO groups_users" + + " (groupId,userId)" + + " VALUES" + + " (:groupId, :userId)"; + + return jdbcDao.executeBatchUpdate(sql, batchValues); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int[] removeGroupUser(Map[] batchValues) { + + String sql = "DELETE FROM groups_users" + + " WHERE groupId = :groupId AND userId = :userId"; + + return jdbcDao.executeBatchUpdate(sql, batchValues); + } + + /* group's auth */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> listGroupAuth(int groupId) { + + Map args = MapUtils.toHashMap("groupId", groupId); + + StringBuilder sql = new StringBuilder("SELECT" + + " a.module," + + " a.authority," + + " a.name, " + + " a.description, " + + " EXISTS(SELECT 1 FROM groups_authorities WHERE authority = a.authority AND groupId = :groupId) AS v" + + " FROM authorities a" + + " ORDER BY a.authority"); + + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int[] addGroupAuth(Map[] batchValues) { + + String sql = "INSERT IGNORE INTO groups_authorities" + + " (groupId, authority)" + + " VALUES" + + " (:groupId, :authority)"; + + return jdbcDao.executeBatchUpdate(sql, batchValues); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int[] removeGroupAuth(Map[] batchValues) { + + String sql = "DELETE FROM groups_authorities" + + " WHERE groupId = :groupId AND authority = :authority"; + + return jdbcDao.executeBatchUpdate(sql, batchValues); + } + +} diff --git a/src/main/java/com/ffii/tls/user/service/SysGroupService.java b/src/main/java/com/ffii/tls/user/service/SysGroupService.java new file mode 100644 index 0000000..1bbe166 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/service/SysGroupService.java @@ -0,0 +1,167 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.service; + +import java.util.Date; +import java.util.List; +import java.util.Map; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.file.FileBlob; +import com.ffii.tbms.file.FileRef; +import com.ffii.tbms.file.service.FileService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + + +@Service +public class SysGroupService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private FileService fileService; + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer insert(Map args) { + + args.put("deleted", Boolean.FALSE); + args.put("versionId", 0); + args.put("created", new Date()); + args.put("createdBy", SecurityUtils.getUser().getId()); + args.put("modified", new Date()); + args.put("modifiedBy", SecurityUtils.getUser().getId()); + + return jdbcDao.executeInsertAndReturnKey("sys_groups", "id", args).intValue(); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer update(Map args) { + + args.put("modified", new Date()); + args.put("modifiedBy", SecurityUtils.getUser().getId()); + + String sql = "UPDATE sys_groups SET "; + if(args.containsKey("deleted")){ + sql+=" deleted = :deleted, "; + } + if(args.containsKey("name")){ + sql+=" name = :name, "; + } + if(args.containsKey("companyName")){ + sql+=" companyName = :companyName, "; + } + if(args.containsKey("phone")){ + sql+=" phone = :phone, "; + } + if(args.containsKey("fax")){ + sql+=" fax = :fax, "; + } + if(args.containsKey("email")){ + sql+=" email = :email, "; + } + if(args.containsKey("address")){ + sql+=" address = :address, "; + } + if(args.containsKey("smtp_host")){ + sql+=" smtp_host = :smtp_host, "; + } + if(args.containsKey("smtp_port")){ + sql+=" smtp_port = :smtp_port, "; + } + if(args.containsKey("smtp_username")){ + sql+=" smtp_username = :smtp_username, "; + } + if(args.containsKey("smtp_password")){ + sql+=" smtp_password = :smtp_password, "; + } + sql += " modified = :modified, modifiedBy = :modifiedBy WHERE id = :id "; + return jdbcDao.executeUpdate(sql,args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map find(Integer id) { + logger.info("sys_groups: "+id); + Map args = MapUtils.toHashMap("id", id); + + StringBuilder sql = new StringBuilder( + " SELECT sg.* FROM sys_groups sg WHERE sg.id = :id " + ); + + return jdbcDao.queryForMap(sql.toString(),args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + StringBuilder sql = new StringBuilder("SELECT " + +" sg.*, " + +" userCount.count AS userCount " + +" FROM sys_groups sg " + +" LEFT JOIN " + +" (SELECT " + +" u.sysGroupId, COUNT(id) AS count " + +" FROM " + +" users u " + +" GROUP BY u.sysGroupId) " + +" userCount ON userCount.sysGroupId = sg.id" + +" WHERE 1=1 "); + + if(args.containsKey("deleted")){ + sql.append(" AND sg.deleted = :deleted "); + } + if(args.containsKey("name")){ + sql.append(" AND sg.name LIKE :name "); + } + + if (args.containsKey(Params.QUERY)) sql.append(" AND (sg.name LIKE :query)"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchForCombo(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " g.id," + + " g.name AS groupName" + + " FROM groups g" + + " WHERE g.deleted = 0"); + + if (args.containsKey(Params.QUERY)) sql.append(" AND (g.name LIKE :query)"); + + if (args.containsKey(Params.ID)) sql.append(" AND g.id = :id"); + + sql.append(" ORDER BY g.name"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public FileRef getIconFileRef(){ + return fileService.findFileRefByTypeAndId("SysGroupIcon", SecurityUtils.getUser().getSysGroupId()); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public FileBlob getIconBlob(){ + FileRef ref = getIconFileRef(); + if(ref == null) return null; + FileBlob blob = fileService.findFileBlobByFileId(ref.getFileId()); + return blob; + } + +} diff --git a/src/main/java/com/ffii/tls/user/service/UserService.java b/src/main/java/com/ffii/tls/user/service/UserService.java new file mode 100644 index 0000000..29c40b9 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/service/UserService.java @@ -0,0 +1,234 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.service; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.persistence.Table; + +import com.ffii.core.User; +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.utils.DataBindUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.web.AbstractService; +import com.ffii.tbms.user.dao.UserDao; + +import org.springframework.beans.BeanUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +@Service +public class UserService extends AbstractService { + + @Autowired + private JdbcDao jdbcDao; + + @Autowired + private UserDao userDao; + + + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdateForChangePwd(User instance) { + return userDao.saveOrUpdate(instance); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public Integer saveOrUpdate(User instance) { + String tableName = instance.getClass().getAnnotation(Table.class).name(); + StringBuilder sql = new StringBuilder("SELECT * FROM " + tableName + " WHERE id = :id"); + + if (instance != null && instance.getId() != null && instance.getId() > 0) { + Map map = jdbcDao.queryForMap(sql.toString(), MapUtils.toHashMap("id", instance.getId())); + map.remove("password"); + } + + Integer id = userDao.saveOrUpdate(instance); + + userDao.flush(); + + Map map = jdbcDao.queryForMap(sql.toString(), MapUtils.toHashMap("id", id)); + map.remove("password"); + + return id; + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public User find(Integer id) { + return userDao.find(id); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map findUserMap(Map args) { + //@formatter:off + StringBuilder sql = new StringBuilder("SELECT" + + " u.id," + + " u.versionId," + + " u.username," + + " u.password," + + " u.expired," + + " u.locked," + + " u.locale," + + " u.fullname," + + " u.firstname," + + " u.lastname," + + " u.deptId," + + " u.title," + + " u.email," + + " u.phone1," + + " u.phone2," + + " u.remarks," + + " u.companyId," + + " u.customerId" + + " FROM users u" + + " WHERE u.deleted = 0"); + //@formatter:on + + if (args.containsKey("id")) + sql.append(" AND u.id = :id"); + + if (args.containsKey("username")) + sql.append(" AND u.username = :username"); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> searchForCombo(Map args) { + StringBuilder sql = new StringBuilder( + "SELECT" + + " u.id," + + " u.companyId," + + " u.department," + + " u.username," + + " u.fullname" + + " FROM users u" + + " WHERE u.deleted = 0"); + //@formatter:on + if (args.containsKey(Params.QUERY)) + sql.append(" AND (u.username LIKE :query OR u.fullname LIKE :query)"); + + if (args.containsKey("senderId")) + sql.append(" AND u.id <> :senderId"); + + if (args.containsKey(Params.ID)) + sql.append(" AND u.id = :id"); + + if (args.containsKey("companyIds")) + sql.append(" AND u.companyId IN (:companyIds)"); + + if (args.containsKey("authority")) + sql.append( + " AND (EXISTS(SELECT 1 FROM users_authorities WHERE userId = id AND authority = :authority) OR EXISTS(SELECT 1 FROM groups_users gu INNER JOIN groups_authorities ga ON ga.groupId = gu.groupId AND ga.authority = :authority WHERE gu.userId = id))"); + + sql.append(" ORDER BY u.fullname"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public List> search(Map args) { + + StringBuilder sql = new StringBuilder("SELECT" + + " u.id," + + " u.modified," + + " u.username," + + " u.fullname," + + " u.firstname," + + " u.lastname," + + " u.department," + + " u.deptId," + + " u.title," + + " u.email," + + " u.phone1," + + " u.phone2," + + " u.remarks," + + " u.companyId," + + " gu.groupId" + + " FROM users u" + + " LEFT JOIN groups_users gu on u.id = gu.userId" + + " WHERE u.deleted = 0"); + + if (args.containsKey(Params.ID)) + sql.append(" AND u.id = :id"); + + if(args.containsKey("sysGroupId")){ + sql.append(" AND u.sysGroupId = :sysGroupId "); + } + if (args.containsKey("groupId")) + sql.append(" AND gu.groupId = :groupId"); + if (args.containsKey("username")) + sql.append(" AND u.username LIKE :username"); + if (args.containsKey("fullname")) + sql.append(" AND u.fullname LIKE :fullname"); + + sql.append(" ORDER BY u.fullname"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public Map queryForMap(String username) { + String sql = "SELECT" + " *" + " FROM users" + " WHERE username = :username"; + + return jdbcDao.queryForMap(sql, MapUtils.toHashMap("username", username)); + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public boolean lockUser(String username, boolean lock) { + return jdbcDao.executeUpdate("UPDATE users SET locked = :lock WHERE username = :username", + MapUtils.toHashMap("username", username, "lock", lock)) > 0; + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public boolean changeLocale(int id, String locale) { + return jdbcDao.executeUpdate("UPDATE users SET locale = :locale WHERE id = :id", + MapUtils.toHashMap("locale", locale, "id", id)) > 0; + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public boolean clone(User instance, String username, String password) { + User newUser = new User(); + BeanUtils.copyProperties(instance, newUser, DataBindUtils.coreFields); + newUser.setUsername(username); + newUser.setPassword(password); + int newId = saveOrUpdate(newUser); + Map args = MapUtils.toHashMap("sourceId", instance.getId(), "targetId", newId); + jdbcDao.executeUpdate("INSERT INTO users_authorities (userId, authority)" + " SELECT :targetId , authority" + + " FROM users_authorities" + " WHERE userId = :sourceId", args); + + jdbcDao.executeUpdate("INSERT INTO groups_users (userId, groupId)" + " SELECT :targetId , groupId" + + " FROM groups_users" + " WHERE userId = :sourceId", args); + return true; + } + + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = true) + public Map getSysGroup(int sysGroupId) { + Map args = new HashMap<>(); + args.put("id", sysGroupId); + //@formatter:off + StringBuilder sql = new StringBuilder(" SELECT " + + " * " + + " FROM sys_groups sg" + + " WHERE sg.deleted = 0"); + //@formatter:on + + if (args.containsKey("id")) + sql.append(" AND sg.id = :id"); + + return jdbcDao.queryForMap(sql.toString(), args); + } + + +} \ No newline at end of file diff --git a/src/main/java/com/ffii/tls/user/service/UserSettingsService.java b/src/main/java/com/ffii/tls/user/service/UserSettingsService.java new file mode 100644 index 0000000..ac66760 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/service/UserSettingsService.java @@ -0,0 +1,158 @@ +/******************************************************************************* + * Copyright 2019 2Fi Business Solutions Ltd. + * + * This code is part of the Core project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.service; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.security.access.SecurityConfig; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Isolation; +import org.springframework.transaction.annotation.Transactional; + +import com.ffii.core.dao.JdbcDao; +import com.ffii.core.setting.Setting; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.NumberUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; + +/** + * System Settings Service + * + * @author Patrick + */ +@Service +public class UserSettingsService { + + private static final String SQL_INSERT_OR_UPDATE_SETTING = "INSERT INTO user_settings (`userId`,`name`, `value`) VALUES (:userId, :name, :value) ON DUPLICATE KEY UPDATE `userId` = VALUES(`userId`),`name` = VALUES(`name`), `value` = VALUES(`value`)"; + + /** + * Settings cache + + private static Map SETTINGS = null; + */ + + @Autowired + private JdbcDao jdbcDao; + + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public List> searchSettings(Map args) { + + int userId = SecurityUtils.getUser().getId(); + args.put("userId", userId); + + + StringBuilder sql = new StringBuilder("SELECT * FROM user_settings WHERE 1=1"); + + if (args.containsKey("category")) sql.append(" AND category = :category"); + if (args.containsKey("userId")) sql.append(" AND userId = :userId"); + if (args.containsKey("name")) sql.append(" AND name = :name"); + + sql.append(" ORDER BY category, name"); + + return jdbcDao.queryForList(sql.toString(), args); + } + + + /** + * @param name + * the name of the setting + * @param defaultValue + * the default value to return if setting is not found + * + * @return the String value of the setting, or the default value if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public String getString(String name, String defaultValue) { + List> userSettings = searchSettings(MapUtils.toHashMap(Params.NAME, name)); + if(userSettings == null) return defaultValue; + return userSettings.get(0).get(name) != null ? userSettings.get(0).get(name).toString() : defaultValue; + } + + /** + * @param name + * the name of the setting + * + * @return the String value of the setting, or {@code null} if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public String getString(String name) { + return getString(name, null); + } + + /** + * @param name + * the name of the setting + * @param defaultValue + * the default value to return if setting is not found + * + * @return the int value of the setting, or the default value if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public int getInt(String name, int defaultValue) { + return NumberUtils.toInt(getString(name), defaultValue); + } + + /** + * @param name + * the name of the setting + * + * @return the int value of the setting, or zero (0) if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public int getInt(String name) { + return getInt(name, 0); + } + + /** + * @param name + * the name of the setting + * @param defaultValue + * the default value to return if setting is not found + * + * @return the double value of the setting, or the default value if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public double getDouble(String name, double defaultValue) { + return NumberUtils.toDouble(getString(name), defaultValue); + } + + /** + * @param name + * the name of the setting + * + * @return the double value of the setting, or zero (0.0) if not found + */ + @Transactional(isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, readOnly = true) + public double getDouble(String name) { + return getDouble(name, 0.0d); + } + + /** + * @param name + * the name of the setting + * @param value + * the value of the setting + */ + @Transactional(isolation = Isolation.SERIALIZABLE, rollbackFor = Exception.class, readOnly = false) + public int saveSetting(String name, String value) { + int userId = SecurityUtils.getUser().getId(); + Map args = new HashMap(); + args.put("userId", userId); + args.put(Params.NAME, name); + args.put(Params.VALUE, value); + return jdbcDao.executeUpdate(SQL_INSERT_OR_UPDATE_SETTING, args); + } + +} diff --git a/src/main/java/com/ffii/tls/user/web/GroupController.java b/src/main/java/com/ffii/tls/user/web/GroupController.java new file mode 100644 index 0000000..cf211ca --- /dev/null +++ b/src/main/java/com/ffii/tls/user/web/GroupController.java @@ -0,0 +1,217 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.web; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.BooleanUtils; +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.JsonUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.user.Group; +import com.ffii.tbms.user.service.GroupService; +import com.ffii.tbms.user.service.AuthService; + +@Controller +@RequestMapping(value = "/user/group") +public class GroupController extends AbstractController { + + @Autowired + private GroupService groupService; + + @Autowired + private AuthService authService; + + @SuppressWarnings("unchecked") + @RequestMapping(value = "/save", method = RequestMethod.POST) + public String save(Model model, HttpServletRequest request, @RequestParam(defaultValue = "-1") Integer id, + @RequestParam(required = false) String userUpdatedRecordsData, + @RequestParam(required = false) String authUpdatedRecordsData) throws Exception { + + Group instance; + if (id > 0) { + instance = groupService.find(id); + } else { + instance = new Group(); + } + + ServletRequestUtils.doBind(request, instance, null); + id = groupService.saveOrUpdate(instance); + + // Handle Group User + if (userUpdatedRecordsData != null) { + List> userUpdatedRecords = JsonUtils.fromJsonStringAsListOfMap(userUpdatedRecordsData); + + List> userBatchInsertValues = new ArrayList>(); + List> userBatchDeleteValues = new ArrayList>(); + + for (Map record : userUpdatedRecords) { + Map batchValue = new HashMap(2); + batchValue.put("groupId", id); + batchValue.put("userId", record.get("id")); + + if (BooleanUtils.isTrue(record.get("v"))) { + userBatchInsertValues.add(batchValue); + } else { + userBatchDeleteValues.add(batchValue); + } + } + + if (userBatchInsertValues.size() > 0) + groupService.addGroupUser(userBatchInsertValues.toArray((Map[]) new Map[0])); + if (userBatchDeleteValues.size() > 0) + groupService.removeGroupUser(userBatchDeleteValues.toArray((Map[]) new Map[0])); + } + + // Handle Group Authority + if (authUpdatedRecordsData != null) { + List> authUpdatedRecords = JsonUtils.fromJsonStringAsListOfMap(authUpdatedRecordsData); + + List> authBatchInsertValues = new ArrayList>(); + List> authBatchDeleteValues = new ArrayList>(); + + for (Map record : authUpdatedRecords) { + Map batchValue = new HashMap(2); + batchValue.put("groupId", id); + batchValue.put("authority", record.get("authority")); + + if (BooleanUtils.isTrue(record.get("v"))) { + authBatchInsertValues.add(batchValue); + } else { + authBatchDeleteValues.add(batchValue); + } + } + + if (authBatchInsertValues.size() > 0) + groupService.addGroupAuth(authBatchInsertValues.toArray((Map[]) new Map[0])); + if (authBatchDeleteValues.size() > 0) + groupService.removeGroupAuth(authBatchDeleteValues.toArray((Map[]) new Map[0])); + } + + model.addAttribute(Params.ID, id); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "/delete", method = RequestMethod.POST) + public String delete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + // find, mark delete, and save + Group instance = groupService.find(id); + groupService.delete(instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + + + @RequestMapping(value = "/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String load(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + Map data = groupService.queryForMap(id); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + + return JsonView.NAME; + } + + @RequestMapping(value = "/combo.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String comboJson(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, Params.QUERY); + + List> records = groupService.searchForCombo(args); + + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, Params.NAME); + CriteriaUtils.addInteger(request, args, "userId"); + + + List> records = groupService.search(args); + + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + + /** + * @param id groupId + */ + @RequestMapping(value = "/user.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String jsonUser(Model model, HttpServletRequest request, @RequestParam(defaultValue = "-1") Integer id) + throws Exception { + + if (id > 0) { + List> records = groupService.listGroupUser(id); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, records != null); + } else + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + return JsonView.NAME; + } + + @RequestMapping(value = "/auth.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String jsonAuth(Model model, HttpServletRequest request) throws Exception { + // Map args = new HashMap(); + int groupId = ServletRequestUtils.getIntParameter(request, Params.ID, 0); + + List> records = groupService.listGroupAuth(groupId); + + model.addAttribute(Params.RECORDS, records); + model.addAttribute(Params.SUCCESS, records != null); + return JsonView.NAME; + } + + @RequestMapping(value = "/authlist.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String jsonListAuth(Model model, HttpServletRequest request) throws Exception { + + List> records = authService.list(); + + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } +} diff --git a/src/main/java/com/ffii/tls/user/web/SysGroupController.java b/src/main/java/com/ffii/tls/user/web/SysGroupController.java new file mode 100644 index 0000000..f860e48 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/web/SysGroupController.java @@ -0,0 +1,179 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.web; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.user.service.SysGroupService; +import com.ffii.tbms.mail.MailUtils; +import com.ffii.tbms.user.service.AuthService; + +@Controller +@RequestMapping(value = "/user/sys-group") +public class SysGroupController extends AbstractController { + + @Autowired + private SysGroupService sysGroupService; + + @Autowired + private AuthService authService; + + @SuppressWarnings("unchecked") + @RequestMapping(value = "/save", method = RequestMethod.POST) + public String save(Model model, HttpServletRequest request, @RequestParam(defaultValue = "-1") Integer id) throws Exception { + + if(id<=0){ + Map args = new HashMap<>(); + CriteriaUtils.addString(request, args, "name"); + CriteriaUtils.addString(request, args, "description"); + CriteriaUtils.addString(request, args, "companyName"); + CriteriaUtils.addString(request, args, "phone"); + CriteriaUtils.addString(request, args, "fax"); + CriteriaUtils.addString(request, args, "email"); + CriteriaUtils.addString(request, args, "address"); + args.put("mailSubject", MailUtils.TEMP_SUBJECT); + args.put("mailBody", MailUtils.TEMP_BODY); + id = sysGroupService.insert(args); + }else{ + Map args = new HashMap<>(); + args.put("id", id); + CriteriaUtils.addString(request, args, "name"); + CriteriaUtils.addString(request, args, "description"); + CriteriaUtils.addString(request, args, "companyName"); + CriteriaUtils.addString(request, args, "phone"); + CriteriaUtils.addString(request, args, "fax"); + CriteriaUtils.addString(request, args, "email"); + CriteriaUtils.addString(request, args, "address"); + if(!args.containsKey("description")){ + args.put("description", null); + } + sysGroupService.update(args); + } + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "/delete", method = RequestMethod.POST) + public String delete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + Map args = new HashMap(); + args.put("id", id); + args.put("deleted", Boolean.TRUE); + sysGroupService.update(args); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + + + @RequestMapping(value = "/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String load(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + Map data = sysGroupService.find(id); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + + return JsonView.NAME; + } + + @RequestMapping(value = "/combo.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String comboJson(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, Params.QUERY); + + List> records = sysGroupService.search(args); + + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, Params.NAME); + CriteriaUtils.addInteger(request, args, "userId"); + + + List> records = sysGroupService.search(args); + + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + + @SuppressWarnings("unchecked") + @RequestMapping(value = "/smtp/save", method = RequestMethod.POST) + public String saveSMTP(Model model, HttpServletRequest request) throws Exception { + int id = SecurityUtils.getUser().getSysGroupId(); + if(id>0){ + Map args = new HashMap<>(); + args.put("id", id); + CriteriaUtils.addString(request, args, "smtp_host"); + CriteriaUtils.addString(request, args, "smtp_port"); + CriteriaUtils.addString(request, args, "smtp_username"); + CriteriaUtils.addString(request, args, "smtp_password"); + sysGroupService.update(args); + } + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + + return JsonView.NAME; + } + + @RequestMapping(value = "/smtp/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String loadSMTP(Model model, HttpServletRequest request) throws Exception { + + Map sysGroup = sysGroupService.find(SecurityUtils.getUser().getSysGroupId()); + + Map data = null; + if(sysGroup != null){ + data = new HashMap<>(); + data.put("smtp_host", sysGroup.get("smtp_host")); + data.put("smtp_port", sysGroup.get("smtp_port")); + data.put("smtp_username", sysGroup.get("smtp_username")); + data.put("smtp_password", sysGroup.get("smtp_password")); + } + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/user/web/UserAuthController.java b/src/main/java/com/ffii/tls/user/web/UserAuthController.java new file mode 100644 index 0000000..046e221 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/web/UserAuthController.java @@ -0,0 +1,52 @@ +/******************************************************************************* + * Copyright 2014 2Fi Business Solutions Ltd. + * + * This code is part of the PCS project. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.web; + +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.user.service.AuthService; + +@Controller +@RequestMapping(value = "/user") +public class UserAuthController extends AbstractController { + + @Autowired + private AuthService authService; + + @RequestMapping(value = "/auth.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String authJson(Model model, HttpServletRequest request, + @RequestParam int userId) throws Exception { + + if (SecurityUtils.isGranted("USER_MAINTAIN")) { + List> records = authService.search(userId); + model.addAttribute(Params.RECORDS, records); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + +} diff --git a/src/main/java/com/ffii/tls/user/web/UserController.java b/src/main/java/com/ffii/tls/user/web/UserController.java new file mode 100644 index 0000000..4fb25b2 --- /dev/null +++ b/src/main/java/com/ffii/tls/user/web/UserController.java @@ -0,0 +1,378 @@ +/******************************************************************************* + * Copyright 2Fi Business Solutions Ltd. + * + * This code is copyrighted. Under no circumstances should any party, people, + * or organization should redistribute any portions of this code in any form, + * either verbatim or through electronic media, to any third parties, unless + * under explicit written permission by 2Fi Business Solutions Ltd. + ******************************************************************************/ +package com.ffii.tbms.user.web; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; + +import com.ffii.core.Settings; +import com.ffii.core.Settings.PasswordRule; +import com.ffii.core.setting.service.SettingsService; +import com.ffii.core.User; +import com.ffii.core.utils.BooleanUtils; +import com.ffii.core.utils.CriteriaUtils; +import com.ffii.core.utils.JsonUtils; +import com.ffii.core.utils.MapUtils; +import com.ffii.core.utils.Params; +import com.ffii.core.utils.SecurityUtils; +import com.ffii.core.utils.StringUtils; +import com.ffii.core.utils.web.ServletRequestUtils; +import com.ffii.core.web.AbstractController; +import com.ffii.core.web.view.json.JsonView; +import com.ffii.tbms.user.service.AuthService; +import com.ffii.tbms.user.service.GroupService; +import com.ffii.tbms.user.service.UserService; +import com.ffii.tbms.user.service.UserSettingsService; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.security.core.userdetails.UserDetailsService; +import org.springframework.security.crypto.password.StandardPasswordEncoder; +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestMethod; +import org.springframework.web.bind.annotation.RequestParam; + +@Controller +@RequestMapping(value = "/user") +public class UserController extends AbstractController { + + @Autowired + private AuthService authService; + + @Autowired + private GroupService groupService; + + @Autowired + private UserService userService; + + @Autowired + private SettingsService settingsService; + + @Autowired + private UserDetailsService userDetailsService; + + @Autowired + private UserSettingsService userSettingsService; + + @Autowired + private StandardPasswordEncoder passwordEncoder; + + @SuppressWarnings("unchecked") + @RequestMapping(value = "/save", method = RequestMethod.POST) + public String save(Model model, HttpServletRequest request, @RequestParam(defaultValue = "-1") Integer id, + @RequestParam(required = false) String password, + @RequestParam(required = false) String groupUpdatedRecordsData, + @RequestParam(required = false) String authUpdatedRecordsData) throws Exception { + + if (SecurityUtils.isGranted("USER_MAINTAIN")) { + User instance; + if (id > 0) { + instance = userService.find(id); + } else { + instance = new User(); + PasswordRule rule = new Settings.PasswordRule(settingsService); + String randomPassword = SecurityUtils.genPwd(rule.getMin(), rule.needNumberChar(), + rule.needUpperEngChar(), rule.needLowerEngChar(), rule.needSpecialChar()); + instance.setPassword(passwordEncoder.encode(randomPassword)); + } + + ServletRequestUtils.doBind(request, instance, ""); + + // handle password hash + if (StringUtils.isNotBlank(password)) { + instance.setPassword(passwordEncoder.encode(password)); + } + + id = userService.saveOrUpdate(instance); + + // handle user's group + if (groupUpdatedRecordsData != null) { + List> groupUpdatedRecords = JsonUtils + .fromJsonStringAsListOfMap(groupUpdatedRecordsData); + + List> groupBatchInsertValues = new ArrayList<>(); + List> groupBatchDeleteValues = new ArrayList<>(); + + for (Map record : groupUpdatedRecords) { + Map batchValue = new HashMap<>(2); + batchValue.put("userId", id); + batchValue.put("groupId", record.get("id")); + + if (BooleanUtils.isTrue(record.get("v"))) { + groupBatchInsertValues.add(batchValue); + } else { + groupBatchDeleteValues.add(batchValue); + } + } + if (groupBatchInsertValues.size() > 0) + groupService.addGroupUser(groupBatchInsertValues.toArray((Map[]) new Map[0])); + if (groupBatchDeleteValues.size() > 0) + groupService.removeGroupUser(groupBatchDeleteValues.toArray((Map[]) new Map[0])); + } + + // Handle Group Authority + if (authUpdatedRecordsData != null) { + List> authUpdatedRecords = JsonUtils + .fromJsonStringAsListOfMap(authUpdatedRecordsData); + + List> authBatchInsertValues = new ArrayList>(); + List> authBatchDeleteValues = new ArrayList>(); + + for (Map record : authUpdatedRecords) { + Map batchValue = new HashMap(2); + batchValue.put("userId", id); + batchValue.put("authority", record.get("authority")); + + if (BooleanUtils.isTrue(record.get("v"))) { + authBatchInsertValues.add(batchValue); + } else { + authBatchDeleteValues.add(batchValue); + } + } + + if (authBatchInsertValues.size() > 0) + authService.batchInsertUsersAuthorities( + authBatchInsertValues.toArray((Map[]) new Map[0])); + + if (authBatchDeleteValues.size() > 0) + authService.batchDeleteUsersAuthorities( + authBatchDeleteValues.toArray((Map[]) new Map[0])); + } + + model.addAttribute(Params.ID, id); + model.addAttribute(Params.VERSION_ID, instance.getVersionId()); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/get-lang", method = { RequestMethod.GET, RequestMethod.POST }) + public String getLang(Model model, HttpServletRequest request) throws Exception { + User instance = userService.find(SecurityUtils.getUser().getId()); + model.addAttribute("locale", instance.getLocale()); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "/get-settings", method = { RequestMethod.GET, RequestMethod.POST }) + public String getUserSettings(Model model, HttpServletRequest request) throws Exception { + List> userSettings = userSettingsService.searchSettings(new HashMap<>()); + model.addAttribute(Params.RECORDS, userSettings); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "/setting/save", method = { RequestMethod.GET, RequestMethod.POST }) + public String saveUserSetting(Model model, HttpServletRequest request, String name, String value) throws Exception { + userSettingsService.saveSetting(name, value); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + return JsonView.NAME; + } + + @RequestMapping(value = "/change-lang", method = { RequestMethod.POST }) + public String changeLang(Model model, HttpServletRequest request, @RequestParam String locale) throws Exception { + User instance = userService.find(SecurityUtils.getUser().getId()); + if (instance != null) { + instance.setLocale(locale); + userService.saveOrUpdate(instance); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.MSG, "no record"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/delete", method = RequestMethod.POST) + public String delete(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("USER_MAINTAIN")) { + + // find, mark delete, and save + User instance = userService.find(id); + instance.setDeleted(true); + userService.saveOrUpdate(instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/load", method = { RequestMethod.GET, RequestMethod.POST }) + public String load(Model model, HttpServletRequest request, @RequestParam Integer id) throws Exception { + + if (SecurityUtils.isGranted("USER_MAINTAIN")) { + Map data = userService.findUserMap(MapUtils.toHashMap("id", id)); + + // remove un-necessary fields + data.remove("password"); + + model.addAttribute(Params.DATA, data); + model.addAttribute(Params.SUCCESS, data != null); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/combo.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String comboJson(Model model, HttpServletRequest request, @RequestParam(required=false, defaultValue="false") Boolean send) throws Exception { + + Map args = new HashMap(); + + if(send){ + args.put("senderId", SecurityUtils.getUser().getId()); + } + + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, Params.QUERY); + + // if current user is not from host compnay, then restrict access to users in + // (self company + host company) + if (SecurityUtils.getUser().getCompanyId() > 1) { + List companyIds = new ArrayList(); + companyIds.add(1); // add host company + companyIds.add(SecurityUtils.getUser().getCompanyId()); + + args.put("companyIds", companyIds); + } + + List> records = userService.searchForCombo(args); + + model.addAttribute(Params.RECORDS, records); + + return JsonView.NAME; + } + + @RequestMapping(value = "/list.json", method = { RequestMethod.GET, RequestMethod.POST }) + public String listJson(Model model, HttpServletRequest request) throws Exception { + + if (SecurityUtils.isGranted("USER_MAINTAIN")) { + Map args = new HashMap(); + + CriteriaUtils.addInteger(request, args, Params.ID); + CriteriaUtils.addStringLike(request, args, "fullname"); + CriteriaUtils.addStringLike(request, args, "username"); + CriteriaUtils.addInteger(request, args, "sysGroupId"); + CriteriaUtils.addInteger(request, args, "groupId"); + CriteriaUtils.addInteger(request, args, "recipient"); + + List> records = userService.search(args); + + model.addAttribute(Params.RECORDS, records); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/login-as", method = RequestMethod.POST) + public String loginAs(Model model, @RequestParam String username) { + if (SecurityUtils.isGranted("USER_MAINTAIN")) { + SecurityUtils.loginUser(userDetailsService, username); + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + + @RequestMapping(value = "/change-password", method = RequestMethod.POST) + public String changePassword(Model model, HttpServletRequest request, @RequestParam String password, + @RequestParam String newPassword) throws Exception { + + int id = SecurityUtils.getUser().getId(); + User instance = userService.find(id); + + if (passwordEncoder.matches(password, instance.getPassword())) { + PasswordRule rule = new Settings.PasswordRule(settingsService); + if (SecurityUtils.checkPwd(newPassword, rule.getMin(), rule.getMax(), rule.needNumberChar(), + rule.needUpperEngChar(), rule.needLowerEngChar(), rule.needSpecialChar())) { + instance.setPassword(passwordEncoder.encode(newPassword)); + userService.saveOrUpdateForChangePwd(instance); + + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.MSG, rule.getWrongMsg()); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + } else { + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/reset-password", method = RequestMethod.POST) + public String resetPassword(Model model, HttpServletRequest request, @RequestParam Integer userId) + throws Exception { + + if (SecurityUtils.isGranted("USER_MAINTAIN")) { + User instance = userService.find(userId); + if (instance != null) { + PasswordRule rule = new Settings.PasswordRule(settingsService); + String randomPassword = SecurityUtils.genPwd(rule.getMin(), rule.needNumberChar(), + rule.needUpperEngChar(), rule.needLowerEngChar(), rule.needSpecialChar()); + + instance.setPassword(passwordEncoder.encode(randomPassword)); + userService.saveOrUpdate(instance); + + model.addAttribute(Params.DATA, randomPassword); + } + model.addAttribute(Params.SUCCESS, Boolean.TRUE); + } else { + model.addAttribute(Params.MSG, "No Auth"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + + return JsonView.NAME; + } + + @RequestMapping(value = "/clone", method = { RequestMethod.POST }) + public String clone(Model model, HttpServletRequest request, @RequestParam Integer id, + @RequestParam String username, @RequestParam String password) throws Exception { + if (SecurityUtils.isGranted("USER_MAINTAIN")) { + User instance = userService.find(id); + if (instance != null) { + PasswordRule rule = new Settings.PasswordRule(settingsService); + if (SecurityUtils.checkPwd(password, rule.getMin(), rule.getMax(), rule.needNumberChar(), + rule.needUpperEngChar(), rule.needLowerEngChar(), rule.needSpecialChar())) { + model.addAttribute(Params.SUCCESS, + userService.clone(instance, username, passwordEncoder.encode(password))); + } else { + model.addAttribute(Params.MSG, rule.getWrongMsg()); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + } else { + model.addAttribute(Params.MSG, "no record"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + } else { + model.addAttribute(Params.MSG, "No Auth"); + model.addAttribute(Params.SUCCESS, Boolean.FALSE); + } + return JsonView.NAME; + } + +} \ No newline at end of file diff --git a/src/main/webapp/META-INF/context.xml b/src/main/webapp/META-INF/context.xml new file mode 100644 index 0000000..11b5999 --- /dev/null +++ b/src/main/webapp/META-INF/context.xml @@ -0,0 +1,26 @@ + + + + \ No newline at end of file diff --git a/src/main/webapp/META-INF/context.xml.2fi b/src/main/webapp/META-INF/context.xml.2fi new file mode 100644 index 0000000..6deecd1 --- /dev/null +++ b/src/main/webapp/META-INF/context.xml.2fi @@ -0,0 +1,26 @@ + + + + \ No newline at end of file diff --git a/src/main/webapp/META-INF/context.xml.local b/src/main/webapp/META-INF/context.xml.local new file mode 100644 index 0000000..11b5999 --- /dev/null +++ b/src/main/webapp/META-INF/context.xml.local @@ -0,0 +1,26 @@ + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/app.properties b/src/main/webapp/WEB-INF/app.properties new file mode 100644 index 0000000..4784a53 --- /dev/null +++ b/src/main/webapp/WEB-INF/app.properties @@ -0,0 +1,2 @@ +#Deployment-specific properties for Project. +freemarker.template.home=file:C:/Workspace/TBMS/src/main/webapp/WEB-INF/ diff --git a/src/main/webapp/WEB-INF/app.properties.local b/src/main/webapp/WEB-INF/app.properties.local new file mode 100644 index 0000000..4784a53 --- /dev/null +++ b/src/main/webapp/WEB-INF/app.properties.local @@ -0,0 +1,2 @@ +#Deployment-specific properties for Project. +freemarker.template.home=file:C:/Workspace/TBMS/src/main/webapp/WEB-INF/ diff --git a/src/main/webapp/WEB-INF/app.properties.local.mac b/src/main/webapp/WEB-INF/app.properties.local.mac new file mode 100644 index 0000000..61c2ce5 --- /dev/null +++ b/src/main/webapp/WEB-INF/app.properties.local.mac @@ -0,0 +1,2 @@ +#Deployment-specific properties for Project. +freemarker.template.home=file:/Users/2fiadmin/workspace/TBMS/src/main/webapp/WEB-INF/ diff --git a/src/main/webapp/WEB-INF/app.properties.prod b/src/main/webapp/WEB-INF/app.properties.prod new file mode 100644 index 0000000..5b9c9a2 --- /dev/null +++ b/src/main/webapp/WEB-INF/app.properties.prod @@ -0,0 +1,2 @@ +#Deployment-specific properties for Project. +freemarker.template.home=/WEB-INF/ diff --git a/src/main/webapp/WEB-INF/application-context.xml b/src/main/webapp/WEB-INF/application-context.xml new file mode 100644 index 0000000..2c557bd --- /dev/null +++ b/src/main/webapp/WEB-INF/application-context.xml @@ -0,0 +1,71 @@ + + + + + + + + + WEB-INF/app.properties + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/classes/log4j.properties b/src/main/webapp/WEB-INF/classes/log4j.properties new file mode 100644 index 0000000..2600439 --- /dev/null +++ b/src/main/webapp/WEB-INF/classes/log4j.properties @@ -0,0 +1,22 @@ +#log4j properties +log4j.rootCategory=info,logfile + +#log4j.category.org.hibernate=logfile +#log4j.appender.console=org.apache.log4j.ConsoleAppender +#log4j.appender.console.Target=System.out +#log4j.appender.console.Threshold=DEBUG +#log4j.appender.console.layout=org.apache.log4j.PatternLayout +#log4j.appender.console.layout.ConversionPattern=%d{ABSOLUTE} %-5p [%c{1}.%M] %m%n +#log4j.logger.org.hibernate.SQL=DEBUG, SQL_APPENDER +#log4j.additivity.org.hibernate.SQL=false + + + +log4j.appender.logfile=org.apache.log4j.RollingFileAppender +log4j.appender.logfile.File=C:/Workspace/all.log +log4j.appender.logfile.MaxFileSize=4096KB +# Keep three backup files +log4j.appender.logfile.MaxBackupIndex=2 +log4j.appender.logfile.layout=org.apache.log4j.PatternLayout +#Pattern to output : date priority [category] - line_separator +log4j.appender.logfile.layout.ConversionPattern=%d %p [%l] - %m%n \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/classes/log4j.properties.local.mac b/src/main/webapp/WEB-INF/classes/log4j.properties.local.mac new file mode 100644 index 0000000..ca4a877 --- /dev/null +++ b/src/main/webapp/WEB-INF/classes/log4j.properties.local.mac @@ -0,0 +1,22 @@ +#log4j properties +log4j.rootCategory=info,logfile + +#log4j.category.org.hibernate=logfile +#log4j.appender.console=org.apache.log4j.ConsoleAppender +#log4j.appender.console.Target=System.out +#log4j.appender.console.Threshold=DEBUG +#log4j.appender.console.layout=org.apache.log4j.PatternLayout +#log4j.appender.console.layout.ConversionPattern=%d{ABSOLUTE} %-5p [%c{1}.%M] %m%n +#log4j.logger.org.hibernate.SQL=DEBUG, SQL_APPENDER +#log4j.additivity.org.hibernate.SQL=false + + + +log4j.appender.logfile=org.apache.log4j.RollingFileAppender +log4j.appender.logfile.File=/Users/2fiadmin/workspace/all.log +log4j.appender.logfile.MaxFileSize=4096KB +# Keep three backup files +log4j.appender.logfile.MaxBackupIndex=2 +log4j.appender.logfile.layout=org.apache.log4j.PatternLayout +#Pattern to output : date priority [category] - line_separator +log4j.appender.logfile.layout.ConversionPattern=%d %p [%l] - %m%n \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/classes/log4j.properties.prod b/src/main/webapp/WEB-INF/classes/log4j.properties.prod new file mode 100644 index 0000000..2600439 --- /dev/null +++ b/src/main/webapp/WEB-INF/classes/log4j.properties.prod @@ -0,0 +1,22 @@ +#log4j properties +log4j.rootCategory=info,logfile + +#log4j.category.org.hibernate=logfile +#log4j.appender.console=org.apache.log4j.ConsoleAppender +#log4j.appender.console.Target=System.out +#log4j.appender.console.Threshold=DEBUG +#log4j.appender.console.layout=org.apache.log4j.PatternLayout +#log4j.appender.console.layout.ConversionPattern=%d{ABSOLUTE} %-5p [%c{1}.%M] %m%n +#log4j.logger.org.hibernate.SQL=DEBUG, SQL_APPENDER +#log4j.additivity.org.hibernate.SQL=false + + + +log4j.appender.logfile=org.apache.log4j.RollingFileAppender +log4j.appender.logfile.File=C:/Workspace/all.log +log4j.appender.logfile.MaxFileSize=4096KB +# Keep three backup files +log4j.appender.logfile.MaxBackupIndex=2 +log4j.appender.logfile.layout=org.apache.log4j.PatternLayout +#Pattern to output : date priority [category] - line_separator +log4j.appender.logfile.layout.ConversionPattern=%d %p [%l] - %m%n \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/dao.xml b/src/main/webapp/WEB-INF/dao.xml new file mode 100644 index 0000000..a3fbb1c --- /dev/null +++ b/src/main/webapp/WEB-INF/dao.xml @@ -0,0 +1,21 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/dataSource.xml b/src/main/webapp/WEB-INF/dataSource.xml new file mode 100644 index 0000000..e20a201 --- /dev/null +++ b/src/main/webapp/WEB-INF/dataSource.xml @@ -0,0 +1,34 @@ + + + + + + + + + + + org.hibernate.dialect.MySQL57Dialect + + 1 + + false + true + true + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/db/changelog.sql b/src/main/webapp/WEB-INF/db/changelog.sql new file mode 100644 index 0000000..7418af2 --- /dev/null +++ b/src/main/webapp/WEB-INF/db/changelog.sql @@ -0,0 +1,3 @@ +--liquibase formatted sql +--format: https://www.liquibase.org/documentation/sql_format.html + diff --git a/src/main/webapp/WEB-INF/favicon.ico b/src/main/webapp/WEB-INF/favicon.ico new file mode 100644 index 0000000..1c11eee Binary files /dev/null and b/src/main/webapp/WEB-INF/favicon.ico differ diff --git a/src/main/webapp/WEB-INF/mail.xml b/src/main/webapp/WEB-INF/mail.xml new file mode 100644 index 0000000..5d7f678 --- /dev/null +++ b/src/main/webapp/WEB-INF/mail.xml @@ -0,0 +1,27 @@ + + + + + + + + + + + + true + true + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/mail/contentMail.ftl b/src/main/webapp/WEB-INF/mail/contentMail.ftl new file mode 100644 index 0000000..7b9405b --- /dev/null +++ b/src/main/webapp/WEB-INF/mail/contentMail.ftl @@ -0,0 +1,11 @@ +<#import "/spring.ftl" as spring> + + + + + + + +${content} + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/mail/exampleMail.ftl b/src/main/webapp/WEB-INF/mail/exampleMail.ftl new file mode 100644 index 0000000..48e62f2 --- /dev/null +++ b/src/main/webapp/WEB-INF/mail/exampleMail.ftl @@ -0,0 +1,12 @@ +<#import "/spring.ftl" as spring> + + + + + +Hello ${name} + + +

Hello ${name}

+ + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/mail/invoiceTemplateMail.ftl b/src/main/webapp/WEB-INF/mail/invoiceTemplateMail.ftl new file mode 100644 index 0000000..78e9499 --- /dev/null +++ b/src/main/webapp/WEB-INF/mail/invoiceTemplateMail.ftl @@ -0,0 +1,14 @@ +<#import "/spring.ftl" as spring> + + + + + + + + +Dear Customer,

Order No.: {$orderNo}
Order Date: {$orderDate}
Order Amount: {$amount}

Please find attached invoice for more details, Thank you.

+Yours faithfully,

+2fi business solutions limited
Suite 1405, 14/F, Century Square, 1-13 D'Aguilar Street, Central, Hong Kong 
Tel: (852) 2804-6788 Fax: (852) 2804-6997
Email: sales@dreambespoke.com
+ + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/mail/invoiceTemplateMail2.ftl b/src/main/webapp/WEB-INF/mail/invoiceTemplateMail2.ftl new file mode 100644 index 0000000..ee67459 --- /dev/null +++ b/src/main/webapp/WEB-INF/mail/invoiceTemplateMail2.ftl @@ -0,0 +1,14 @@ +<#import "/spring.ftl" as spring> + + + + + + + + +Dear Customer,

Order No.: {$orderNo}
Order Date: {$orderDate}
Order Amount: {$amount}

Please find attached invoice for more details, Thank you.

+Yours faithfully,

+Dream Bespoke Limited
Suite 1405, 14/F, Century Square, 1-13 D'Aguilar Street, Central, Hong Kong 
Tel: (852) 2804-6788 Fax: (852) 2804-6997
Email: sales@dreambespoke.com
+ + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/mvc-dispatcher-servlet.xml b/src/main/webapp/WEB-INF/mvc-dispatcher-servlet.xml new file mode 100644 index 0000000..c1146fe --- /dev/null +++ b/src/main/webapp/WEB-INF/mvc-dispatcher-servlet.xml @@ -0,0 +1,26 @@ + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/report/cust_first_order.xlsx b/src/main/webapp/WEB-INF/report/cust_first_order.xlsx new file mode 100644 index 0000000..200cb06 Binary files /dev/null and b/src/main/webapp/WEB-INF/report/cust_first_order.xlsx differ diff --git a/src/main/webapp/WEB-INF/report/customer.xlsx b/src/main/webapp/WEB-INF/report/customer.xlsx new file mode 100644 index 0000000..964914f Binary files /dev/null and b/src/main/webapp/WEB-INF/report/customer.xlsx differ diff --git a/src/main/webapp/WEB-INF/report/dreamBespokeInvoiceTemp.jrxml b/src/main/webapp/WEB-INF/report/dreamBespokeInvoiceTemp.jrxml new file mode 100644 index 0000000..e4950b5 --- /dev/null +++ b/src/main/webapp/WEB-INF/report/dreamBespokeInvoiceTemp.jrxml @@ -0,0 +1,353 @@ + + + + + + + + + + + + + + + + + + + + + + <band height="151" splitType="Stretch"> + <staticText> + <reportElement x="0" y="80" width="555" height="31" uuid="5f97a73f-7f05-4694-aa31-8c30a0be1c84"/> + <textElement textAlignment="Center"> + <font size="24" isBold="false"/> + </textElement> + <text><![CDATA[Dream Bespoke Limited]]></text> + </staticText> + <staticText> + <reportElement x="0" y="113" width="555" height="38" uuid="fe9c6e35-6cdf-471d-be30-39ddb39f8896"/> + <textElement textAlignment="Center" markup="html"> + <font size="12"/> + </textElement> + <text><![CDATA[Suite 1405, 14/F, Century Square, 1-13 D'Aguilar Street, Central, Hong Kong.<br/>Tel: (852) 2804-6788 Fax: (852) 2804-6997 Email: sales@dreambespoke.com]]></text> + </staticText> + <image scaleImage="RealSize" hAlign="Center" vAlign="Bottom"> + <reportElement x="180" y="0" width="200" height="80" uuid="a03bd52d-7bf5-40cf-ac5a-2b31d62074b8"/> + <graphicElement fill="Solid"/> + <imageExpression><![CDATA["./image/dream_bespoke_icon.png"]]></imageExpression> + </image> + <textField> + <reportElement x="454" y="10" width="100" height="30" uuid="51c583cf-aaa2-4224-ade0-2d68b86a21cc"/> + <textElement textAlignment="Right"> + <font size="12" isBold="true"/> + </textElement> + <textFieldExpression><![CDATA[$P{orderNo}]]></textFieldExpression> + </textField> + </band> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/main/webapp/WEB-INF/report/dream_bespoke_icon.png b/src/main/webapp/WEB-INF/report/dream_bespoke_icon.png new file mode 100644 index 0000000..6a5c612 Binary files /dev/null and b/src/main/webapp/WEB-INF/report/dream_bespoke_icon.png differ diff --git a/src/main/webapp/WEB-INF/report/dream_bespoke_icon2.png b/src/main/webapp/WEB-INF/report/dream_bespoke_icon2.png new file mode 100644 index 0000000..edc091c Binary files /dev/null and b/src/main/webapp/WEB-INF/report/dream_bespoke_icon2.png differ diff --git a/src/main/webapp/WEB-INF/report/invoiceTemp.jrxml b/src/main/webapp/WEB-INF/report/invoiceTemp.jrxml new file mode 100644 index 0000000..fb7ad61 --- /dev/null +++ b/src/main/webapp/WEB-INF/report/invoiceTemp.jrxml @@ -0,0 +1,355 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + <band height="121" splitType="Stretch"> + <image scaleImage="RetainShape" hAlign="Center" vAlign="Middle"> + <reportElement x="170" y="0" width="220" height="50" uuid="57915fcd-d22d-4c6a-b920-730f4ed689a3"/> + <imageExpression><![CDATA[$P{companyIcon}]]></imageExpression> + </image> + <textField isBlankWhenNull="true"> + <reportElement x="0" y="50" width="555" height="30" uuid="605f1eec-4d39-449b-a711-b27ea1daee56"/> + <textElement textAlignment="Center" verticalAlignment="Middle"> + <font size="18"/> + </textElement> + <textFieldExpression><![CDATA[$P{companyName}]]></textFieldExpression> + </textField> + <textField isBlankWhenNull="true"> + <reportElement x="0" y="80" width="555" height="41" uuid="a4fa51c0-299d-4a01-8fa6-0ae9d25b6e4d"/> + <textElement textAlignment="Center" markup="html"> + <font size="12" isBold="false"/> + </textElement> + <textFieldExpression><![CDATA[$P{contactStr}]]></textFieldExpression> + </textField> + <textField isBlankWhenNull="true"> + <reportElement x="455" y="0" width="100" height="30" uuid="a947f3aa-a8bb-4dec-a012-a1d6572f3173"/> + <textElement textAlignment="Right" verticalAlignment="Middle"> + <font size="12"/> + </textElement> + <textFieldExpression><![CDATA[$P{orderNo}]]></textFieldExpression> + </textField> + </band> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/main/webapp/WEB-INF/report/invoiceTemp2.jrxml b/src/main/webapp/WEB-INF/report/invoiceTemp2.jrxml new file mode 100644 index 0000000..7b5119f --- /dev/null +++ b/src/main/webapp/WEB-INF/report/invoiceTemp2.jrxml @@ -0,0 +1,353 @@ + + + + + + + + + + + + + + + + + + + + + + + + + <band height="121" splitType="Stretch"> + <image scaleImage="RetainShape" hAlign="Center" vAlign="Middle"> + <reportElement x="170" y="0" width="220" height="50" uuid="57915fcd-d22d-4c6a-b920-730f4ed689a3"/> + <imageExpression><![CDATA[$P{imagePath}]]></imageExpression> + </image> + <staticText> + <reportElement x="0" y="50" width="555" height="30" uuid="59fb14e9-3d79-438d-9a66-9a485bbce557"/> + <textElement textAlignment="Center" verticalAlignment="Middle"> + <font size="18"/> + </textElement> + <text><![CDATA[Dream Bespoke Limited]]></text> + </staticText> + <staticText> + <reportElement x="0" y="80" width="555" height="41" uuid="cfd1a3a8-5645-4073-a9d7-5bd4c150f563"/> + <textElement textAlignment="Center" markup="html"> + <font size="12" isBold="false"/> + </textElement> + <text><![CDATA[Suite 1405, 14/F, Century Square, 1-13 D'Aguilar Street, Central, Hong Kong.<br/>Tel: (852) 2804-6788   Fax: (852) 2804-6997   Email: sales@dreambespoke.com]]></text> + </staticText> + <textField isBlankWhenNull="true"> + <reportElement x="455" y="0" width="100" height="30" uuid="a947f3aa-a8bb-4dec-a012-a1d6572f3173"/> + <textElement textAlignment="Right" verticalAlignment="Middle"> + <font size="12"/> + </textElement> + <textFieldExpression><![CDATA[$P{orderNo}]]></textFieldExpression> + </textField> + </band> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/main/webapp/WEB-INF/report/measurementSheet.jrxml b/src/main/webapp/WEB-INF/report/measurementSheet.jrxml new file mode 100644 index 0000000..7927db8 --- /dev/null +++ b/src/main/webapp/WEB-INF/report/measurementSheet.jrxml @@ -0,0 +1,46 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
單號 : "+$F{orderNo}]]>
+
+
+
+
diff --git a/src/main/webapp/WEB-INF/report/measurementSheetImage.jpeg b/src/main/webapp/WEB-INF/report/measurementSheetImage.jpeg new file mode 100644 index 0000000..335e749 Binary files /dev/null and b/src/main/webapp/WEB-INF/report/measurementSheetImage.jpeg differ diff --git a/src/main/webapp/WEB-INF/report/order.xlsx b/src/main/webapp/WEB-INF/report/order.xlsx new file mode 100644 index 0000000..6d0f704 Binary files /dev/null and b/src/main/webapp/WEB-INF/report/order.xlsx differ diff --git a/src/main/webapp/WEB-INF/report/outstanding.xlsx b/src/main/webapp/WEB-INF/report/outstanding.xlsx new file mode 100644 index 0000000..1634536 Binary files /dev/null and b/src/main/webapp/WEB-INF/report/outstanding.xlsx differ diff --git a/src/main/webapp/WEB-INF/report/payment.xlsx b/src/main/webapp/WEB-INF/report/payment.xlsx new file mode 100644 index 0000000..a0bb0f9 Binary files /dev/null and b/src/main/webapp/WEB-INF/report/payment.xlsx differ diff --git a/src/main/webapp/WEB-INF/report/preview.jrxml b/src/main/webapp/WEB-INF/report/preview.jrxml new file mode 100644 index 0000000..6c39320 --- /dev/null +++ b/src/main/webapp/WEB-INF/report/preview.jrxml @@ -0,0 +1,23 @@ + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/main/webapp/WEB-INF/report/tlsPrintPreview.jrxml b/src/main/webapp/WEB-INF/report/tlsPrintPreview.jrxml new file mode 100644 index 0000000..27303fa --- /dev/null +++ b/src/main/webapp/WEB-INF/report/tlsPrintPreview.jrxml @@ -0,0 +1,23 @@ + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/main/webapp/WEB-INF/root/home.ftl b/src/main/webapp/WEB-INF/root/home.ftl new file mode 100644 index 0000000..a2503a3 --- /dev/null +++ b/src/main/webapp/WEB-INF/root/home.ftl @@ -0,0 +1,344 @@ +<#import "/spring.ftl" as spring> + + + + + + +TBMS + + +<#-- + +--> + + +<#-- Ext JS --> + + + + +<#-- Ext JS Theme --> + + "> +<#-- Ext JS Additional Packages --> + <#-- D3 --> + + "> + + <#-- Charts --> + + "> + + <#-- Calendar --> + + "> + + <#-- UX --> + + "> + + <#-- Date Range Picker --> + + + +<#-- <#if SecurityUtils.getUser().username == ""> + +<#else> + + --> + +<#-- Main and Icons CSS --> + "> + "> + "> + "> + "> + "> + "> + <#-- + "> + "> + --> + +<#-- App --> + + + + + + + + +<#-- Common stores --> + + + + + + +<#-- Common --> + + + + + + + + + + + +<#-- Common Combo --> + + + + + + + + + + + +<#-- Common Field --> + + + + + + +<#-- Viewport --> + + + + + +<#-- Group --> + + + + + + + +<#-- User --> + + + + + + + + + + +<#-- ################################################## Operation ################################################## --> + + +<#-- ################################################## End of Operation ################################################## --> + + +<#-- Order --> + + + + + + + + + + + + + + + + + + +<#-- Invoice Template --> + + +<#-- Workshop --> + + + + + + + + +<#-- Customer --> + + + + + + + + + + +<#-- Message --> + + + + + + + + + +<#-- Meeting --> + + + + + +<#-- Setting --> + + + + + + + + +<#-- Calendar --> + + + + + + +<#-- Report --> + + + + + + +<#-- Material --> + + + + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/root/index.ftl b/src/main/webapp/WEB-INF/root/index.ftl new file mode 100644 index 0000000..795f982 --- /dev/null +++ b/src/main/webapp/WEB-INF/root/index.ftl @@ -0,0 +1,280 @@ +<#import "/spring.ftl" as spring> + + + + + + +TBMS + + +<#-- + +--> + +<#-- Ext JS --> + + +"> + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/root/oldhome.ftl b/src/main/webapp/WEB-INF/root/oldhome.ftl new file mode 100644 index 0000000..6852af9 --- /dev/null +++ b/src/main/webapp/WEB-INF/root/oldhome.ftl @@ -0,0 +1,175 @@ +<#import "/spring.ftl" as spring> + + + + + + +SMS +" /> + +<#-- + +--> + + +<#-- Ext JS --> + + + + +<#-- Ext JS Theme --> + + "> + + + + +<#-- Ext JS Additional Packages --> + <#-- D3 --> + + "> + + <#-- Charts --> + + "> + + <#-- Calendar --> + + "> + + <#-- UX --> + + "> + + <#-- Date Range Picker --> + + + + +<#-- Main and Icons CSS --> + "> + "> + "> + "> + "> + <#-- + "> + "> + --> + +<#-- App --> + + +<#-- Common stores --> + + +<#-- Viewport --> + + + + +<#-- Vendor --> + + + + + +<#-- Equipment --> + + + + + + + + + + + diff --git a/src/main/webapp/WEB-INF/security.xml b/src/main/webapp/WEB-INF/security.xml new file mode 100644 index 0000000..728f2c4 --- /dev/null +++ b/src/main/webapp/WEB-INF/security.xml @@ -0,0 +1,90 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/services.xml b/src/main/webapp/WEB-INF/services.xml new file mode 100644 index 0000000..abd4637 --- /dev/null +++ b/src/main/webapp/WEB-INF/services.xml @@ -0,0 +1,21 @@ + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/sjs/controller/App.js.ftl b/src/main/webapp/WEB-INF/sjs/controller/App.js.ftl new file mode 100644 index 0000000..0e3103e --- /dev/null +++ b/src/main/webapp/WEB-INF/sjs/controller/App.js.ftl @@ -0,0 +1,886 @@ +<#import "/spring.ftl" as spring> +/** + * App.js + * + * @author Patrick + */ +App = { + name: 'TBMS', + version: '5.0', + navMenu: [], + localeMap_en: {}, + localeMap_zh: {}, + localeMap_ch: {}, + localeCode: '', + userSettings: { + "USER_materialItemGroup":"T", + "USER_showMaterialItemCost": "F", + }, + username: '${SecurityUtils.getUser().getUsername()?js_string}', + fullname: '${SecurityUtils.getUser().getFullname()?js_string}', + userAuths: [], + msgPos: [ 0, 0, 0, 0, 0, 0, 0, 0 ],<#-- remember which msg position is currently being used --> + fullMonthNames: ['January', 'February', 'March', 'April', 'May', 'June', + 'July', 'August', 'September', 'October', 'November', 'December'], + monthNames: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'], + debug: true, + trace: false, <#-- show trace when log --> + vp: null, + autoRefreshInterval: 30000, + intNumberFormat: '0,000', + moneyNumberFormat: '0,000.00######', + floatNumberFormat: '0,000.0000', + unitCostFormat: '0,000.########', + confirmedColor: '#80EA65', + <#-- Ext.Date.format(date, format) --> + dateFormat: 'd/m/Y', + monthYearFormat: 'M Y', + dateTimeFormat: 'Y-m-d H:i', + timeFormat: 'H:i', + dateTimeSubmitFormat: 'Y-m-d\\TH:i:s', + dateTimeSecFormat: 'd/m/Y H:i:s', + colDateTimeFormat: 'd/m/Y H:i', + colDateFormat: 'd-m-Y', + readOnlyStyle: 'background-color: #ddd;', + linkStyle: 'color: blue; text-decoration:underline; cursor:pointer;', + runner: new Ext.util.TaskRunner(), + csrf: '${_csrf}', + basePath: '<@spring.url "" />', + panelAuths: new Map([ + ["calendarContainer", ["CALENDAR_VIEW"]], + ["orderContainer", ["ORDER_MAINTAIN"]], + ["workshopContainer", ["WORKSHOP_MAINTAIN"]], + ["customerContainer", ["CUSTOMER_MAINTAIN"]], + ["report_PaymentContainer", ["PAYMENT_REPORT"]], + ["userBaseContainer", ["USER_MAINTAIN"]], + ["materialContainer", ["PRICE_LIST_VIEW","PRICE_LIST_MAINTAIN"]], + ["invoiceTemplateContainer", ["MATERIAL_MAIL_TEMPLATE"]], + ]) +}; + +Ext.apply(App, { + url: function(url) { + return this.basePath + url; + }, + + log: function(o) { + if (this.debug) { + console.log(o); + if (this.trace) console.trace(); + } + }, + + nl2br: function(v) { + return Ext.isEmpty(v) ? v : v.replace(/\r?\n/g, '
'); + }, + + confirm: function(msg, title, fn) { + Ext.Msg.show({ + title: title || '<@spring.message "COMMON.pleaseConfirm"/>', + msg: msg, + width: 400, + minHeight: 150, + icon: Ext.Msg.QUESTION, + buttons: Ext.Msg.YESNO, + fn: fn || function(buttonId, text, opt) { + } + }); + }, + + showInfo: function(msg, title, fn) { + Ext.Msg.show({ + title: title || 'Information', + msg: msg, + width: 300, + minHeight: 150, + icon: Ext.Msg.INFO, + buttons: Ext.Msg.OK, + fn: fn || function(buttonId, text, opt) { + } + }); + }, + + showWarning: function(msg, title) { + Ext.Msg.show({ + title: title || 'Warning', + msg: msg, + width: 300, + minHeight: 150, + icon: Ext.Msg.WARNING, + buttons: Ext.Msg.OK + }); + }, + + showError: function(msg, title) { + Ext.Msg.show({ + title: title || 'Error', + msg: msg, + width: 300, + minHeight: 150, + icon: Ext.Msg.ERROR, + buttons: Ext.Msg.OK + }); + }, + + showException: function(msg, details, title){ + Ext.Msg.show({ + title: title || 'Action Failure', + msg: msg, + width: 300, + minHeight: 150, + icon: Ext.Msg.ERROR, + buttons: Ext.Msg.YESNO, + buttonText: {yes: 'OK',no: 'Show Details'}, + fn: function(buttonId){ + if(buttonId=='no'){ + Ext.Msg.show({ + title: msg, + msg: '
' + details + '
', + buttons: Ext.Msg.OK, + fn: function(buttonId){ + } + }); + } + } + }); + }, + + showPrompt: function(msg, title, fn, multiLine){ + Ext.Msg.prompt( + title, + msg, + fn || function(buttonId,value){}, + null, + multiLine + ); + }, + + showMsg: function(msg, duration) { + var me = this, + pos = 0; + + <#-- find out which position is available --> + for (var i = 0; i < me.msgPos.length; i++) { + if (me.msgPos[i] == 0) { + me.msgPos[i] = 1; + pos = i; + break; + } + } + //console.log(pos); + + var bottom = pos * 65 + 30, + el = Ext.getBody().createChild({ html: msg, style: 'display:none; position:fixed; bottom:' + bottom + 'px; right:30px; width:280px; height:60px; padding:20px; border-radius:10px; background-color:#64AA00; color:white; text-align:center; font-size:18px; z-index:99999;' }); + + el.slideIn('b'); + setTimeout(function() { el.fadeOut({ remove: true }); me.msgPos[pos] = 0; }, duration || 2500); + }, + + initLoadMask: function() { + if (!this.loadMask && Ext.isReady) this.loadMask = Ext.create('Ext.LoadMask', { target: App.vp }); + }, + + checkAlphaCase: function(value) { + var checkValue = value; + <#if SettingsService.getString("autoUpperCase")?? && SettingsService.getString("autoUpperCase") == "1"> + if ((typeof checkValue) === 'string') + checkValue = checkValue.toUpperCase(); + + return checkValue; + }, + + setLoading: function(load) { + this.initLoadMask(); + if (this.loadMask) { + if (load) + this.loadMask.show(); + else + this.loadMask.hide(); + } + }, + + getInnerWidth: function() { + return window.innerWidth || 1000; + }, + getInnerHeight: function() { + return window.innerHeight || 600; + }, + + location: function(url) { + window.location.assign(url); + }, + logout: function() { + Ext.Ajax.request({ + url: App.url('/logout'), + method: 'POST', + callback: function(options, success, response) { + location.reload(); + window.location.assign(this.basePath); + } + }); + }, + loadNavMenu: function(navMenu) { + this.navMenu = navMenu || []; + }, + getNavMenu: function() { + return this.loopNavMenu(this.navMenu.items); + }, + loopNavMenu: function(nav){ + var me = this; + Ext.each(nav, function(n) { + n.text = me.localeRes(n.text); + n.title = me.localeRes(n.title); + if(n.children){ + me.loopNavMenu(n.children); + } + }); + return nav; + }, + loadLocale_EN: function(localeMap) { + this.localeMap_en = localeMap || {}; + }, + loadLocale_ZH: function(localeMap) { + this.localeMap_zh = localeMap || {}; + }, + loadLocale_CH: function(localeMap) { + this.localeMap_ch = localeMap || {}; + }, + loadUserAuths: function(auths) { + this.userAuths = auths || []; + }, + setCustTooltip: function(name, phone, email){ + var str = name; + str += phone?"
"+phone:""; + str += email?"
"+email:""; + return str; + }, + setClickableCust: function(extId, custId, viewText, callback) { + var me = this; + if(!App.isGranted(this.getPanelAuths('customerContainer'))) return viewText; + setTimeout(function () { + if (Ext.fly(extId)) { + Ext.EventManager.addListener( + extId, 'click', + function () { + App.loadModuleWin('customerWindow', me.localeRes('Customer'), { + params: { id: custId }, + callbackOnClose: function() { + if(callback) callback(); + } + }); + } + ); + } + }, 200); + + viewText = ""+viewText+""; + + return Ext.String.format('{1}', extId, viewText); + }, + setClickableMaterial: function(extId, params, viewText, callback) { + var me = this; + if(!App.isGranted(this.getPanelAuths('materialContainer'))) return viewText; + setTimeout(function () { + if (Ext.fly(extId)) { + Ext.EventManager.addListener( + extId, 'click', + function () { + App.loadModuleWin('materialItemWindow', me.localeRes('Material'), { + params: params, + callbackOnClose: function() { + if(callback) callback(); + } + }); + } + ); + } + }, 200); + + viewText = ""+viewText+""; + + return Ext.String.format('{1}', extId, viewText); + }, + setClickableCustOrder: function(extId, custId, viewText, callback) { + var me = this; + if(!App.isGranted(this.getPanelAuths('customerContainer'))) return viewText; + setTimeout(function () { + if (Ext.fly(extId)) { + Ext.EventManager.addListener( + extId, 'click', + function () { + App.loadModuleWin('customerOrderWindow', me.localeRes('Customer Order List'), { + params: { id: custId }, + callbackOnClose: function() { + if(callback) callback(); + } + }); + } + ); + } + }, 200); + + viewText = ""+viewText+""; + + return Ext.String.format('{1}', extId, viewText); + }, + setClickableOrder: function(extId, orderId, ignored, type, orderNo, callback) { + var viewText = orderNo; + if(ignored){ + //marked ignore + viewText = ""+orderNo+""; + }else if (type == OrderTypeCombo.TYPE_S){ + //S + viewText = "" + orderNo + ''; + }else{ + //SH + viewText = "" + orderNo + ''; + } + var me = this; + if(!App.isGranted(this.getPanelAuths('orderContainer'))) return viewText; + setTimeout(function () { + if (Ext.fly(extId)) { + Ext.EventManager.addListener( + extId, 'click', + function () { + App.loadModuleWin('orderWindow', App.localeRes('Order'), { + params: { id: orderId }, + callbackOnClose: function() { + if(callback) callback(); + } + }); + } + ); + } + }, 200); + + return Ext.String.format('{1}', extId, viewText); + }, + setClickableIcon: function(extId, id, icon,bank, callback) { + var me = this; + setTimeout(function () { + if (Ext.fly(extId)) { + Ext.EventManager.addListener( + extId, 'click', + function () { + App.loadModuleWin('materialBandIconWindow', App.localeRes('Icon'), { + params: { id: id }, + callbackOnClose: function() { + if(callback) callback(); + } + }); + } + ); + } + }, 200); + + return Ext.String.format('{1}   {2}', extId, icon, bank); + }, + + + setClickableWorkshop: function(extId, data, ignored, type, orderNo, callback) { + var viewText = orderNo; + if(ignored){ + //marked ignore + viewText = ""+orderNo+""; + }else if (type == OrderTypeCombo.TYPE_S){ + //S + viewText = "" + orderNo + ''; + }else{ + //SH + viewText = "" + orderNo + ''; + } + var me = this; + if(!App.isGranted(this.getPanelAuths('workshopContainer'))) return viewText; + setTimeout(function () { + if (Ext.fly(extId)) { + Ext.EventManager.addListener( + extId, 'click', + function () { + App.loadModuleWin('workshopWindow', App.localeRes('Workshop'), { + params: { data: data }, + callbackOnClose: function() { + if(callback) callback(); + } + }); + } + ); + } + }, 200); + + return Ext.String.format('{1}', extId, viewText); + }, + + getNewButton: function(extId, text, onClick) { + var me = this; + setTimeout(function () { + if (Ext.fly(extId)) { + Ext.EventManager.addListener( + extId, 'click', + function () { + onClick(); + } + ); + } + }, 200); + + return Ext.String.format('', extId, text); + }, + + isGranted: function(auths) { + if(!auths) return true; + var me = this; + + if(me.userAuths.includes("SUPERUSER")){ + return true; + } + var isGranted = false; + auths.forEach(function(value, index, array) { + if(me.userAuths.includes(value)){ + isGranted = true; + } + }); + return isGranted; + }, + getLocaleStr: function(code){ + code = code?code:this.localeCode; + if(code == 'zh_TW') + return '繁'; + if(code == 'zh_CN') + return '简'; + return 'Eng'; + }, + setLocale: function(code){ + this.localeCode = code; + }, + initUserSetting: function(settings){ + if(settings!= null){ + for(var i=0; i < settings.length;i++){ + var item = settings[i]; + var itemName = item["name"]; + var itemValue = item["value"]; + this.userSettings[itemName] = itemValue; + } + } + }, + setUserSetting: function(setting){ + this.userSettings[setting['name']]=setting['value']; + Ext.Ajax.request({ + url: App.url('/user/setting/save'), + params: { name: setting['name'], value: setting['value']}, + success: function(response, opts) {}, + failure: function(response, opts) { + App.showError('Action Fail : ' + response.status); + }, + }); + }, + getUserSetting: function(settingName){ + if(!this.userSettings) return ""; + if(!this.userSettings[settingName]) return ""; + return this.userSettings[settingName]; + }, + localeRes : function(key, ...args) { + + let str = this.localeMap_en[key] || key; + if(this.localeCode == 'zh_TW') + str = this.localeMap_zh[key] || key; + else if(this.localeCode == 'zh_CN') + str = this.localeMap_ch[key] || key; + return args.reduce((_str, val) => _str.replace(/%s|%v|%d|%f|%d/, val), str); + }, + delCoreFields: function(obj){ + // delete(obj.ownerId); + // delete(obj.deleted); + delete(obj.createdBy); + delete(obj.modifiedBy); + delete(obj.created); + delete(obj.modified); + delete(obj.password); + }, + loadModule: function(xtype, title, params, hash) { + if (xtype) { + var alias = 'widget.' + xtype, + className = Ext.ClassManager.getNameByAlias(alias), + contentPanel = Ext.getCmp('mainContainer'), + cmp; + + contentPanel.removeAll(true); + + if (className) { + cmp = Ext.create(className, params); + contentPanel.add(cmp); + + // contentPanel.setTitle(' '); + // contentPanel.getHeader().hide(); + + if (title) { + //contentPanel.setTitle(title); + //contentPanel.getHeader().show(); + document.title = title + ' - ' + App.name; + } else if (cmp.title) { + document.title = cmp.title + ' - ' + App.name; + } else { + document.title = App.name; + } + + if (hash) location.hash = hash; + + return cmp; + } else { + contentPanel.setTitle(''); + this.showError('Module not found!'); + } + } + }, + + loadModuleDash: function (xtype, title, params, hash) { + if(!App.isGranted(App.getPanelAuths(xtype))){ + if(App.isGranted(["CALENDAR_VIEW"])){ + xtype = 'calendarContainer'; + }else if(App.isGranted(["WORKSHOP_MAINTAIN"])){ + xtype = 'workshopContainer'; + }else { + xtype = 'report_OrderContainer'; + } + } + if (xtype) { + var alias = 'widget.' + xtype, + className = Ext.ClassManager.getNameByAlias(alias), + Main = Ext.getCmp('main-view-detail-wrap'), + contentPanel = Main.down('#contentPanel'), + cmp; + + contentPanel.removeAll(true); + Main.up("#mainView").down("#containerTitle").setHtml("
"+this.getTitle(xtype)+"
"); + + + if (className) { + cmp = Ext.create(className, params); + contentPanel.add(cmp); + + location.hash = xtype; + + return cmp; + } else { + this.showError('Module not found!'); + } + } + }, + + loadModuleWin: function(xtype, title, params, hash) { + if (xtype) { + var alias = 'widget.' + xtype, + className = Ext.ClassManager.getNameByAlias(alias), + cmp; + + if (className) { + cmp = Ext.create(className, params); + cmp.show(); + + if (title) { + cmp.setTitle(title); + } + +<#-- + if (title) { + cmp.setTitle(title); + document.title = title + ' - ' + App.name; + } else if (cmp.title) { + document.title = cmp.title + ' - ' + App.name; + } else { + document.title = App.name; + } +--> + + if (hash) location.hash = hash; + + return cmp; + } else { + this.showError('Module not found!'); + } + } + }, + + <#-- + allowed url: + /home#xxxPanel:{id} + /home#xxxPanel:xxxId=1&xxx=true&xxx='asd' + + /home#xxxPanel:{id}:{title} + /home#xxxPanel:xxxId=1&xxx=true&xxx='asd':{title} + --> + loadModuleByToken: function(token) { + var delimiter = ':', + parts = token.split(delimiter); + + if (parts.length > 1) { + var title = '', + params = {}; + + if (parts.length > 2) title = decodeURI(parts[parts.length-1]).replace(/\ /g, ''); + + if (this.isInt(parts[1])){ + <#-- /home#xxxPanel:{id} --> + if(parts[1] > 0) + params.id = parts[1]; + }else{ + <#-- /home#xxxPanel:xxxId=1&xxx=true&xxx='asd' --> + Ext.apply(params,Ext.JSON.decode('{"' + parts[1].replace(/\=/g, '":"').replace(/\&/g, '","') + '"}',true)); + } + + this.loadModule(parts[0], title, { params: params, + askCloseEvent: ( + params.id ? function() { + App.confirm('Close current tab?', 'Close current tab?', function(buttonId, text, option) { + if (buttonId != 'yes') return false; + window.close(); + }); + } : null + ) + }); + } else { + this.loadModule(parts[0]); + } + }, + addHistory: function(tokenStr){ + if(Ext.History.getToken() == tokenStr) + this.loadModuleByToken(tokenStr); + else + Ext.History.add(tokenStr); + }, + numberFormat: function(value, format){ + if(!value) value = 0; + if(!format) format=App.moneyNumberFormat; + return Ext.util.Format.numberRenderer(format)(value); + }, + integerNumberFormat: function(value, format){ + if(!value) value = 0; + if(!format) format=App.intNumberFormat; + return Ext.util.Format.numberRenderer(format)(value); + }, + isNumber: function(n){ + return Ext.isNumeric(n); + }, + isInt: function(n){ + return App.isNumber(n) && n % 1 === 0; + }, + isFloat: function(n){ + return App.isNumber(n) && n % 1 !== 0; + }, + sec2HHMMSS: function(sec){ + var sec_num = parseInt(sec, 10); + var hours = Math.floor(sec_num / 3600); + var minutes = Math.floor((sec_num - (hours * 3600)) / 60); + var seconds = sec_num - (hours * 3600) - (minutes * 60); + + if (hours < 10) {hours = "0"+hours;} + if (minutes < 10) {minutes = "0"+minutes;} + if (seconds < 10) {seconds = "0"+seconds;} + return hours+':'+minutes+':'+seconds; + }, + convertTimestampToTime: function(value){ + if(!value||value=='')return; + return Ext.Date.format(new Date(value), "H:i"); + }, + convertTimestampToDate: function(value){ + if(!value||value=='')return; + return Ext.Date.format(new Date(value), App.dateFormat); + }, + convertTimestampToDateTime: function(value){ + if(!value||value=='')return; + return Ext.Date.format(new Date(value), App.colDateTimeFormat); + }, + getTitle: function(xtype){ + var me = this; + if(xtype == 'calendarContainer') return me.localeRes('Calendar'); + if(xtype == 'orderContainer') return me.localeRes('Order'); + if(xtype == 'workshopContainer') return me.localeRes('Workshop'); + if(xtype == 'customerContainer') return me.localeRes('Customer'); + if(xtype == 'settingContainer') return me.localeRes('Setting'); + if(xtype == 'report_PaymentContainer') return me.localeRes('Payment Report'); + if(xtype == 'report_OrderContainer') return me.localeRes('Orders Report'); + if(xtype == 'report_OutstandingContainer') return me.localeRes('Outstanding Report'); + if(xtype == 'report_CustomerContainer') return me.localeRes('Customer Report'); + if(xtype == 'userBaseContainer') return me.localeRes('User Setting'); + if(xtype == 'materialContainer') return me.localeRes('Price List'); + if(xtype == 'invoiceTemplateContainer') return me.localeRes('Mail Settings'); + if(xtype == 'systemGroupContainer') return me.localeRes('System Settings'); + return xtype; + }, + getPanelAuths: function(xtype){ + return this.panelAuths.get(xtype) || ''; + }, + runTask: function(func, interval){ + if(func == null) return null; + return App.runner.start({ + run: func, + interval: interval + }); + }, + stopTask: function(task, andRemove){ + App.runner.stop(task, andRemove); + }, + stopAllTask: function(andRemove){ + App.runner.stopAll(andRemove); + }, + codePadding: function(num, width, sym){ + sym = sym || '0'; + num = num.toString(); + if(num.length >= width) return num; + return new Array((width - num.length)+1).join(sym) + num; + }, + setStatusStyle: function(value){ + <#-- 2/10/2018 + common : pending, confirmed, cancelled, completed, closed + e-order : draft + jobNo : released + DN : hold, passed + quotation : awarded + contract : inactive, active, expired + --> + if (!value) return ''; + if (value == 'draft') return 'Draft'; + if (value == 'New') return 'New'; + if (value == 'confirmed') return 'Confirmed'; + if (value == 'Completed') return 'Completed'; + if (value == 'closed') return 'Closed'; + if (value == 'Cancelled') return 'Cancelled'; + if (value == 'released') return 'Released'; + + if (value == 'hold') return 'Hold'; + if (value == 'passed') return 'Passed'; + + if (value == 'awarded') return 'Awarded'; + + if (value == 'active') return 'Active'; + if (value == 'expired') return 'Expired'; + + if (value == 'paid') return 'Paid'; + + return '' + Ext.util.Format.capitalize(value) + ''; + + }, + setPriorityStyle: function(value){ + if (value == 'Not Urgent') return 'Not Urgent'; + if (value == 'Urgent') return 'Urgent'; + return '' + Ext.util.Format.capitalize(value) + ''; + }, + + setPosNegStyle: function(value){ + if (value >= 0) return '

'+ Ext.util.Format.number(value, "0,000.##") + '

'; + if (value < 0 ) return '

' + Ext.util.Format.number(value, "0,000.##") + '

'; +}, + + newDate: function (day, month, year, hr, min, sec) { + var d = new Date(); + if (day) d.setDate(d.getDate() + day); + if (month) d.setMonth(d.getMonth() + month); + if (year) d.setFullYear(d.getFullYear() + year); + if (hr) d.setHours(d.getHours() + hr); + if (min) d.setMinutes(d.getMinutes() + min); + if (sec) d.setSeconds(d.getSeconds() + sec); + return d; + }, + printImage: function(source){ + if(!source || source=="" || source.length==0 ) return; + var str = "" + +"" + +"" + +"" + +"" + +"" +this.setImageTab(source) + "" + +""; + var Pagelink = "about:blank"; + var pwa = window.open(Pagelink, "_new"); + pwa.document.open(); + pwa.document.write(str); + pwa.document.close(); + }, + setImageTab:function(source){ + var sourceStr = ""; + for(var i = 0; i" + } + return sourceStr; + }, + +}); + + +<#-- Default header for CSRF --> +//Ext.Ajax.setDefaultHeaders({ 'X-CSRF-TOKEN': '${_csrf}' }); +Ext.util.Cookies.set('X-CSRF-TOKEN', '${_csrf}'); +Ext.Ajax.onBefore('beforerequest', function(conn, options){ + options.headers = options.headers || {}; + Ext.apply(options.headers,{ + 'X-CSRF-TOKEN': Ext.util.Cookies.get('X-CSRF-TOKEN') + }); +}); + +Ext.Ajax.onAfter('requestexception',function(conn, response, options){ + if (options.retry--) { + Ext.defer(function() { + Ext.Ajax.request(options) + }, 300 + Math.random() * 500 ); + } else { + App.log("requestexception: " + response.status); + if(response.responseText == 'DataIntegrityViolation'){ + App.showError('Data Integrity Violation'); + return; + } + + if(response.status == 403 && response.request.url != '<@spring.url "/logout" />'){ + alert('<@spring.message "SESSION.timeout.message" />'); + location.reload(); + return; + } + + <#-- Exception handling --> + if(response.status == 500){ + App.log("requestexception: 500"); + try{ + var result = Ext.decode(response.responseText); + if(result.msg){ + App.showException(result.msg,response.responseText); + }else{ + App.showException("Request Exception: 500",response.responseText); + } + }catch(e){ + App.showException("Request Exception: 500",response.responseText); + } + } + } +}); + +Ext.History.on('change', function(token) { + if (token) { + App.loadModuleDash(token, App.getTitle(token)); + } +}); + + +<#-- +Combo Renderer for Grid + +@param combo + required, the combo to search for display value +@param recordDisplayField + required, the display field in grid store record object to get display value from (useful when first rendering the grid since the combo store is not loaded yet) +@param comboValueField + optional (defaults to combo.valueField), the value field used in combo.findRecord(valueField) +@param comboDisplayField + optional (defaults to combo.displayField), the display field used to get the display value from the record object resulted from combo.findRecord(valueField) +--> +Ext.util.Format.comboRenderer = function(combo, recordDisplayField, comboValueField, comboDisplayField) { + return function(value, metaData, record, row, col, store, grid) { + var r = combo.findRecord(comboValueField || combo.valueField, value); + var v = r ? r.get(comboDisplayField || combo.displayField) : record.get(recordDisplayField) || combo.valueNotFoundText || value; + if (metaData) metaData.tdAttr = 'data-qtip="' + v + '"'; + return v; + }; +}; diff --git a/src/main/webapp/WEB-INF/sjs/controller/navMenu.js.ftl b/src/main/webapp/WEB-INF/sjs/controller/navMenu.js.ftl new file mode 100644 index 0000000..70d0520 --- /dev/null +++ b/src/main/webapp/WEB-INF/sjs/controller/navMenu.js.ftl @@ -0,0 +1,134 @@ +<#import "/spring.ftl" as spring> + +App.loadNavMenu({ + "items" : [ + <#if SecurityUtils.isGrantedAny("SUPERUSER","CUSTOMER_MAINTAIN")> + { + text: "Customer", + title: "Customer", + iconCls: "x-fa fa-user-circle-o", + viewType: "customerContainer", + leaf: true, + }, + + <#if SecurityUtils.isGrantedAny("SUPERUSER","CALENDAR_VIEW")> + { + text: "Calendar", + title:"Calendar", + iconCls: "x-fa fa-calendar", + viewType: "calendarContainer", + leaf: true, + }, + + <#if SecurityUtils.isGrantedAny("SUPERUSER","ORDER_MAINTAIN")> + { + text: "Order", + title: "Order", + // text: App.localeRes("Message"), + iconCls: "x- fa fa-file-text", + viewType: "orderContainer", + leaf: true, + }, + + <#if SecurityUtils.isGrantedAny("SUPERUSER","WORKSHOP_MAINTAIN")> + { + text: 'Workshop', + title: "Workshop", + iconCls: "x-fa fa-cut", + viewType: "workshopContainer", + leaf: true, + + }, + + <#if SecurityUtils.isGrantedAny("SUPERUSER","PRICE_LIST_VIEW","PRICE_LIST_MAINTAIN")> + { + text: 'Price List', + title: "Price List", + iconCls: "x-fa fa-sitemap", + viewType: 'materialContainer', + leaf: true, + }, + + { + text: "Report", + iconCls: "x-fa fa-sticky-note", + expanded: false, + selectable: false, + children: [ + <#if SecurityUtils.isGrantedAny("SUPERUSER","PAYMENT_REPORT")> + { + text: 'Payment Report', + title: 'Payment Report', + viewType: "report_PaymentContainer", + iconCls: "x-fa fa-file-excel-o", + leaf: true, + }, + + { + text: 'Orders Report', + title: 'Orders Report', + viewType: "report_OrderContainer", + iconCls: "x-fa fa-file-excel-o", + leaf: true + }, + { + text: 'Outstanding Report', + title: 'Outstanding Report', + viewType: "report_OutstandingContainer", + iconCls: "x-fa fa-file-excel-o", + leaf: true + }, + { + text: 'Customer Report', + title: 'Customer Report', + viewType: "report_CustomerContainer", + iconCls: "x-fa fa-file-excel-o", + leaf: true + }, + ] + }, + { + text: "Settings", + iconCls: "x-fa fa-cogs", + expanded: false, + selectable: false, + visible: App.isGranted(["USER_MAINTAIN"]), + children: [ + /* + { + text: 'System Settings', + title: "System Settings", + iconCls: "x-fa fa-cogs", + viewType: "settingContainer", + leaf: true + }, + */ + { + text: 'User Setting', + title: "User Setting", + iconCls: "fas fa-users", + viewType: "userBaseContainer", + visible: App.isGranted(App.getPanelAuths("userBaseContainer")), + leaf: true + }, + { + text: 'Mail Settings', + title: "Mail Settings", + iconCls: "fas fa-mail-bulk", + viewType: "invoiceTemplateContainer", + visible: App.isGranted(App.getPanelAuths("invoiceTemplateContainer")), + leaf: true + }, + <#if SecurityUtils.isGrantedOnly("2FI_ADMIN")> + { + text: 'System Settings', + title: "System Settings", + iconCls: "x-fa fa-cogs", + viewType: "systemGroupContainer", + leaf: true + } + + ] + } + ] +}); diff --git a/src/main/webapp/WEB-INF/sjs/controller/user-auths.js.ftl b/src/main/webapp/WEB-INF/sjs/controller/user-auths.js.ftl new file mode 100644 index 0000000..76b323a --- /dev/null +++ b/src/main/webapp/WEB-INF/sjs/controller/user-auths.js.ftl @@ -0,0 +1,6 @@ +App.loadUserAuths([ +<#import "/spring.ftl" as spring> +<#list SecurityUtils.getUser().getAuthorities() as authority> +"${authority}", + +]); \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/sjs/store/Common.js.ftl b/src/main/webapp/WEB-INF/sjs/store/Common.js.ftl new file mode 100644 index 0000000..86a96ec --- /dev/null +++ b/src/main/webapp/WEB-INF/sjs/store/Common.js.ftl @@ -0,0 +1,86 @@ +<#import "/spring.ftl" as spring> + +<#-- Common Store for Available Locales --> +Ext.define('App.store.LocaleStore', { + extend: 'Ext.data.Store', + + constructor: function(cfg) { + var me = this; + cfg = cfg || {}; + me.callParent([Ext.apply({ + data: [ +<#if availableLocales??> +<#list availableLocales as availableLocale> + { + text: '<@spring.message "COMMON.locale.${availableLocale}" />', + value: '${availableLocale}' + }, + + + ], + fields: [ + { + name: 'text' + }, + { + name: 'value' + } + ] + }, cfg)]); + } +}); + + +<#-- Common Store for Year Combo --> +Ext.define('App.store.common.YearStore', { + extend: 'Ext.data.Store', + + constructor: function(cfg) { + var me = this; + cfg = cfg || {}; + me.callParent([Ext.apply({ + data: [ +<#list 2008..2037 as i> + { + value: ${i?c} + }, + + { + value: null + } + ], + fields: [ + { + name: 'value' + } + ] + }, cfg)]); + } +}); + +<#-- Common Store for Month Combo --> +Ext.define('App.store.common.MonthStore', { + extend: 'Ext.data.Store', + + constructor: function(cfg) { + var me = this; + cfg = cfg || {}; + me.callParent([Ext.apply({ + data: [ +<#list 1..12 as i> + { + value: ${i?c} + }, + + { + value: null + } + ], + fields: [ + { + name: 'value' + } + ] + }, cfg)]); + } +}); \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/sjs/view/CustomFormWindow.js.ftl b/src/main/webapp/WEB-INF/sjs/view/CustomFormWindow.js.ftl new file mode 100644 index 0000000..0f782c9 --- /dev/null +++ b/src/main/webapp/WEB-INF/sjs/view/CustomFormWindow.js.ftl @@ -0,0 +1,63 @@ +<#import "/spring.ftl" as spring> +Ext.define('App.view.CustomFormWindow',{ + extend: 'Ext.window.Window', + alias: 'widget.customFormWindow', + + scrollable: true, + constrainHeader: true, + modal: true, + resizable: true, + title: null, + layout: 'hbox', + + config:{ + saveBtnText: '<@spring.message "COMMON.save" />', + formItems: [], + + callback: function(values,form){}, + }, + + onSaveBtnClick: function(button){ + var me = this, + f = me.down('form'); + if(f.isValid()){ + if(me.callback) me.callback(f.getValues(),f); + me.close(); + } + }, + + initComponent: function(){ + var me = this; + Ext.apply(me,{ + items:[{ + xtype: 'form', + bodyPadding: 10, + buttonAlign: 'left', + defaults: { + selectOnFocus: true, + labelWidth: 150, + width: 400 + }, + items: me.formItems, + buttons:[ + { + xtype: 'button', + text: me.saveBtnText, + iconCls: 'silk-disk', + formBind: true, + handler: me.onSaveBtnClick, + scope: me + }, + { + xtype: 'button', + text: '<@spring.message "COMMON.close" />', + handler: function(button, event) { + me.close(); + } + }, + ] + }] + }); + me.callParent(); + } +}); diff --git a/src/main/webapp/WEB-INF/sjs/view/OldViewport.js.ftl b/src/main/webapp/WEB-INF/sjs/view/OldViewport.js.ftl new file mode 100644 index 0000000..c418551 --- /dev/null +++ b/src/main/webapp/WEB-INF/sjs/view/OldViewport.js.ftl @@ -0,0 +1,203 @@ +<#import "/spring.ftl" as spring> + +<#-- ### Content Panel --> +Ext.define('App.view.ContentPanel', { + extend: 'Ext.panel.Panel', + xtype: 'contentPanel', + + id: 'contentPanel', + scrollable: true, + height: '100%', + width: '100%', + <#-- title: ' ' --> +}); + +<#-- ### Header --> +Ext.define('App.view.Header', { + extend: 'Ext.toolbar.Toolbar', + xtype: 'appheader', + + <#-- + cls: 'header-toolbar', + --> + style:{ + background: '#8bc34a !important', + padding: '0 0 0 6px !important', + // background-image: 'url('../images/user/header-bg.png') !important' + <#-- 'toolbar-border-style' : '0 4px 8px 0 rgba(0,0,0,0.2)' --> + <#-- 'border-bottom': '1px solid #191919 !important', --> + <#-- '-webkit-box-shadow': 'inset 0 0 1px rgba(255, 255, 255, 0.1), 0 0 3px rgba(0, 0, 0, 0.8) !important', --> + }, + onChangeLocale: function(locale) { + Ext.Ajax.request({ + method: 'GET', + url: '<@spring.url "/locale" />', + params: { locale: locale }, + + success: function(response, opts) { + var obj = Ext.decode(response.responseText); + location.reload(); + }, + + failure: function(response, opts) { + console.log('server-side failure with status code ' + response.status); + } + }); + }, + + initComponent: function() { + var me = this; + const items = []; + + me.items = [ + { + xtype: 'tbitem', + html: '">" width="75" height="24" />', + width: 75, + height: 24 + }, + { + xtype: 'toolbar', + overflowHandler: 'menu', + items: items, + flex: 1, + style: me.style, + }, + ]; + Ext.apply(items, [ + { + xtype: 'button', + text: 'PCS', + //tooltip: '', + iconCls: 'silk-monitor', + width: 85, + handler: function(button, e) { + App.location('<@spring.url "/pcs" />'); + } + }, + { + xtype: 'button', + text: 'Edit ', + iconCls: 'silk-monitor', + width: 85, + menu: [ + { + text: 'Vendor', + iconCls: 'icon-users', + handler: function(button, e) { + App.loadModule('vendorPanel'); + } + }, + '-', + { + text: 'Equipment', + iconCls: 'icon-users', + handler: function(button, e) { + App.loadModule('equipmentBasePanel'); + } + }, + + ] + }, + { + xtype: 'button', + text: 'New ViewPort', + //tooltip: '', + iconCls: 'silk-monitor', + width: 85, + handler: function(button, e) { + window.open('<@spring.url "/home/new-viewport" />'); + } + }, + + '->', + { + xtype: 'combo', + store: Ext.create('App.store.LocaleStore', {}), + valueField: 'value', + value: '${rc.getLocale()}', + editable: false, + forceSelection: true, + width: 68+15, + hideTrigger: true, + displayTpl: '🌐{text}', + listeners: { + change: function(combo, newValue, oldValue, eOpts) { + me.onChangeLocale(newValue); + } + } + }, + <#-- + { + xtype: 'tbtext', + text: '${SecurityUtils.getUser().getFullname()}', + cls: 'x-panel-header-text-container-default header-text' + }, + { + xtype: 'tbspacer' + }, + --> + { + xtype: 'button', + text: '${SecurityUtils.getUser().getFullname()}', + //tooltip: '', + iconCls: 'icon-page-key', + //iconCls: 'fa fa-key', + //cls: 'password-btn', + handler: function() { + App.loadModuleWin('userChangePasswordWindow'); + } + }, + { + xtype: 'button', + text: '<@spring.message "COMMON.logout" />', + //tooltip: '', + iconCls: 'icon-generate', + //cls: 'logout-btn', + //iconCls: 'fa fa-sign-out', + handler: function() { + App.logout(); + } + } + ]); + me.callParent(arguments); + } +}); + +<#-- ### Viewport --> +Ext.define('App.view.Viewport', { + extend: 'Ext.container.Viewport', + + layout: { + type: 'border' + }, + + initComponent: function() { + var me = this; + + Ext.apply(me, { + items: [ +<#if !SecurityUtils.isGranted("KANBAN_MODE")> + { + xtype: 'appheader', + region: 'north', + height: 48 + }, + + { + xtype: 'contentPanel', + region: 'center' + } + ], + listeners: { + render: function(viewport, eOpts) { +// App.loadModule('dashboardPanel'); +// App.loadModule('kanbanJobStatusView'); + } + } + }); + + me.callParent(arguments); + } + +}); diff --git a/src/main/webapp/WEB-INF/sjs/view/UserChangePasswordWindow.js.ftl b/src/main/webapp/WEB-INF/sjs/view/UserChangePasswordWindow.js.ftl new file mode 100644 index 0000000..87c121d --- /dev/null +++ b/src/main/webapp/WEB-INF/sjs/view/UserChangePasswordWindow.js.ftl @@ -0,0 +1,162 @@ +<#import "/spring.ftl" as spring> + +<#-- User Password Change Window --> +Ext.define('App.view.UserChangePasswordWindow', { + extend: 'Ext.window.Window', + alias: 'widget.userChangePasswordWindow', + + autoScroll: true, + constrainHeader: true, + modal: true, + title: 'Change password', + + onSaveBtnClick: function(button, event) { + var me = this, + f = me.down('form').getForm(); + if (f.isValid()) { + f.submit({ + waitMsg: 'Saving...', + success: function(form, action) { + App.showMsg('Password changed'); + me.close(); + }, + failure: function(form, action) { + App.log(action); + App.showError(App.localeRes('Failed to change password, please make sure you have entered your current password correctly!')); + } + }); + } + }, + + initComponent: function() { + var me = this; + + Ext.applyIf(me, { + items: [ + { + xtype: 'form', + bodyPadding: 10, + buttonAlign: 'left', + + url: '<@spring.url "/user/change-password" />', + + defaults: { + selectOnFocus: true, + labelWidth: 150, + width: 350 + }, + + items: [ + { + xtype: 'textfield', + name: 'password', + fieldLabel: 'Current Password', + inputType: 'password', + allowBlank: false, + minLength: 5, + maxLength: 20 + }, + { + xtype: 'textfield', + name: 'newPassword', + fieldLabel: 'New Password', + inputType: 'password', + allowBlank: false, + validator: function(value) { + <#-- + return new RegExp("^(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[!\"#$%&'()*+,-./:;<=>?@\\[\\\\\\]^_`{|}~]).{8,20}").test(value)? true: + 'Please Input Strong Password.
Minimum 8 Characters
Capital Letters
Lower-Case Letters
Symbols
Numbers'; + --> + <#-- front and back end both check--> + const min = ${SettingsService.getInt("SYS.password.rule.length.min")}; + const max = ${SettingsService.getInt("SYS.password.rule.length.max")}; + const number = ${SettingsService.getString("SYS.password.rule.number")!}; + const upperEng = ${SettingsService.getString("SYS.password.rule.upper.eng")!}; + const lowerEng = ${SettingsService.getString("SYS.password.rule.lower.eng")!}; + const specialChar = ${SettingsService.getString("SYS.password.rule.special")!}; + + let regExp = "^"; + if(number) regExp += '(?=.*[0-9])'; + if(upperEng) regExp += '(?=.*[A-Z])'; + if(lowerEng) regExp += '(?=.*[a-z])'; + if(specialChar) regExp += "(?=.*[!\"#$%&'()*+,-./:;<=>?@\\[\\\\\\]^_`{|}~])"; + regExp += '.{'+min+','+max+'}'; + + if(new RegExp(regExp).test(value)){ + return true; + }else{ + let wrongMsg = 'Please Following Password Rule.
'; + wrongMsg += 'Minimum ' + min + ' Characters
'; + wrongMsg += 'Maximum ' + max + ' Characters
'; + if(number) wrongMsg += 'Numbers
'; + if(lowerEng) wrongMsg += 'Lower-Case Letters
'; + if(upperEng) wrongMsg += 'Capital Letters
'; + if(specialChar) wrongMsg += 'Symbols
'; + return wrongMsg; + } + } + }, + { + xtype: 'textfield', + fieldLabel: 'Confirm New Password', + inputType: 'password', + submitValue: false, + maxLength: 20, + validator: function(value) { + var p = me.down('field[name=newPassword]').getValue(); + return (p == value) ? true : 'New passwords do not match!'; + } + } + ], + + buttons: [ + { + xtype: 'button', + itemId: 'saveBtn', + text: App.localeRes('Save & Close'), + ui: "blue", + iconCls: 'silk-disk', + formBind: true, + handler: me.onSaveBtnClick, + scope: me + }, + { + xtype: 'component', + flex: 1 + }, + { + xtype: 'button', + text: App.localeRes('Cancel'), + handler: function(button, event) { + me.close(); + } + } + ] + } + ], + + listeners: { + show: function(window, opts) { + + }, + close: function(window, opts) { + if (me.callbackOnClose) me.callbackOnClose(); + }, + afterrender: function(window, options) { + this.keyNav = new Ext.util.KeyMap({ + target: window.el, + binding: [{ + key: 13, + fn: function(keyCode,event){ + me.down('#saveBtn').click(); + } + }] + }); + } + } + }); + + me.callParent(arguments); + } + +}); diff --git a/src/main/webapp/WEB-INF/views-excel.xml b/src/main/webapp/WEB-INF/views-excel.xml new file mode 100644 index 0000000..79fe1a3 --- /dev/null +++ b/src/main/webapp/WEB-INF/views-excel.xml @@ -0,0 +1,43 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/views-system.xml b/src/main/webapp/WEB-INF/views-system.xml new file mode 100644 index 0000000..ddea58c --- /dev/null +++ b/src/main/webapp/WEB-INF/views-system.xml @@ -0,0 +1,9 @@ + + + + + + \ No newline at end of file diff --git a/src/main/webapp/WEB-INF/web.xml b/src/main/webapp/WEB-INF/web.xml new file mode 100644 index 0000000..a20cdb3 --- /dev/null +++ b/src/main/webapp/WEB-INF/web.xml @@ -0,0 +1,110 @@ + + + + + contextConfigLocation + /WEB-INF/application-context.xml + + + + org.springframework.web.util.IntrospectorCleanupListener + + + + org.springframework.web.context.ContextLoaderListener + + + + org.springframework.security.web.session.HttpSessionEventPublisher + + + + ajaxSessionExpirationFilter + com.ffii.core.web.filter.AjaxSessionExpirationFilter + + + + ajaxSessionExpirationFilter + /* + + + + springSecurityFilterChain + org.springframework.web.filter.DelegatingFilterProxy + + + + springSecurityFilterChain + /* + REQUEST + FORWARD + INCLUDE + ERROR + + + + characterEncoding + org.springframework.web.filter.CharacterEncodingFilter + + encoding + utf-8 + + + + + characterEncoding + /* + + + + mvc-dispatcher + org.springframework.web.servlet.DispatcherServlet + 1 + + + + mvc-dispatcher + /* + + + + index.html + + + + 30 + + + + + *.jsp + false + UTF-8 + false + + + + + DB Connection + jdbc/tbmsdb + javax.sql.DataSource + Container + Shareable + + + + + diff --git a/src/main/webapp/resources/css/DateRangePicker.css b/src/main/webapp/resources/css/DateRangePicker.css new file mode 100644 index 0000000..192b4bb --- /dev/null +++ b/src/main/webapp/resources/css/DateRangePicker.css @@ -0,0 +1,7 @@ +.drp-icon-yes { + background: url("icons/tick.png") no-repeat scroll 0 0 transparent !important; +} + +.drp-icon-calendar { + background: url("../images/icons-silk/calendar.png") no-repeat scroll 0 0 transparent !important; +} diff --git a/src/main/webapp/resources/css/adminDashboardCSS/Admin-all.css b/src/main/webapp/resources/css/adminDashboardCSS/Admin-all.css new file mode 100644 index 0000000..231f15c --- /dev/null +++ b/src/main/webapp/resources/css/adminDashboardCSS/Admin-all.css @@ -0,0 +1,3 @@ +@import 'Admin-all_1.css'; +@import 'Admin-all_2.css'; +@import 'Admin-all_3.css'; diff --git a/src/main/webapp/resources/css/adminDashboardCSS/Admin-all_1.css b/src/main/webapp/resources/css/adminDashboardCSS/Admin-all_1.css new file mode 100644 index 0000000..71328bf --- /dev/null +++ b/src/main/webapp/resources/css/adminDashboardCSS/Admin-all_1.css @@ -0,0 +1,13237 @@ +:root { + --side-bar-height: 64px; +} + +.x-size-monitored { + position: relative; +} +.x-size-monitors { + position: absolute; + left: 0; + top: 0; + width: 100%; + height: 100%; + visibility: hidden; + overflow: hidden; +} +.x-size-monitors > * { + width: 100%; + height: 100%; + overflow: hidden; +} +.x-size-monitors.scroll > *.shrink::after { + content: ""; + display: block; + width: 200%; + height: 200%; + min-width: 1px; + min-height: 1px; +} +.x-size-monitors.scroll > *.expand::after { + content: ""; + display: block; + width: 100000px; + height: 100000px; +} +.x-size-monitors.overflowchanged > *.shrink > * { + width: 100%; + height: 100%; +} +.x-size-monitors.overflowchanged > *.expand > * { + width: 200%; + height: 200%; +} +.x-size-change-detector { + visibility: hidden; + position: absolute; + left: 0; + top: 0; + z-index: -1; + width: 100%; + height: 100%; + overflow: hidden; +} +.x-size-change-detector > * { + visibility: hidden; +} +.x-size-change-detector-shrink > * { + width: 200%; + height: 200%; +} +.x-size-change-detector-expand > * { + width: 100000px; + height: 100000px; +} +@-webkit-keyframes x-paint-monitor-helper { + from { + zoom: 1; + } + to { + zoom: 1; + } +} +@keyframes x-paint-monitor-helper { + from { + zoom: 1; + } + to { + zoom: 1; + } +} +.x-paint-monitored { + position: relative; +} +.x-paint-monitor { + width: 0 !important; + height: 0 !important; + visibility: hidden; +} +.x-paint-monitor.cssanimation { + -webkit-animation-duration: 0.0001ms; + -webkit-animation-name: x-paint-monitor-helper; + animation-duration: 0.0001ms; + animation-name: x-paint-monitor-helper; +} +.x-paint-monitor.overflowchange { + overflow: hidden; +} +.x-paint-monitor.overflowchange::after { + content: ""; + display: block; + width: 1px !important; + height: 1px !important; +} +.x-unselectable { + user-select: none; + -o-user-select: none; + -ms-user-select: none; + -moz-user-select: -moz-none; + -webkit-user-select: none; + -webkit-tap-highlight-color: transparent; + -webkit-user-drag: none; + cursor: default; +} +.x-hidden-clip { + position: absolute !important; + clip: rect(0, 0, 0, 0); +} +.x-hidden-display { + display: none !important; +} +.x-hidden-offsets, +.x-hidden { + display: block !important; + visibility: hidden !important; + position: absolute !important; + top: -10000px !important; +} +.x-hidden-opacity { + opacity: 0 !important; + pointer-events: none; +} +.x-hidden-visibility { + visibility: hidden !important; +} +.x-pressed .x-ripple-transition, +.x-pressing .x-ripple-transition { + transition: background-color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1), + color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1); +} +.x-pressed .x-ripple-transition .x-icon-el, +.x-pressed .x-ripple-transition .x-arrow-el, +.x-pressing .x-ripple-transition .x-icon-el, +.x-pressing .x-ripple-transition .x-arrow-el { + transition: background-color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1), + color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1); +} +.x-rippling { + position: relative; +} +.x-rippling.x-component-confirm .x-ripple { + background-color: green; +} +.x-rippling.x-component-decline .x-ripple { + background-color: red; +} +.x-rippling.x-rippling-unbound { + overflow: visible !important; +} +.x-rippling.x-rippling-unbound .x-ripple-container { + overflow: visible; + position: absolute; +} +.x-safari .x-rippling:not(.x-rippling-unbound) .x-ripple-container { + -webkit-transform: rotate(0); + -moz-transform: rotate(0); + -ms-transform: rotate(0); + -o-transform: rotate(0); + transform: rotate(0); +} +.x-ripple-container { + overflow: hidden; + position: absolute; + top: 0; + bottom: 0; + left: 0; + right: 0; + pointer-events: none; +} +.x-ripple-wrapper { + z-index: 1000; +} +.x-button-fab .x-ripple-container, +.x-button-round .x-ripple-container { + border-radius: 10000px; +} +.x-splitButton-fab .x-ripple-container, +.x-splitButton-round .x-ripple-container { + border-radius: 10000px; +} +.x-ripple { + position: absolute; + border-radius: 50%; + background-color: white; + -webkit-transform: scale(1, 1); + -moz-transform: scale(1, 1); + -ms-transform: scale(1, 1); + -o-transform: scale(1, 1); + transform: scale(1, 1); + opacity: 0.4; + pointer-events: none; +} +.x-rippling.x-rippling-unbound .x-ripple { + -webkit-animation: x-ripple-unbound-animation 0.3s ease-out forwards; + animation: x-ripple-unbound-animation 0.3s ease-out forwards; +} +.x-rippling:not(.x-rippling-unbound) .x-ripple { + -webkit-animation: x-ripple-animation 0.35s ease-out forwards; + animation: x-ripple-animation 0.35s ease-out forwards; +} +@-webkit-keyframes x-ripple-animation { + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + 75% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0.2; + } + 100% { + -webkit-transform: scale(2.35, 2.35); + -moz-transform: scale(2.35, 2.35); + -ms-transform: scale(2.35, 2.35); + -o-transform: scale(2.35, 2.35); + transform: scale(2.35, 2.35); + opacity: 0; + } +} +@keyframes x-ripple-animation { + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + 75% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0.2; + } + 100% { + -webkit-transform: scale(2.35, 2.35); + -moz-transform: scale(2.35, 2.35); + -ms-transform: scale(2.35, 2.35); + -o-transform: scale(2.35, 2.35); + transform: scale(2.35, 2.35); + opacity: 0; + } +} +@-webkit-keyframes x-ripple-unbound-animation { + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + 75% { + -webkit-transform: scale(1.75, 1.75); + -moz-transform: scale(1.75, 1.75); + -ms-transform: scale(1.75, 1.75); + -o-transform: scale(1.75, 1.75); + transform: scale(1.75, 1.75); + opacity: 0.2; + } + 100% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0; + } +} +@keyframes x-ripple-unbound-animation { + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + 75% { + -webkit-transform: scale(1.75, 1.75); + -moz-transform: scale(1.75, 1.75); + -ms-transform: scale(1.75, 1.75); + -o-transform: scale(1.75, 1.75); + transform: scale(1.75, 1.75); + opacity: 0.2; + } + 100% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0; + } +} +.x-progress { + overflow: hidden; + position: relative; +} +.x-progress-bar { + height: 100%; + width: 0; +} +.x-progress-text { + overflow: hidden; +} +.x-progress-bar { + overflow: hidden; + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-scroller { + -webkit-overflow-scrolling: touch; + overflow-anchor: none; +} +.x-scroller-spacer { + position: absolute; + top: 0; + overflow: hidden; + height: 1px; + width: 1px; + font-size: 0; + line-height: 0; + pointer-events: none; +} +.x-scroller-snappable { + -ms-scroll-snap-type: mandatory; + -webkit-scroll-snap-type: mandatory; + scroll-snap-type: mandatory; +} +.x-no-scrollbars { + -ms-overflow-style: none; +} +.x-no-scrollbars::-webkit-scrollbar { + width: 0; +} +.x-touch-action-pan-y { + overflow-x: hidden !important; +} +.x-touch-action-pan-x { + overflow-y: hidden !important; +} +.x-treelist { + background-color: #fff; + background-position: 16px 0%; + overflow: hidden; + padding: 0 0 0 0; +} +.x-treelist-container, +.x-treelist-root-container { + width: 100%; +} +.x-treelist-toolstrip { + display: none; +} +.x-treelist-micro > .x-treelist-toolstrip { + display: inline-block; +} +.x-treelist-micro > .x-treelist-root-container { + display: none; +} +.x-treelist-item, +.x-treelist-container, +.x-treelist-root-container { + position: relative; + overflow: hidden; + list-style: none; + padding: 0; + margin: 0; +} +.x-treelist-item-tool, +.x-treelist-row, +.x-treelist-item-wrap { + position: relative; +} +.x-treelist-item-icon, +.x-treelist-item-expander { + display: none; + position: absolute; + top: -6; +} +.x-treelist-item-expander { + right: 0; + cursor: pointer; +} +.x-treelist-expander-only + .x-treelist-item-expandable + > * + > .x-treelist-item-wrap + > * { + cursor: pointer; +} +.x-treelist-item-text { + cursor: pointer; + white-space: nowrap; + overflow: hidden; +} +.x-treelist-item-collapsed > .x-treelist-container { + display: none; +} +.x-treelist-item-expandable > * > * > .x-treelist-item-expander, +.x-treelist-item-icon { + display: block; +} +.x-treelist-item-floated > * > * > .x-treelist-item-expander, +.x-treelist-item-floated > * > * > .x-treelist-item-icon { + display: none; +} +.x-treelist-expander-first .x-treelist-item-expander { + left: 0; + right: auto; +} +.x-treelist-toolstrip { + background-color: #f8f8f8; +} +.x-treelist-item-selected > .x-treelist-row { + background-color: #ffefbb; +} +.x-treelist-item-selected > .x-treelist-row-over { + background-color: #ffefbb; +} +.x-treelist-item-tool { + padding-left: 6px; + padding-right: 10px; +} +.x-treelist-item-icon:before, +.x-treelist-item-tool:before, +.x-treelist-item-expander { + line-height: 32px; +} +.x-treelist-item-icon, +.x-treelist-item-tool, +.x-treelist-item-expander { + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; +} +.x-treelist-item-loading .x-treelist-item-icon { + background-image: url(images/tree/loading.gif); + color: transparent; +} +.x-treelist-item-icon, +.x-treelist-item-tool { + color: #5aaed4; + font-size: 16px; + width: 16px; +} +.x-treelist-item-tool { + width: 32px; +} +.x-treelist-item-expander { + color: #5aaed4; + font-size: 16px; + width: 18px; +} +.x-treelist-item-expander:after { + content: "\f0da"; + font: 16px/32px FontAwesome; +} +.x-treelist-item-expanded > * > * > .x-treelist-item-expander:after { + content: "\f0d7"; + font: 16px/32px FontAwesome; +} +.x-treelist-item-text { + color: #404040; + margin-left: 22px; + margin-right: 18px; + font-size: 14px; + line-height: 32px; + text-overflow: ellipsis; +} +.x-treelist-row { + padding-left: 6px; + padding-right: 10px; + height: 54px; +} +.x-treelist-item-floated .x-treelist-container { + width: auto; +} +.x-treelist-item-floated > .x-treelist-row { + background-color: #f8f8f8; +} +.x-treelist-item-floated > .x-treelist-container { + margin-left: -6px; +} +.x-big .x-treelist-item-floated > .x-treelist-container { + margin-left: -6px; +} +.x-treelist-item-floated > * > * > .x-treelist-item-text { + margin-left: 0; +} +.x-treelist-item-floated > * .x-treelist-row { + cursor: pointer; + padding-left: 0; +} +.x-treelist-item-floated .x-treelist-row:before { + width: 0; +} +.x-treelist-item-floated > .x-treelist-row-over { + background-color: #f8f8f8; +} +.x-treelist-item-floated > .x-treelist-row-over > * > .x-treelist-item-text { + color: #3e68d5; +} +.x-treelist-item-expanded > .x-treelist-item-expander:after { + content: "\f0d7"; + font: 16px/1 FontAwesome; +} +.x-treelist-item-collapsed > * > .x-treelist-item-expander:after { + content: "\f0da"; + font: 16px/1 FontAwesome; +} +.x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-icon { + color: #5aaed4; + transition: color 0.5s; +} +.x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-text { + color: #404040; + transition: color 0.5s; +} +.x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-expander { + color: #5aaed4; + transition: color 0.5s; +} +.x-treelist-row-over { + background-color: #e6f1f6; +} +.x-treelist-row-over > * > .x-treelist-item-icon { + color: #5aaed4; + transition: color 0.5s; +} +.x-treelist-row-over > * > .x-treelist-item-text { + color: #3f6ad8; + transition: color 0.5s; +} +.x-treelist-row-over > * > .x-treelist-item-expander { + color: #5aaed4; + transition: color 0.5s; +} +.x-treelist-expander-first .x-treelist-item-icon { + left: 18px; +} +.x-treelist-expander-first .x-treelist-item-text { + margin-left: 40px; + margin-right: 0; +} +.x-treelist-expander-first + .x-treelist-item-hide-icon + > * + > * + > .x-treelist-item-text { + margin-left: 21px; +} +.x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 3px; +} +.x-treelist-nav { + background-color: #ffffff; + background-position: 10px 0%; + padding: 0 0 0 0; +} +.x-treelist-nav .x-treelist-toolstrip { + background-color: #ffffff; +} +.x-treelist-nav .x-treelist-item-selected.x-treelist-item-tool { + background-color: #e0f3ff; + color: #495057; +} +.x-treelist-nav .x-treelist-item-selected.x-treelist-item-tool:after { + height: var(--side-bar-height); + position: absolute; + top: 0; + left: 0; + content: " "; + width: 5px; + background-color: #5aaed4; +} +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row { + background-color: #e0f3ff; +} +.x-treelist-nav .x-treelist-item-tool { + padding-left: 10px; + padding-right: 10px; +} +.x-treelist-nav .x-treelist-item-tool-floated:after { + height: var(--side-bar-height); + position: absolute; + top: 0; + left: 0; + content: " "; + width: 5px; + background-color: #5aaed4; +} +.x-treelist-nav .x-treelist-item-icon:before, +.x-treelist-nav .x-treelist-item-tool:before, +.x-treelist-nav .x-treelist-item-expander { +} +.x-treelist-nav .x-treelist-item-icon, +.x-treelist-nav .x-treelist-item-tool, +.x-treelist-nav .x-treelist-item-expander { + line-height: var(--side-bar-height); + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; +} +.x-treelist-nav .x-treelist-item-loading .x-treelist-item-icon { + background-image: url(images/tree/loading.gif); + color: transparent; +} +.x-treelist-nav .x-treelist-item-icon, +/* icon color */ +.x-treelist-nav .x-treelist-item-tool { + color: #f89d03; + font-size: 25px; + width: 40px; +} +.x-treelist-nav .x-treelist-item-tool { + width: 64px; + height: var(--side-bar-height); +} +.x-treelist-nav .x-treelist-item-expander { + color: #f89d03; + font-size: 16px; + width: 24px; +} +/* nav text color */ +.x-treelist-nav .x-treelist-item-text { + color: #404040; + margin-left: 40px; + margin-right: 24px; + font-size: 16px; + line-height: var(--side-bar-height); +} +.x-treelist-nav .x-treelist-row { + padding-left: 10px; + padding-right: 10px; + height: var(--side-bar-height); +} +.x-treelist-nav .x-treelist-row-over:before, +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before { + content: " "; + position: absolute; + display: block; + left: 0; + top: 0; + width: 5px; + height: 100%; +} +.x-treelist-nav .x-treelist-row-over:before { + background-color: transparent; +} +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row-over:before { + background-color: #57c6f8; +} +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before { + background-color: #5aaed4; +} +.x-treelist-nav .x-treelist-item-floated .x-treelist-container { + width: auto; +} +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row { + background-color: #ffffff; +} +.x-treelist-nav .x-treelist-item-floated > .x-treelist-container { + margin-left: -10px; +} +.x-big .x-treelist-nav .x-treelist-item-floated > .x-treelist-container { + margin-left: -10px; +} +.x-treelist-nav .x-treelist-item-floated > * > * > .x-treelist-item-text { + margin-left: 0; +} +.x-treelist-nav .x-treelist-item-floated > * .x-treelist-row { + cursor: pointer; + padding-left: 0; +} +.x-treelist-nav .x-treelist-item-floated .x-treelist-row:before { + width: 0; +} +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row-over { + background-color: #e0f3ff; +} +.x-treelist-nav + .x-treelist-item-floated + > .x-treelist-row-over + > * + > .x-treelist-item-text { + color: #3f6ad8; +} +.x-treelist-nav .x-treelist-item-expanded { + background-color: #ffffff; +} +.x-treelist-nav + .x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-icon { + color: #fff; +} +.x-treelist-nav + .x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-text { + color: #d6d9dc; +} +.x-treelist-nav + .x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-expander { + color: #fff; +} +.x-treelist-nav .x-treelist-row-over { + background-color: #e0f3ff; +} +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-icon { + color: #3f6ad8; +} +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-text { + color: #3f6ad8; +} +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-expander { + color: #3f6ad8; +} +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-icon { + left: 24px; +} +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-text { + margin-left: 74px; + margin-right: 0; +} +.x-treelist-nav + .x-treelist-expander-first + .x-treelist-item-hide-icon + > * + > * + > .x-treelist-item-text { + margin-left: 27px; +} +.x-treelist-nav .x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 3px; +} +.x-body { + margin: 0; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} +@-ms-viewport { + width: device-width; +} +img { + border: 0; +} +.x-border-box, +.x-border-box * { + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +.x-ltr { + direction: ltr; +} +.x-clear { + overflow: hidden; + clear: both; + font-size: 0; + line-height: 0; + display: table; +} +.x-layer { + position: absolute !important; + top: 0; + left: 0; + overflow: hidden; +} +.x-fixed-layer { + position: fixed !important; + overflow: hidden; +} +.x-shim { + position: absolute; + left: 0; + top: 0; + overflow: hidden; + opacity: 0; +} +.x-hidden-clip { + position: absolute !important; + clip: rect(0, 0, 0, 0); +} +.x-masked-relative { + position: relative; +} +.x-ie-shadow { + background-color: #777; + position: absolute; + overflow: hidden; +} +.x-selectable { + cursor: auto; + -moz-user-select: text; + -webkit-user-select: text; + -ms-user-select: text; + user-select: text; + -o-user-select: text; +} +.x-list-plain { + list-style-type: none; + margin: 0; + padding: 0; +} +.x-table-plain { + border-collapse: collapse; + border-spacing: 0; + font-size: 1em; +} +.x-frame-tl, +.x-frame-tr, +.x-frame-tc, +.x-frame-bl, +.x-frame-br, +.x-frame-bc { + overflow: hidden; + background-repeat: no-repeat; +} +.x-frame-tc, +.x-frame-bc { + background-repeat: repeat-x; +} +td.x-frame-tl, +td.x-frame-tr, +td.x-frame-bl, +td.x-frame-br { + width: 1px; +} +.x-frame-mc { + background-repeat: repeat-x; + overflow: hidden; +} +.x-proxy-el { + position: absolute; + background: #b4b4b4; + opacity: 0.8; +} +.x-css-shadow { + position: absolute; + -webkit-border-radius: 5px; + -moz-border-radius: 5px; + -ms-border-radius: 5px; + -o-border-radius: 5px; + border-radius: 5px; +} +.x-item-disabled, +.x-item-disabled * { + cursor: default; + pointer-events: none; +} +.x-component, +.x-container { + position: relative; +} +:focus { + outline: none; +} +.x-body .x-sync-repaint:before, +.x-body .x-sync-repaint:after { + content: none !important; +} +.x-position-relative { + position: relative !important; +} +.x-tab-guard { + position: absolute; + clip: rect(0, 0, 0, 0); +} +.x-box-item { + position: absolute !important; + left: 0; + top: 0; +} +.x-autocontainer-outerCt { + display: table; +} +.x-mobile-safari .x-autocontainer-outerCt { + transform: translateZ(0); +} +.x-clipped .x-autocontainer-outerCt { + transform: initial; +} +.x-autocontainer-innerCt { + display: table-cell; + height: 100%; + vertical-align: top; +} +.x-mask { + z-index: 100; + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + outline: none !important; +} +.x-ie8 .x-mask { + background-image: url(data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7); +} +.x-mask-fixed { + position: fixed; +} +.x-mask-msg { + position: absolute; +} +.x-progress { + border-style: solid; +} +.x-btn { + display: inline-block; + outline: 0; + cursor: pointer; + white-space: nowrap; + text-decoration: none; + vertical-align: top; + overflow: hidden; + position: relative; +} +.x-btn > .x-frame { + height: 100%; + width: 100%; +} +.x-btn-wrap { + height: 100%; + width: 100%; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: stretch; + -ms-flex-align: stretch; + align-items: stretch; +} +.x-btn-wrap.x-btn-arrow-bottom, +.x-btn-wrap.x-btn-split-bottom { + -webkit-box-orient: vertical; + -ms-flex-direction: column; + flex-direction: column; +} +.x-ie9m .x-btn-wrap { + display: table; + border-spacing: 0; +} +.x-btn-button { + white-space: nowrap; + line-height: 0; + position: relative; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: center; + -ms-flex-align: center; + align-items: center; + -webkit-box-flex: 1; + -ms-flex: 1 1 auto; + flex: 1 1 auto; + min-width: 0; +} +.x-btn-button.x-btn-icon-top, +.x-btn-button.x-btn-icon-bottom { + -webkit-box-orient: vertical; + -ms-flex-direction: column; + flex-direction: column; + -webkit-box-align: stretch; + -ms-flex-align: stretch; + align-items: stretch; + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +.x-ie10p .x-btn-button.x-btn-icon-top, +.x-ie10p .x-btn-button.x-btn-icon-bottom { + overflow: hidden; +} +.x-ie9m .x-btn-button { + display: table-cell; + vertical-align: middle; +} +.x-btn-inner { + overflow: hidden; + text-overflow: ellipsis; + -ms-flex-negative: 1; + display: block; +} +.x-ie9m .x-btn-inner { + display: inline-block; + vertical-align: middle; +} +.x-btn-icon.x-btn-no-text > .x-btn-inner { + display: none; +} +.x-btn-icon-el { + display: none; + vertical-align: middle; + text-align: center; + background-position: center center; + background-repeat: no-repeat; + flex-shrink: 0; +} +.x-btn-icon > .x-btn-icon-el { + display: block; +} +.x-ie9m .x-btn-icon-left > .x-btn-icon-el, +.x-ie9m .x-btn-icon-right > .x-btn-icon-el { + display: inline-block; +} +.x-btn-button-center { + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +.x-ie9m .x-btn-button-center { + text-align: center; +} +.x-btn-button-center.x-btn-icon-top, +.x-btn-button-center.x-btn-icon-bottom { + text-align: center; +} +.x-btn-button-left { + text-align: left; + -webkit-box-pack: start; + -ms-flex-pack: start; + justify-content: flex-start; +} +.x-btn-button-right { + text-align: right; + -webkit-box-pack: end; + -ms-flex-pack: end; + justify-content: flex-end; +} +.x-btn-arrow:after, +.x-btn-split:after { + display: block; + background-repeat: no-repeat; + content: ""; + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; + text-align: center; +} +.x-btn-arrow-right:after, +.x-btn-split-right:after { + background-position: right center; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: center; + -ms-flex-align: center; + align-items: center; + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +.x-ie9m .x-btn-arrow-right:after, +.x-ie9m .x-btn-split-right:after { + display: table-cell; + vertical-align: middle; +} +.x-btn-arrow-bottom:after, +.x-btn-split-bottom:after { + background-position: center bottom; + content: "\00a0"; + line-height: 0; +} +.x-ie9m .x-btn-arrow-bottom:after, +.x-ie9m .x-btn-split-bottom:after { + display: table-row; +} +.x-btn-split-right > .x-btn-button:after { + position: absolute; + display: block; + top: -100%; + right: 0; + height: 300%; + content: ""; +} +.x-btn-split-bottom > .x-btn-button:after { + position: absolute; + display: block; + bottom: 0; + left: -100%; + font-size: 0; + width: 300%; + content: ""; +} +.x-btn-mc { + overflow: visible; +} +.x-segmented-button { + display: table; + table-layout: fixed; +} +.x-segmented-button-item { + display: table-cell; + vertical-align: top; +} +.x-segmented-button-item > .x-frame { + width: 100%; + height: 100%; +} +.x-segmented-button-item .x-btn-mc { + width: 100%; +} +.x-segmented-button-item-horizontal { + display: table-cell; + height: 100%; +} +.x-segmented-button-item-horizontal.x-segmented-button-first { + border-top-right-radius: 0; + border-bottom-right-radius: 0; +} +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-tr, +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-mr, +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-br { + display: none; +} +.x-segmented-button-item-horizontal.x-segmented-button-middle { + border-radius: 0; + border-left: 0; +} +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tl, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tr, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-ml, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-mr, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-bl, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-br { + display: none; +} +.x-segmented-button-item-horizontal.x-segmented-button-last { + border-left: 0; + border-top-left-radius: 0; + border-bottom-left-radius: 0; +} +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-tl, +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-ml, +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-bl { + display: none; +} +.x-segmented-button-row { + display: table-row; +} +.x-segmented-button-item-vertical.x-segmented-button-first { + border-bottom-right-radius: 0; + border-bottom-left-radius: 0; +} +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bl, +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bc, +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-br { + display: none; +} +.x-segmented-button-item-vertical.x-segmented-button-middle { + border-radius: 0; + border-top: 0; +} +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tl, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tc, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tr, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bl, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bc, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-br { + display: none; +} +.x-segmented-button-item-vertical.x-segmented-button-last { + border-top: 0; + border-top-right-radius: 0; + border-top-left-radius: 0; +} +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tl, +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tc, +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tr { + display: none; +} +.x-title-icon { + background-repeat: no-repeat; + background-position: 0 0; + vertical-align: middle; + line-height: 1; + text-align: center; +} +.x-title { + display: table; + table-layout: fixed; +} +.x-title-text { + display: table-cell; + overflow: hidden; + white-space: nowrap; + -o-text-overflow: ellipsis; + text-overflow: ellipsis; + vertical-align: middle; +} +.x-title-align-left { + text-align: left; +} +.x-title-align-center { + text-align: center; +} +.x-title-align-right { + text-align: right; +} +.x-title-rotate-right { + -webkit-transform: rotate(90deg); + -webkit-transform-origin: 0 0; + -moz-transform: rotate(90deg); + -moz-transform-origin: 0 0; + -ms-transform: rotate(90deg); + -ms-transform-origin: 0 0; + transform: rotate(90deg); + transform-origin: 0 0; +} + +.x-title-rotate-left { + -webkit-transform: rotate(270deg); + -webkit-transform-origin: 100% 0; + -moz-transform: rotate(270deg); + -moz-transform-origin: 100% 0; + -ms-transform: rotate(270deg); + -ms-transform-origin: 100% 0; + transform: rotate(270deg); + transform-origin: 100% 0; +} +.x-horizontal.x-header + .x-title-rotate-right.x-title-align-left + > .x-title-item { + vertical-align: bottom; +} +.x-horizontal.x-header + .x-title-rotate-right.x-title-align-center + > .x-title-item { + vertical-align: middle; +} +.x-horizontal.x-header + .x-title-rotate-right.x-title-align-right + > .x-title-item { + vertical-align: top; +} +.x-horizontal.x-header .x-title-rotate-left.x-title-align-left > .x-title-item { + vertical-align: top; +} +.x-horizontal.x-header + .x-title-rotate-left.x-title-align-center + > .x-title-item { + vertical-align: middle; +} +.x-horizontal.x-header + .x-title-rotate-left.x-title-align-right + > .x-title-item { + vertical-align: bottom; +} +.x-vertical.x-header .x-title-rotate-none.x-title-align-left > .x-title-item { + vertical-align: top; +} +.x-vertical.x-header .x-title-rotate-none.x-title-align-center > .x-title-item { + vertical-align: middle; +} +.x-vertical.x-header .x-title-rotate-none.x-title-align-right > .x-title-item { + vertical-align: bottom; +} +.x-title-icon-wrap { + display: table-cell; + text-align: center; + vertical-align: middle; + line-height: 0; +} +.x-title-icon-wrap.x-title-icon-top, +.x-title-icon-wrap.x-title-icon-bottom { + display: table-row; +} +.x-title-icon { + display: inline-block; + vertical-align: middle; + background-position: center; + background-repeat: no-repeat; +} +.x-tool { + font-size: 16px; + line-height: 1; +} +.x-header > .x-box-inner, +.x-panel-header-mc > .x-box-inner, +.x-window-header-mc > .x-box-inner { + overflow: visible; +} +.x-splitter { + font-size: 1px; +} +.x-splitter-horizontal { + cursor: e-resize; + cursor: row-resize; +} +.x-splitter-vertical { + cursor: e-resize; + cursor: col-resize; +} +.x-splitter-collapsed, +.x-splitter-horizontal-noresize, +.x-splitter-vertical-noresize { + cursor: default; +} +.x-splitter-active { + z-index: 4; +} +.x-collapse-el { + position: absolute; + background-repeat: no-repeat; +} +.x-splitter-focus { + z-index: 4; +} +.x-box-layout-ct { + overflow: hidden; +} +.x-box-target { + position: absolute; + width: 20000px; + top: 0; + left: 0; + min-height: 1px; +} +.x-box-inner { + overflow: hidden; + position: relative; + left: 0; + top: 0; +} +.x-box-scroller { + position: absolute; + background-repeat: no-repeat; + background-position: center; + line-height: 0; + font-size: 0; + text-align: center; +} +.x-box-scroller-top { + top: 0; +} +.x-box-scroller-right { + right: 0; +} +.x-box-scroller-bottom { + bottom: 0; +} +.x-box-scroller-left { + left: 0; +} +.x-box-menu-body-horizontal { + float: left; +} +.x-box-menu-after { + position: relative; + float: left; +} +.x-box-scroller-body-vertical, +.x-box-scroller-body-horizontal { + -ms-overflow-style: none; +} +.x-box-scroller-body-vertical .x-scroller, +.x-box-scroller-body-horizontal .x-scroller { + -ms-overflow-style: auto; +} +.x-box-scroller-body-vertical :not(.x-scroller)::-webkit-scrollbar, +.x-box-scroller-body-horizontal :not(.x-scroller)::-webkit-scrollbar { + display: none; +} +.x-toolbar-text { + white-space: nowrap; +} +.x-toolbar-separator { + display: block; + font-size: 1px; + overflow: hidden; + cursor: default; + border: 0; + width: 0; + height: 0; + line-height: 0px; +} +.x-toolbar-scroller { + padding-left: 0; +} +.x-toolbar-plain { + border: 0; +} +.x-dd-drag-proxy, +.x-dd-drag-current { + z-index: 1000000 !important; + pointer-events: none; +} +.x-dd-drag-proxy { + display: table; +} +.x-dd-drag-repair .x-dd-drag-ghost { + opacity: 0.6; +} +.x-dd-drag-repair .x-dd-drop-icon { + display: none; +} +.x-dd-drag-ghost, +.x-dd-drop-icon { + display: table-cell; + vertical-align: middle; +} +.x-dd-drag-ghost { + opacity: 0.85; + white-space: nowrap; +} +.x-dd-drop-icon { + height: 26px; + width: 26px; + background-color: transparent; + background-position: center; + background-repeat: no-repeat; +} +.x-docked { + position: absolute !important; + z-index: 2; +} +.x-docked-vertical { + position: static; +} +.x-docked-top { + border-bottom-width: 0 !important; +} +.x-docked-bottom { + border-top-width: 0 !important; +} +.x-docked-left { + border-right-width: 0 !important; +} +.x-docked-right { + border-left-width: 0 !important; +} +.x-docked-noborder-top { + border-top-width: 0 !important; +} +.x-docked-noborder-right { + border-right-width: 0 !important; +} +.x-docked-noborder-bottom { + border-bottom-width: 0 !important; +} +.x-docked-noborder-left { + border-left-width: 0 !important; +} +.x-noborder-l { + border-left-width: 0 !important; +} +.x-noborder-b { + border-bottom-width: 0 !important; +} +.x-noborder-bl { + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-r { + border-right-width: 0 !important; +} +.x-noborder-rl { + border-right-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-rb { + border-right-width: 0 !important; + border-bottom-width: 0 !important; +} +.x-noborder-rbl { + border-right-width: 0 !important; + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-t { + border-top-width: 0 !important; +} +.x-noborder-tl { + border-top-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-tb { + border-top-width: 0 !important; + border-bottom-width: 0 !important; +} +.x-noborder-tbl { + border-top-width: 0 !important; + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-tr { + border-top-width: 0 !important; + border-right-width: 0 !important; +} +.x-noborder-trl { + border-top-width: 0 !important; + border-right-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-trb { + border-top-width: 0 !important; + border-right-width: 0 !important; + border-bottom-width: 0 !important; +} +.x-noborder-trbl { + border-width: 0 !important; +} +.x-panel, +.x-plain { + overflow: hidden; + position: relative; +} +.x-panel { + outline: none; +} +td.x-frame-mc { + vertical-align: top; +} +.x-panel-bodyWrap { + overflow: hidden; + position: static; + height: 100%; + width: 100%; +} +.x-panel-body { + overflow: hidden; + position: relative; +} +.x-panel-header-plain, +.x-panel-body-plain { + border: 0; + padding: 0; +} +.x-panel-collapsed-mini { + visibility: hidden; +} +.x-viewport > .x-body.x-panel > .x-panel-bodyWrap { + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-viewport, +.x-viewport > .x-body { + margin: 0; + padding: 0; + border: 0 none; +} +.x-viewport { + width: 100%; + height: 100%; + position: static; +} +.x-viewport > .x-body { + position: fixed; + top: 0; + left: 0; + min-width: 100%; + min-height: 100%; +} + +@page{ + size: A4; + margin: 20mm; +} +@media print { + .x-viewport > .x-body { + position: static; + -webkit-print-color-adjust: exact; + } + h1, h2, h3, h4, h5, h6 { + page-break-after:avoid; + page-break-inside:avoid + } + + h1+p, h2+p, h3+p { + page-break-before: avoid; + } + a { + page-break-inside:avoid + } + img{ + page-break-after: avoid; + page-break-inside: avoid; + } + table, blockquote{ + page-break-inside: avoid; + } + ul, ol, dl { + page-break-before:avoid; + } + /* 如架構本身用一組一組的 DIV 包住,也可強制設定每組 DIV 會各自切成一頁 */ + div.pageBlock{ + page-break-before: always; + } +} +.x-resizable-overlay { + position: absolute; + left: 0; + top: 0; + width: 100%; + height: 100%; + display: none; + z-index: 200000; + background-color: #fff; + opacity: 0; +} +.x-window { + outline: none; + overflow: hidden; +} +.x-window .x-window-wrap { + position: relative; +} +.x-window-body { + position: relative; + overflow: hidden; +} +.x-form-item { + display: table; + table-layout: fixed; + border-spacing: 0; + border-collapse: separate; +} +.x-form-item-label { + overflow: hidden; +} +.x-form-item.x-form-item-no-label > .x-form-item-label { + display: none; +} +.x-form-item-label, +.x-form-item-body { + display: table-cell; +} +.x-form-item-body { + vertical-align: middle; + height: 100%; +} +.x-form-item-label-inner { + display: inline-block; +} +.x-form-item-label-top { + display: table-row; + height: 1px; +} +.x-form-item-label-top > .x-form-item-label-inner { + display: table-cell; +} +.x-form-item-label-top-side-error:after { + display: table-cell; + content: ""; +} +.x-form-item-label-right { + text-align: right; +} +.x-form-error-wrap-side { + display: table-cell; + vertical-align: middle; +} +.x-form-error-wrap-under { + display: table-row; + height: 1px; +} +.x-form-error-wrap-under > .x-form-error-msg { + display: table-cell; +} +.x-form-error-wrap-under-side-label:before { + display: table-cell; + content: ""; + pointer-events: none; +} +.x-form-invalid-icon { + overflow: hidden; +} +.x-form-invalid-icon ul { + display: none; +} +.x-form-trigger-wrap { + display: table; + width: 100%; +} +.x-form-text-heighted .x-form-trigger-wrap { + height: 100%; +} +.x-gecko .x-form-trigger-wrap { + display: -moz-inline-box; + display: inline-flex; + vertical-align: top; +} +.x-form-type-text.x-has-min-height { + height: 1px; +} +.x-form-type-text.x-has-min-height .x-form-text-field-body, +.x-form-type-text.x-has-min-height .x-form-trigger-wrap, +.x-form-type-text.x-has-min-height .x-form-text-wrap { + min-height: inherit; +} +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-field-body, +.x-ie8 .x-form-type-text.x-has-min-height .x-form-trigger-wrap, +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-wrap { + min-height: inherit; +} +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text { + min-height: inherit; +} +.x-form-type-text.x-has-min-height .x-form-text { + height: 100%; +} +.x-form-text-wrap { + display: table-cell; + overflow: hidden; + height: 100%; + position: relative; +} +.x-gecko .x-form-text-wrap { + display: block; + -moz-box-flex: 1; + flex: 1; +} +.x-form-text-wrap .x-placeholder-label { + position: absolute; + top: 0; + left: 0; + cursor: text; + white-space: nowrap; + overflow: hidden; +} +.x-form-item-body.x-form-text-grow { + min-width: inherit; + max-width: inherit; +} +.x-form-text { + border: 0; + margin: 0; + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + display: block; + background: repeat-x 0 0; + width: 100%; + height: 100%; +} +.x-form-trigger { + display: table-cell; + vertical-align: top; + cursor: pointer; + overflow: hidden; + background-repeat: no-repeat; + text-align: center; + line-height: 0; + white-space: nowrap; +} +.x-item-disabled .x-form-trigger { + cursor: default; +} +.x-form-trigger.x-form-trigger-cmp { + background: none; + border: 0; +} +.x-gecko .x-form-trigger { + display: block; +} +.x-form-textarea-body.x-form-text-grow > .x-form-trigger-wrap { + height: 100%; +} +.x-form-textarea { + overflow: auto; + resize: none; +} +div.x-form-text-grow .x-form-textarea { + min-height: inherit; +} +.x-message-box .x-form-display-field { + height: auto; +} +.x-safari .x-form-fieldcontainer { + table-layout: auto; +} +.x-ie8 + .x-form-fieldcontainer + > .x-form-item-body.x-field-container-body-vertical { + display: table-row; +} +.x-form-cb-wrap { + vertical-align: top; +} +.x-form-cb-wrap-inner { + position: relative; +} +.x-form-cb { + position: absolute; + left: 0; + right: auto; + vertical-align: top; + overflow: hidden; + padding: 0; + border: 0; +} +.x-form-cb::-moz-focus-inner { + padding: 0; + border: 0; +} +.x-form-cb-input { + position: absolute; + margin: 0; + padding: 0; + border: 0; + top: 0; + left: 0; + width: 100%; + height: 100%; + opacity: 0; +} +.x-form-cb-after { + left: auto; + right: 0; +} +.x-form-cb-label { + display: inline-block; +} +.x-form-cb-label.x-form-cb-no-box-label { + display: none; +} +.x-keyboard-mode .x-view-item-focused { + outline: 1px dashed #5aaed4 !important; + outline-offset: -1px; +} +.x-form-display-field-body { + vertical-align: top; +} +.x-form-display-field-body .x-form-display-field { + overflow-wrap: break-word; + word-wrap: break-word; + -ms-word-break: break-all; + word-break: break-all; + word-break: break-word; + -ms-hyphens: auto; + -moz-hyphens: auto; + -webkit-hyphens: auto; + hyphens: auto; +} +.x-form-trigger.x-form-trigger-cmp:before { + content: none; +} +.x-form-file-btn { + overflow: hidden; + position: relative; +} +.x-form-file-input { + border: 0; + position: absolute; + cursor: pointer; + top: 0; + right: 0; + width: 100%; + height: 100%; + overflow: hidden; + text-indent: -10000px; + opacity: 0; + font-size: 1000px; +} +.x-tip { + position: absolute; + overflow: visible; +} +.x-tip-body { + overflow: hidden; + position: relative; +} +.x-tip-anchor { + position: absolute; + border-style: solid; + height: 0; + width: 0; +} +.x-color-picker-item { + float: left; + text-decoration: none; +} +.x-color-picker-item-inner { + display: block; + font-size: 1px; +} +.x-html-editor-tb .x-toolbar { + position: static !important; +} +.x-htmleditor-iframe, +.x-htmleditor-textarea { + display: block; + overflow: auto; + width: 100%; + height: 100%; + border: 0; +} +.x-fit-item { + position: relative; +} +.x-grid-view { + overflow: hidden; + position: relative; +} +.x-grid-row-table { + width: 0; + table-layout: fixed; + border: 0 none; + border-collapse: separate; + border-spacing: 0; +} +.x-grid-item { + table-layout: fixed; + outline: none; + position: relative; +} +.x-ie10 .x-grid-item { + transform: translateZ(0); +} +.x-grid-row { + outline: none; +} +.x-grid-td { + overflow: hidden; + border-width: 0; + vertical-align: top; +} +.x-grid-cell-inner { + overflow: hidden; + white-space: nowrap; +} +.x-wrap-cell .x-grid-cell-inner { + white-space: normal; +} +.x-grid-resize-marker { + position: absolute; + z-index: 5; + top: 0; +} +.x-grid-item-container { + min-height: 1px; + position: relative; +} +.x-col-move-top, +.x-col-move-bottom { + position: absolute; + top: 0; + line-height: 0; + font-size: 0; + overflow: hidden; + z-index: 20000; + background: no-repeat center top transparent; +} +.x-grid-header-ct { + cursor: default; +} +.x-column-header { + position: absolute; + overflow: hidden; + background-repeat: repeat-x; +} +.x-column-header-inner { + white-space: nowrap; + position: relative; + overflow: hidden; +} +.x-leaf-column-header { + height: 100%; +} +.x-leaf-column-header .x-column-header-text-container { + height: 100%; +} +.x-column-header-text-container { + width: 100%; + display: table; + table-layout: fixed; +} +.x-column-header-text-container.x-column-header-text-container-auto { + table-layout: auto; +} +.x-column-header-text-wrapper { + display: table-cell; + vertical-align: middle; +} +.x-column-header-text { + display: block; + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; +} +.x-column-header-sort-DESC .x-column-header-text, +.x-column-header-sort-ASC .x-column-header-text { + overflow: visible; +} +.x-column-header-text-inner { + background-repeat: no-repeat; +} +.x-column-header-inner-empty .x-column-header-text-inner { + display: none; +} +.x-column-header-inner-empty .x-column-header-text-container { + line-height: 0; +} +.x-column-header-trigger { + display: none; + height: 100%; + background-repeat: no-repeat; + position: absolute; + right: 0; + top: 0; + text-align: center; +} +.x-ie9m .x-column-header-trigger { + z-index: 6; +} +.x-column-header-over .x-column-header-trigger, +.x-column-header-open .x-column-header-trigger { + display: block; +} +.x-column-header-align-right { + text-align: right; +} +.x-column-header-align-left { + text-align: left; +} +.x-column-header-align-center { + text-align: center; +} +.x-grid-cell-inner-action-col { + line-height: 0; + font-size: 0; +} +.x-keyboard-mode .x-grid-cell-inner-action-col :focus { + outline: 1px solid #5aaed4; +} +.x-action-col-icon { + display: inline-block; + line-height: 1; +} +.x-column-header-checkbox .x-column-header-text { + margin-bottom: 0.4em; +} +.x-column-header-checkbox .x-column-header-inner-empty .x-column-header-text { + margin-bottom: 0; +} +.x-grid-checkcolumn-cell-inner { + line-height: 0; +} +.x-keyboard-mode .x-grid-checkcolumn-cell-inner :focus { + outline: 1px solid #5aaed4; +} +.x-menu { + outline: none; +} +.x-menu-body { + position: relative; +} +.x-menu-item { + white-space: nowrap; + overflow: hidden; + border-color: transparent; + border-style: solid; +} +.x-menu-item-cmp { + margin: 2px; +} +.x-menu-item-cmp .x-field-label-cell { + vertical-align: middle; +} +.x-menu-icon-separator { + position: absolute; + top: 0px; + z-index: 0; + height: 100%; + overflow: hidden; +} +.x-menu-plain .x-menu-icon-separator { + display: none; +} +.x-menu-item-link { + -webkit-tap-highlight-color: transparent; + -webkit-touch-callout: none; + text-decoration: none; + outline: 0; + display: block; +} +.x-menu-item-link-href { + -webkit-touch-callout: default; +} +.x-menu-item-text { + display: inline-block; +} +.x-menu-item-icon, +.x-menu-item-icon-right, +.x-menu-item-arrow { + font-size: 0; + position: absolute; + text-align: center; + background-repeat: no-repeat; +} +.x-grid-scroll-container { + position: absolute; + z-index: 1; +} +.x-grid-scrollbar-clipper-floated, +.x-grid-scrollbar-floated { + z-index: 2; +} +.x-grid-scroll-body { + width: 100%; + position: relative; +} +.x-grid-scrollbar-clipper { + overflow: hidden; + position: absolute; + top: 0; + left: 0; +} +.x-grid-scrollbar-clipper > .x-grid-view, +.x-grid-scrollbar-clipper > .x-tree-view { + overflow-y: hidden !important; +} +.x-grid-with-col-lines .x-grid-scrollbar-clipper-locked .x-grid-cell-last { + border-right-width: 0; +} +.x-grid-scrollbar { + position: absolute; + bottom: 0; + left: 0; + display: none; +} +.x-grid-scrollbar-visible { + display: block; +} +.x-grid-locking-body > .x-grid { + z-index: 2; + pointer-events: none; +} +.x-grid-locking-body > .x-grid .x-docked { + pointer-events: auto; +} +.x-grid-locking-body .x-grid-body { + background: transparent; +} +.x-grid-locking-body > .x-splitter { + z-index: 2; +} +.x-grid-locking-body > .x-splitter-active { + z-index: 4; +} +.x-grid-locking-body > .x-splitter-focus { + z-index: 4; +} +.x-grid-inner-locked.x-border-region-slide-in { + z-index: 3; +} +.x-grid-inner-locked.x-border-region-slide-in + > .x-panel-bodyWrap + > .x-grid-body + > .x-grid-view, +.x-grid-inner-locked.x-border-region-slide-in + > .x-panel-bodyWrap + > .x-grid-body + > .x-tree-view { + overflow-y: hidden !important; +} +.x-resizable-wrapped { + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +.x-slider { + outline: none; + position: relative; +} +.x-slider-inner { + position: relative; + left: 0; + top: 0; + overflow: visible; +} +.x-slider-vert .x-slider-inner { + background: repeat-y 0 0; +} +.x-slider-thumb { + position: absolute; + background: no-repeat 0 0; + cursor: default; + -webkit-user-callout: none; + display: table; + table-layout: fixed; +} +.x-slider-horz .x-slider-thumb { + left: 0; +} +.x-slider-vert .x-slider-thumb { + bottom: 0; +} +.x-slider-thumb:before { + display: table-cell; + vertical-align: middle; + text-align: center; +} +.x-tab { + display: block; + outline: 0; + cursor: pointer; + white-space: nowrap; + text-decoration: none; + /* vertical-align: top; */ + overflow: hidden; + position: relative; +} +.x-tab > .x-frame { + height: 100%; + width: 100%; +} +.x-tab-wrap { + height: 100%; + width: 100%; + display: table; + border-spacing: 0; +} +.x-tab-button { + white-space: nowrap; + line-height: 0; + position: relative; + display: table-cell; + vertical-align: middle; +} +.x-tab-inner { + overflow: hidden; + text-overflow: ellipsis; + display: inline-block; + vertical-align: middle; +} +.x-tab-icon.x-tab-no-text > .x-tab-inner { + display: none; +} +.x-tab-icon-el { + display: none; + vertical-align: middle; + text-align: center; + background-position: center center; + background-repeat: no-repeat; +} +.x-tab-icon > .x-tab-icon-el { + display: inline-block; +} +.x-tab-icon-top > .x-tab-icon-el, +.x-tab-icon-bottom > .x-tab-icon-el { + display: block; +} +.x-ie9m .x-tab-button-center { + text-align: center; +} +.x-tab-button-center.x-tab-icon-top, +.x-tab-button-center.x-tab-icon-bottom { + text-align: center; +} +.x-tab-button-left { + text-align: left; +} +.x-tab-button-right { + text-align: right; +} +.x-tab-mc { + overflow: visible; +} +.x-tab { + z-index: 1; +} +.x-tab-active { + z-index: 3; +} +.x-tab-button { + position: relative; +} +.x-tab-close-btn { + display: block; + position: absolute; + overflow: hidden; + font-size: 0; + line-height: 0; +} +.x-tab-rotate-left { + -webkit-transform: rotate(270deg); + -webkit-transform-origin: 100% 0; + -moz-transform: rotate(270deg); + -moz-transform-origin: 100% 0; + -ms-transform: rotate(270deg); + -ms-transform-origin: 100% 0; + transform: rotate(270deg); + transform-origin: 100% 0; +} +.x-tab-rotate-right { + -webkit-transform: rotate(90deg); + -webkit-transform-origin: 0 0; + -moz-transform: rotate(90deg); + -moz-transform-origin: 0 0; + -ms-transform: rotate(90deg); + -ms-transform-origin: 0 0; + transform: rotate(90deg); + transform-origin: 0 0; +} +.x-tab-tr, +.x-tab-br, +.x-tab-mr, +.x-tab-tl, +.x-tab-bl, +.x-tab-ml { + width: 1px; +} +.x-tab-bar { + z-index: 0; + position: relative; +} +.x-tab-bar-strip { + position: absolute; + line-height: 0; + font-size: 0; + z-index: 2; +} +.x-tab-bar-top > .x-tab-bar-strip { + bottom: 0; +} +.x-tab-bar-bottom > .x-tab-bar-strip { + top: 0; +} +.x-tab-bar-left > .x-tab-bar-strip { + right: 0; +} +.x-tab-bar-right > .x-tab-bar-strip { + left: 0; +} +.x-tab-bar-horizontal .x-tab-bar-strip { + width: 100%; + left: 0; +} +.x-tab-bar-vertical { + display: table-cell; +} +.x-tab-bar-vertical .x-tab-bar-strip { + height: 100%; + top: 0; +} +.x-tab-bar-plain { + background: transparent !important; +} +.x-box-scroller-plain { + background-color: transparent !important; +} +.x-body { + color: #404040; + font-size: 14px; + line-height: 17px; + font-weight: 400; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + background: #f6f6f6; +} +.x-animating-size, +.x-collapsed { + overflow: hidden !important; +} +.x-animating-size { + z-index: 10000; +} +.x-mask { + background-image: none; + background-color: rgba(208, 208, 208, 0.5); + cursor: default; + border-style: solid; + border-width: 1px; + border-color: transparent; +} +.x-ie8 .x-mask { + zoom: 1; +} +body > .x-mask { + background-image: none; + background-color: rgba(0, 0, 0, 0.75); +} +.x-ie8 body > .x-mask { + zoom: 1; +} +.x-keyboard-mode .x-mask.x-focus { + border-style: solid; + border-width: 1px; + border-color: #5aaed4; +} +.x-mask-msg { + padding: 10px; + background: #d0d0d0; +} +.x-mask-msg-inner { + padding: 0; + background-color: transparent; + color: #404040; + font: 400 14px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; +} +.x-mask-msg-text { + padding: 25px 0 0; + background-image: url(images/loadmask/loading.gif); + background-repeat: no-repeat; + background-position: center 0; +} +.x-progress-default { + background-color: #ececec; + border-width: 0; + height: 24px; + border-color: #5aaed4; + border-style: solid; +} +.x-progress-default .x-progress-bar-default { + background-image: none; + background-color: #458fd2; +} +.x-progress-default .x-progress-text { + color: #fff; + font-weight: 500; + font-size: 14px; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + text-align: center; + line-height: 24px; +} +.x-progress-default .x-progress-text-back { + color: #404040; + line-height: 24px; +} +.x-keyboard-mode .x-progress-default.x-progress-focus:after { + position: absolute; + content: " "; + top: 0; + right: 0; + bottom: 0; + left: 0; + border: 0 solid #5aaed4; + pointer-events: none; +} +.x-progressbar-default-cell > .x-grid-cell-inner, +.x-progress-default-cell > .x-grid-cell-inner, +.x-progressbarwidget-default-cell > .x-grid-cell-inner { + padding-top: 4px; + padding-bottom: 4px; +} +.x-progressbar-default-cell > .x-grid-cell-inner .x-progress-default, +.x-progress-default-cell > .x-grid-cell-inner .x-progress-default, +.x-progressbarwidget-default-cell > .x-grid-cell-inner .x-progress-default { + height: 24px; +} +.x-btn-default-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 7; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #5aaed4; +} +.x-btn-default-small-mc { + background-color: #5aaed4; +} +.x-nbr .x-btn-default-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-default-small-tl { + background-position: 0 -2px; +} +.x-btn-default-small-tr { + background-position: right -3px; +} +.x-btn-default-small-bl { + background-position: 0 -4px; +} +.x-btn-default-small-br { + background-position: right -5px; +} +.x-btn-default-small-ml { + background-position: 0 top; +} +.x-btn-default-small-mr { + background-position: right top; +} +.x-btn-default-small-tc { + background-position: 0 0; +} +.x-btn-default-small-bc { + background-position: 0 -1px; +} +.x-btn-default-small-tr, +.x-btn-default-small-br, +.x-btn-default-small-mr { + padding-right: 1px; +} +.x-btn-default-small-tl, +.x-btn-default-small-bl, +.x-btn-default-small-ml { + padding-left: 1px; +} +.x-btn-default-small-tc { + height: 1px; +} +.x-btn-default-small-bc { + height: 1px; +} +.x-btn-default-small-tl, +.x-btn-default-small-bl, +.x-btn-default-small-tr, +.x-btn-default-small-br, +.x-btn-default-small-tc, +.x-btn-default-small-bc, +.x-btn-default-small-ml, +.x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-corners.gif); +} +.x-btn-default-small-ml, +.x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-default-small { + border-color: #31ade5; +} +.x-btn-button-default-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-default-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-default-small { + font: 500 14px/16px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-default-small { + max-width: none; +} +.x-btn-icon-el-default-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-default-small, +.x-btn-icon-right > .x-btn-icon-el-default-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-default-small, +.x-btn-icon-bottom > .x-btn-icon-el-default-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-default-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-default-small, +.x-btn-split-bottom > .x-btn-button-default-small { + padding-bottom: 7px; +} +.x-btn-wrap-default-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-default-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-default-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-default-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-default-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-default-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-small { + background-image: none; + background-color: #5aaed4; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-default-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-default-small { + border-color: #2d9fd2; + background-image: none; + background-color: #31abe2; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-small, +.x-btn.x-btn-pressed.x-btn-default-small { + border-color: #2582ac; + background-image: none; + background-color: #288cb9; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-small { + background-image: none; + background-color: #5aaed4; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-small-mc { + background-color: #5aaed4; +} +.x-btn-over .x-btn-default-small-tl, +.x-btn-over .x-btn-default-small-bl, +.x-btn-over .x-btn-default-small-tr, +.x-btn-over .x-btn-default-small-br, +.x-btn-over .x-btn-default-small-tc, +.x-btn-over .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-over-corners.gif); +} +.x-btn-over .x-btn-default-small-ml, +.x-btn-over .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-over-sides.gif); +} +.x-btn-over .x-btn-default-small-mc { + background-color: #31abe2; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mc { + background-color: #31abe2; +} +.x-btn.x-btn-menu-active .x-btn-default-small-tl, +.x-btn.x-btn-menu-active .x-btn-default-small-bl, +.x-btn.x-btn-menu-active .x-btn-default-small-tr, +.x-btn.x-btn-menu-active .x-btn-default-small-br, +.x-btn.x-btn-menu-active .x-btn-default-small-tc, +.x-btn.x-btn-menu-active .x-btn-default-small-bc, +.x-btn.x-btn-pressed .x-btn-default-small-tl, +.x-btn.x-btn-pressed .x-btn-default-small-bl, +.x-btn.x-btn-pressed .x-btn-default-small-tr, +.x-btn.x-btn-pressed .x-btn-default-small-br, +.x-btn.x-btn-pressed .x-btn-default-small-tc, +.x-btn.x-btn-pressed .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-small-ml, +.x-btn.x-btn-menu-active .x-btn-default-small-mr, +.x-btn.x-btn-pressed .x-btn-default-small-ml, +.x-btn.x-btn-pressed .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-small-mc, +.x-btn.x-btn-pressed .x-btn-default-small-mc { + background-color: #288cb9; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mc { + background-color: #288cb9; +} +.x-btn.x-btn-disabled .x-btn-default-small-tl, +.x-btn.x-btn-disabled .x-btn-default-small-bl, +.x-btn.x-btn-disabled .x-btn-default-small-tr, +.x-btn.x-btn-disabled .x-btn-default-small-br, +.x-btn.x-btn-disabled .x-btn-default-small-tc, +.x-btn.x-btn-disabled .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-small-ml, +.x-btn.x-btn-disabled .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-small-mc { + background-color: #5aaed4; +} +.x-nbr .x-btn-default-small { + background-image: none; +} +.x-btn-disabled.x-btn-default-small { + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first + .x-btn-default-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle + .x-btn-default-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last + .x-btn-default-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first + .x-btn-default-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle + .x-btn-default-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last + .x-btn-default-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-default-medium { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 8px 8px 8px; + border-width: 1px; + border-style: solid; + background-color: #5aaed4; +} +.x-btn-default-medium-mc { + background-color: #5aaed4; +} +.x-nbr .x-btn-default-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-medium-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-8-8-8-8; +} +.x-btn-default-medium-tl { + background-position: 0 -2px; +} +.x-btn-default-medium-tr { + background-position: right -3px; +} +.x-btn-default-medium-bl { + background-position: 0 -4px; +} +.x-btn-default-medium-br { + background-position: right -5px; +} +.x-btn-default-medium-ml { + background-position: 0 top; +} +.x-btn-default-medium-mr { + background-position: right top; +} +.x-btn-default-medium-tc { + background-position: 0 0; +} +.x-btn-default-medium-bc { + background-position: 0 -1px; +} +.x-btn-default-medium-tr, +.x-btn-default-medium-br, +.x-btn-default-medium-mr { + padding-right: 1px; +} +.x-btn-default-medium-tl, +.x-btn-default-medium-bl, +.x-btn-default-medium-ml { + padding-left: 1px; +} +.x-btn-default-medium-tc { + height: 1px; +} +.x-btn-default-medium-bc { + height: 1px; +} +.x-btn-default-medium-tl, +.x-btn-default-medium-bl, +.x-btn-default-medium-tr, +.x-btn-default-medium-br, +.x-btn-default-medium-tc, +.x-btn-default-medium-bc, +.x-btn-default-medium-ml, +.x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-corners.gif); +} +.x-btn-default-medium-ml, +.x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-medium-mc { + padding: 8px 8px 8px 8px; +} +.x-btn-default-medium { + border-color: #31ade5; +} +.x-btn-button-default-medium { + min-height: 20px; +} +.x-ie9m .x-btn-button-default-medium { + min-height: auto; + height: 20px; +} +.x-btn-inner-default-medium { + font: 500 14px/18px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #f0f0f0; + padding: 0 8px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-medium { + max-width: calc(100% - 20px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-medium { + max-width: calc(100% - 19px); +} +.x-ie10p .x-btn-inner-default-medium { + max-width: none; +} +.x-btn-icon-el-default-medium { + font-size: 20px; + height: 20px; + color: #f0f0f0; + line-height: 20px; +} +.x-btn-icon-left > .x-btn-icon-el-default-medium, +.x-btn-icon-right > .x-btn-icon-el-default-medium { + width: 20px; +} +.x-btn-icon-top > .x-btn-icon-el-default-medium, +.x-btn-icon-bottom > .x-btn-icon-el-default-medium { + min-width: 20px; +} +.x-ie8 .x-btn-icon-el-default-medium.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-medium { + margin-right: 0px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium { + margin-left: 0px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-medium { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-medium { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-medium { + margin-right: 8px; +} +.x-btn-arrow-bottom > .x-btn-button-default-medium, +.x-btn-split-bottom > .x-btn-button-default-medium { + padding-bottom: 8px; +} +.x-btn-wrap-default-medium.x-btn-arrow-right:after { + width: 20px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-medium.x-btn-arrow-bottom:after { + height: 14px; + content: "\f0d7"; + font: 20px/14px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-medium.x-btn-split-right > .x-btn-button { + padding-right: 8px; +} +.x-btn-wrap-default-medium.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-default-medium.x-btn-split-right:after { + width: 26px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #f0f0f0; + padding-left: 8px; +} +.x-btn-wrap-default-medium.x-btn-split-bottom { + margin-bottom: -8px; +} +.x-btn-wrap-default-medium.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-default-medium.x-btn-split-bottom:after { + height: 24px; + content: "\f0d7"; + font: 20px/24px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-medium { + margin-right: 8px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-medium { + background-image: none; + background-color: #5aaed4; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-default-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 34px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-default-medium { + border-color: #2d9fd2; + background-image: none; + background-color: #31abe2; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-medium { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-medium, +.x-btn.x-btn-pressed.x-btn-default-medium { + border-color: #2582ac; + background-image: none; + background-color: #288cb9; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-medium { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-medium { + background-image: none; + background-color: #5aaed4; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mc { + background-color: #5aaed4; +} +.x-btn-over .x-btn-default-medium-tl, +.x-btn-over .x-btn-default-medium-bl, +.x-btn-over .x-btn-default-medium-tr, +.x-btn-over .x-btn-default-medium-br, +.x-btn-over .x-btn-default-medium-tc, +.x-btn-over .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-over-corners.gif); +} +.x-btn-over .x-btn-default-medium-ml, +.x-btn-over .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-over-sides.gif); +} +.x-btn-over .x-btn-default-medium-mc { + background-color: #31abe2; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mc { + background-color: #31abe2; +} +.x-btn.x-btn-menu-active .x-btn-default-medium-tl, +.x-btn.x-btn-menu-active .x-btn-default-medium-bl, +.x-btn.x-btn-menu-active .x-btn-default-medium-tr, +.x-btn.x-btn-menu-active .x-btn-default-medium-br, +.x-btn.x-btn-menu-active .x-btn-default-medium-tc, +.x-btn.x-btn-menu-active .x-btn-default-medium-bc, +.x-btn.x-btn-pressed .x-btn-default-medium-tl, +.x-btn.x-btn-pressed .x-btn-default-medium-bl, +.x-btn.x-btn-pressed .x-btn-default-medium-tr, +.x-btn.x-btn-pressed .x-btn-default-medium-br, +.x-btn.x-btn-pressed .x-btn-default-medium-tc, +.x-btn.x-btn-pressed .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-medium-ml, +.x-btn.x-btn-menu-active .x-btn-default-medium-mr, +.x-btn.x-btn-pressed .x-btn-default-medium-ml, +.x-btn.x-btn-pressed .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-medium-mc, +.x-btn.x-btn-pressed .x-btn-default-medium-mc { + background-color: #288cb9; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mc { + background-color: #288cb9; +} +.x-btn.x-btn-disabled .x-btn-default-medium-tl, +.x-btn.x-btn-disabled .x-btn-default-medium-bl, +.x-btn.x-btn-disabled .x-btn-default-medium-tr, +.x-btn.x-btn-disabled .x-btn-default-medium-br, +.x-btn.x-btn-disabled .x-btn-default-medium-tc, +.x-btn.x-btn-disabled .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-medium-ml, +.x-btn.x-btn-disabled .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-medium-mc { + background-color: #5aaed4; +} +.x-nbr .x-btn-default-medium { + background-image: none; +} +.x-btn-disabled.x-btn-default-medium { + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first + .x-btn-default-medium-mc { + padding-right: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle + .x-btn-default-medium-mc { + padding-right: 8px !important; + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last + .x-btn-default-medium-mc { + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first + .x-btn-default-medium-mc { + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle + .x-btn-default-medium-mc { + padding-top: 8px !important; + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last + .x-btn-default-medium-mc { + padding-top: 8px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-medium:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-medium:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-medium:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-medium:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-medium:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-default-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #5aaed4; +} +.x-btn-default-large-mc { + background-color: #5aaed4; +} +.x-nbr .x-btn-default-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +.x-btn-default-large-tl { + background-position: 0 -2px; +} +.x-btn-default-large-tr { + background-position: right -3px; +} +.x-btn-default-large-bl { + background-position: 0 -4px; +} +.x-btn-default-large-br { + background-position: right -5px; +} +.x-btn-default-large-ml { + background-position: 0 top; +} +.x-btn-default-large-mr { + background-position: right top; +} +.x-btn-default-large-tc { + background-position: 0 0; +} +.x-btn-default-large-bc { + background-position: 0 -1px; +} +.x-btn-default-large-tr, +.x-btn-default-large-br, +.x-btn-default-large-mr { + padding-right: 1px; +} +.x-btn-default-large-tl, +.x-btn-default-large-bl, +.x-btn-default-large-ml { + padding-left: 1px; +} +.x-btn-default-large-tc { + height: 1px; +} +.x-btn-default-large-bc { + height: 1px; +} +.x-btn-default-large-tl, +.x-btn-default-large-bl, +.x-btn-default-large-tr, +.x-btn-default-large-br, +.x-btn-default-large-tc, +.x-btn-default-large-bc, +.x-btn-default-large-ml, +.x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-corners.gif); +} +.x-btn-default-large-ml, +.x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-large-mc { + padding: 9px 9px 9px 9px; +} +.x-btn-default-large { + border-color: #31ade5; +} +.x-btn-button-default-large { + min-height: 24px; +} +.x-ie9m .x-btn-button-default-large { + min-height: auto; + height: 24px; +} +.x-btn-inner-default-large { + font: 500 16px/20px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #f0f0f0; + padding: 0 10px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-large { + max-width: calc(100% - 24px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-large { + max-width: calc(100% - 23px); +} +.x-ie10p .x-btn-inner-default-large { + max-width: none; +} +.x-btn-icon-el-default-large { + font-size: 24px; + height: 24px; + color: #f0f0f0; + line-height: 24px; +} +.x-btn-icon-left > .x-btn-icon-el-default-large, +.x-btn-icon-right > .x-btn-icon-el-default-large { + width: 24px; +} +.x-btn-icon-top > .x-btn-icon-el-default-large, +.x-btn-icon-bottom > .x-btn-icon-el-default-large { + min-width: 24px; +} +.x-ie8 .x-btn-icon-el-default-large.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-large { + margin-right: 0; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large { + margin-left: 0; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-large { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-large { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-large { + margin-right: 10px; +} +.x-btn-arrow-bottom > .x-btn-button-default-large, +.x-btn-split-bottom > .x-btn-button-default-large { + padding-bottom: 9px; +} +.x-btn-wrap-default-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +.x-btn-wrap-default-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-default-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; + padding-left: 9px; +} +.x-btn-wrap-default-large.x-btn-split-bottom { + margin-bottom: -9px; +} +.x-btn-wrap-default-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-default-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-large { + margin-right: 10px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-large { + background-image: none; + background-color: #5aaed4; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-default-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-default-large { + border-color: #2d9fd2; + background-image: none; + background-color: #31abe2; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-large { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-large, +.x-btn.x-btn-pressed.x-btn-default-large { + border-color: #2582ac; + background-image: none; + background-color: #288cb9; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-large { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-large { + background-image: none; + background-color: #5aaed4; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-large-mc { + background-color: #5aaed4; +} +.x-btn-over .x-btn-default-large-tl, +.x-btn-over .x-btn-default-large-bl, +.x-btn-over .x-btn-default-large-tr, +.x-btn-over .x-btn-default-large-br, +.x-btn-over .x-btn-default-large-tc, +.x-btn-over .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-over-corners.gif); +} +.x-btn-over .x-btn-default-large-ml, +.x-btn-over .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-over-sides.gif); +} +.x-btn-over .x-btn-default-large-mc { + background-color: #31abe2; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mc { + background-color: #31abe2; +} +.x-btn.x-btn-menu-active .x-btn-default-large-tl, +.x-btn.x-btn-menu-active .x-btn-default-large-bl, +.x-btn.x-btn-menu-active .x-btn-default-large-tr, +.x-btn.x-btn-menu-active .x-btn-default-large-br, +.x-btn.x-btn-menu-active .x-btn-default-large-tc, +.x-btn.x-btn-menu-active .x-btn-default-large-bc, +.x-btn.x-btn-pressed .x-btn-default-large-tl, +.x-btn.x-btn-pressed .x-btn-default-large-bl, +.x-btn.x-btn-pressed .x-btn-default-large-tr, +.x-btn.x-btn-pressed .x-btn-default-large-br, +.x-btn.x-btn-pressed .x-btn-default-large-tc, +.x-btn.x-btn-pressed .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-large-ml, +.x-btn.x-btn-menu-active .x-btn-default-large-mr, +.x-btn.x-btn-pressed .x-btn-default-large-ml, +.x-btn.x-btn-pressed .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-large-mc, +.x-btn.x-btn-pressed .x-btn-default-large-mc { + background-color: #288cb9; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mc { + background-color: #288cb9; +} +.x-btn.x-btn-disabled .x-btn-default-large-tl, +.x-btn.x-btn-disabled .x-btn-default-large-bl, +.x-btn.x-btn-disabled .x-btn-default-large-tr, +.x-btn.x-btn-disabled .x-btn-default-large-br, +.x-btn.x-btn-disabled .x-btn-default-large-tc, +.x-btn.x-btn-disabled .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-large-ml, +.x-btn.x-btn-disabled .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-large-mc { + background-color: #5aaed4; +} +.x-nbr .x-btn-default-large { + background-image: none; +} +.x-btn-disabled.x-btn-default-large { + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first + .x-btn-default-large-mc { + padding-right: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle + .x-btn-default-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last + .x-btn-default-large-mc { + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first + .x-btn-default-large-mc { + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle + .x-btn-default-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last + .x-btn-default-large-mc { + padding-top: 9px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-large:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-large:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-large:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-large:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-large:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-default-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #f6f6f6; +} +.x-btn-default-toolbar-small-mc { + background-color: #8d8d8d; +} +.x-nbr .x-btn-default-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-default-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-default-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-default-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-default-toolbar-small-br { + background-position: right -5px; +} +.x-btn-default-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-default-toolbar-small-mr { + background-position: right top; +} +.x-btn-default-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-default-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-default-toolbar-small-tr, +.x-btn-default-toolbar-small-br, +.x-btn-default-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-default-toolbar-small-tl, +.x-btn-default-toolbar-small-bl, +.x-btn-default-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-default-toolbar-small-tc { + height: 1px; +} +.x-btn-default-toolbar-small-bc { + height: 1px; +} +.x-btn-default-toolbar-small-tl, +.x-btn-default-toolbar-small-bl, +.x-btn-default-toolbar-small-tr, +.x-btn-default-toolbar-small-br, +.x-btn-default-toolbar-small-tc, +.x-btn-default-toolbar-small-bc, +.x-btn-default-toolbar-small-ml, +.x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-corners.gif); +} +.x-btn-default-toolbar-small-ml, +.x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-default-toolbar-small { + border-color:transparent; +} +.x-btn-button-default-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-default-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-default-toolbar-small { + font: 500 12px/16px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-default-toolbar-small { + max-width: none; +} +.x-btn-icon-el-default-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-default-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-small, +.x-btn-split-bottom > .x-btn-button-default-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-default-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-small { + background-image: none; + background-color: #f6f6f6; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-default-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-default-toolbar-small { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-toolbar-small, +.x-btn.x-btn-pressed.x-btn-default-toolbar-small { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-toolbar-small { + background-image: none; + background-color: #f6f6f6; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mc { + background-color: #f6f6f6; +} +.x-btn-over .x-btn-default-toolbar-small-tl, +.x-btn-over .x-btn-default-toolbar-small-bl, +.x-btn-over .x-btn-default-toolbar-small-tr, +.x-btn-over .x-btn-default-toolbar-small-br, +.x-btn-over .x-btn-default-toolbar-small-tc, +.x-btn-over .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-default-toolbar-small-ml, +.x-btn-over .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-default-toolbar-small-mc { + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mc { + background-color: #ececec; +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mc { + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mc { + background-color: #e2e2e2; +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-default-toolbar-small { + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first + .x-btn-default-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle + .x-btn-default-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last + .x-btn-default-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first + .x-btn-default-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle + .x-btn-default-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last + .x-btn-default-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-default-toolbar-medium { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 8px 8px 8px; + border-width: 1px; + border-style: solid; + background-color: #f6f6f6; +} +.x-btn-default-toolbar-medium-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-toolbar-medium-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-8-8-8-8; +} +.x-btn-default-toolbar-medium-tl { + background-position: 0 -2px; +} +.x-btn-default-toolbar-medium-tr { + background-position: right -3px; +} +.x-btn-default-toolbar-medium-bl { + background-position: 0 -4px; +} +.x-btn-default-toolbar-medium-br { + background-position: right -5px; +} +.x-btn-default-toolbar-medium-ml { + background-position: 0 top; +} +.x-btn-default-toolbar-medium-mr { + background-position: right top; +} +.x-btn-default-toolbar-medium-tc { + background-position: 0 0; +} +.x-btn-default-toolbar-medium-bc { + background-position: 0 -1px; +} +.x-btn-default-toolbar-medium-tr, +.x-btn-default-toolbar-medium-br, +.x-btn-default-toolbar-medium-mr { + padding-right: 1px; +} +.x-btn-default-toolbar-medium-tl, +.x-btn-default-toolbar-medium-bl, +.x-btn-default-toolbar-medium-ml { + padding-left: 1px; +} +.x-btn-default-toolbar-medium-tc { + height: 1px; +} +.x-btn-default-toolbar-medium-bc { + height: 1px; +} +.x-btn-default-toolbar-medium-tl, +.x-btn-default-toolbar-medium-bl, +.x-btn-default-toolbar-medium-tr, +.x-btn-default-toolbar-medium-br, +.x-btn-default-toolbar-medium-tc, +.x-btn-default-toolbar-medium-bc, +.x-btn-default-toolbar-medium-ml, +.x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-corners.gif); +} +.x-btn-default-toolbar-medium-ml, +.x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-toolbar-medium-mc { + padding: 8px 8px 8px 8px; +} +.x-btn-default-toolbar-medium { + border-color: #e4e4e4; +} +.x-btn-button-default-toolbar-medium { + min-height: 20px; +} +.x-ie9m .x-btn-button-default-toolbar-medium { + min-height: auto; + height: 20px; +} +.x-btn-inner-default-toolbar-medium { + font: 500 14px/18px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #606060; + padding: 0 8px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-medium { + max-width: calc(100% - 20px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-medium { + max-width: calc(100% - 19px); +} +.x-ie10p .x-btn-inner-default-toolbar-medium { + max-width: none; +} +.x-btn-icon-el-default-toolbar-medium { + font-size: 20px; + height: 20px; + color: #919191; + line-height: 20px; +} +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + width: 20px; +} +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium { + min-width: 20px; +} +.x-ie8 .x-btn-icon-el-default-toolbar-medium.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium { + margin-right: 0px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + margin-left: 0px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-medium { + margin-right: 8px; +} +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-medium, +.x-btn-split-bottom > .x-btn-button-default-toolbar-medium { + padding-bottom: 8px; +} +.x-btn-wrap-default-toolbar-medium.x-btn-arrow-right:after { + width: 20px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-medium.x-btn-arrow-bottom:after { + height: 14px; + content: "\f0d7"; + font: 20px/14px FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-right > .x-btn-button { + padding-right: 8px; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-right:after { + width: 26px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; + padding-left: 8px; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom { + margin-bottom: -8px; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom:after { + height: 24px; + content: "\f0d7"; + font: 20px/24px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-medium { + margin-right: 8px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-medium { + background-image: none; + background-color: #f6f6f6; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-default-toolbar-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 34px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-toolbar-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-default-toolbar-medium { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-medium { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-toolbar-medium, +.x-btn.x-btn-pressed.x-btn-default-toolbar-medium { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-toolbar-medium { + background-image: none; + background-color: #f6f6f6; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mc { + background-color: #f6f6f6; +} +.x-btn-over .x-btn-default-toolbar-medium-tl, +.x-btn-over .x-btn-default-toolbar-medium-bl, +.x-btn-over .x-btn-default-toolbar-medium-tr, +.x-btn-over .x-btn-default-toolbar-medium-br, +.x-btn-over .x-btn-default-toolbar-medium-tc, +.x-btn-over .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-over-corners.gif); +} +.x-btn-over .x-btn-default-toolbar-medium-ml, +.x-btn-over .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-over-sides.gif); +} +.x-btn-over .x-btn-default-toolbar-medium-mc { + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mc { + background-color: #ececec; +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mc { + background-color: #e2e2e2; +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-br, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mc { + background-color: #e2e2e2; +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-medium { + background-image: none; +} +.x-btn-disabled.x-btn-default-toolbar-medium { + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first + .x-btn-default-toolbar-medium-mc { + padding-right: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle + .x-btn-default-toolbar-medium-mc { + padding-right: 8px !important; + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last + .x-btn-default-toolbar-medium-mc { + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first + .x-btn-default-toolbar-medium-mc { + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle + .x-btn-default-toolbar-medium-mc { + padding-top: 8px !important; + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last + .x-btn-default-toolbar-medium-mc { + padding-top: 8px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-medium:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-default-toolbar-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #f6f6f6; +} +.x-btn-default-toolbar-large-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-toolbar-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +.x-btn-default-toolbar-large-tl { + background-position: 0 -2px; +} +.x-btn-default-toolbar-large-tr { + background-position: right -3px; +} +.x-btn-default-toolbar-large-bl { + background-position: 0 -4px; +} +.x-btn-default-toolbar-large-br { + background-position: right -5px; +} +.x-btn-default-toolbar-large-ml { + background-position: 0 top; +} +.x-btn-default-toolbar-large-mr { + background-position: right top; +} +.x-btn-default-toolbar-large-tc { + background-position: 0 0; +} +.x-btn-default-toolbar-large-bc { + background-position: 0 -1px; +} +.x-btn-default-toolbar-large-tr, +.x-btn-default-toolbar-large-br, +.x-btn-default-toolbar-large-mr { + padding-right: 1px; +} +.x-btn-default-toolbar-large-tl, +.x-btn-default-toolbar-large-bl, +.x-btn-default-toolbar-large-ml { + padding-left: 1px; +} +.x-btn-default-toolbar-large-tc { + height: 1px; +} +.x-btn-default-toolbar-large-bc { + height: 1px; +} +.x-btn-default-toolbar-large-tl, +.x-btn-default-toolbar-large-bl, +.x-btn-default-toolbar-large-tr, +.x-btn-default-toolbar-large-br, +.x-btn-default-toolbar-large-tc, +.x-btn-default-toolbar-large-bc, +.x-btn-default-toolbar-large-ml, +.x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-corners.gif); +} +.x-btn-default-toolbar-large-ml, +.x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-toolbar-large-mc { + padding: 9px 9px 9px 9px; +} +.x-btn-default-toolbar-large { + border-color: #e4e4e4; +} +.x-btn-button-default-toolbar-large { + min-height: 24px; +} +.x-ie9m .x-btn-button-default-toolbar-large { + min-height: auto; + height: 24px; +} +.x-btn-inner-default-toolbar-large { + font: 500 16px/20px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #606060; + padding: 0 10px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-large { + max-width: calc(100% - 24px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-large { + max-width: calc(100% - 23px); +} +.x-ie10p .x-btn-inner-default-toolbar-large { + max-width: none; +} +.x-btn-icon-el-default-toolbar-large { + font-size: 24px; + height: 24px; + color: #919191; + line-height: 24px; +} +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + width: 24px; +} +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large { + min-width: 24px; +} +.x-ie8 .x-btn-icon-el-default-toolbar-large.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large { + margin-right: 0; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + margin-left: 0; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-large { + margin-right: 10px; +} +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-large, +.x-btn-split-bottom > .x-btn-button-default-toolbar-large { + padding-bottom: 9px; +} +.x-btn-wrap-default-toolbar-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; + padding-left: 9px; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom { + margin-bottom: -9px; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-large { + margin-right: 10px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-large { + background-image: none; + background-color: #f6f6f6; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-default-toolbar-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-toolbar-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-default-toolbar-large { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-large { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-toolbar-large, +.x-btn.x-btn-pressed.x-btn-default-toolbar-large { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-toolbar-large { + background-image: none; + background-color: #f6f6f6; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mc { + background-color: #f6f6f6; +} +.x-btn-over .x-btn-default-toolbar-large-tl, +.x-btn-over .x-btn-default-toolbar-large-bl, +.x-btn-over .x-btn-default-toolbar-large-tr, +.x-btn-over .x-btn-default-toolbar-large-br, +.x-btn-over .x-btn-default-toolbar-large-tc, +.x-btn-over .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-over-corners.gif); +} +.x-btn-over .x-btn-default-toolbar-large-ml, +.x-btn-over .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-over-sides.gif); +} +.x-btn-over .x-btn-default-toolbar-large-mc { + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mc { + background-color: #ececec; +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mc { + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mc { + background-color: #e2e2e2; +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-large { + background-image: none; +} +.x-btn-disabled.x-btn-default-toolbar-large { + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first + .x-btn-default-toolbar-large-mc { + padding-right: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle + .x-btn-default-toolbar-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last + .x-btn-default-toolbar-large-mc { + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first + .x-btn-default-toolbar-large-mc { + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle + .x-btn-default-toolbar-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last + .x-btn-default-toolbar-large-mc { + padding-top: 9px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-large:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-tool { + cursor: pointer; +} +.x-tool-tool-el { + overflow: hidden; + width: 16px; + height: 16px; + margin: 0; + color: #fff; + text-align: center; + opacity: 0.8; +} +.x-tool-over .x-tool-tool-el { + opacity: 1; +} +.x-tool-pressed .x-tool-tool-el { + opacity: 0.8; +} +.x-keyboard-mode .x-tool-focus { + outline: 1px solid #5aaed4; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-tool-focus, +.x-edge .x-keyboard-mode .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5aaed4; + pointer-events: none; +} +.x-tool-img { + background-image: url(images/tools/tool-sprites.png); +} +.x-tool-placeholder { + visibility: hidden; +} +.x-tool-close { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-close:before { + content: "\f00d"; +} +.x-tool-minimize { + font: 16px/1 ExtJS; + background: none; +} +.x-tool-minimize:before { + content: "\e608"; +} +.x-tool-maximize { + font: 16px/1 FontAwesome; + background: none; +} +.x-tool-maximize:before { + content: "\f065"; +} +.x-tool-restore { + font: 16px/1 FontAwesome; + background: none; +} +.x-tool-restore:before { + content: "\f066"; +} +.x-tool-toggle { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-toggle:before { + content: "\f077"; +} +.x-panel-collapsed .x-tool-toggle { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-panel-collapsed .x-tool-toggle:before { + content: "\f078"; +} +.x-tool-gear { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-gear:before { + content: "\f013"; +} +.x-tool-prev { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-prev:before { + content: "\f053"; +} +.x-tool-next { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-next:before { + content: "\f054"; +} +.x-tool-pin { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-pin:before { + content: "\f08d"; +} +.x-tool-unpin { + font: 16px/1 ExtJS; + background: none !important; +} +.x-tool-unpin:before { + content: "\e611"; +} +.x-tool-right { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-right:before { + content: "\f0da"; +} +.x-tool-left { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-left:before { + content: "\f0d9"; +} +.x-tool-down { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-down:before { + content: "\f0d7"; +} +.x-tool-up { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-up:before { + content: "\f0d8"; +} +.x-tool-refresh { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-refresh:before { + content: "\f021"; +} +.x-tool-plus { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-plus:before { + content: "\f067"; +} +.x-tool-minus { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-minus:before { + content: "\f068"; +} +.x-tool-search { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-search:before { + content: "\f002"; +} +.x-tool-save { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-save:before { + content: "\f00c"; +} +.x-tool-help { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-help:before { + content: "\f128"; +} +.x-tool-print { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-print:before { + content: "\f02f"; +} +.x-tool-expand { + font: 16px/1 ExtJS; + background: none !important; +} +.x-tool-expand:before { + content: "\e600"; +} +.x-tool-collapse { + font: 16px/1 ExtJS; + background: none !important; +} +.x-tool-collapse:before { + content: "\e606"; +} +.x-tool-resize { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-resize:before { + content: "\f07e"; +} +.x-tool-move { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-move:before { + content: "\f047"; +} +.x-tool-expand-bottom { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-expand-bottom:before { + content: "\f0d7"; +} +.x-tool-collapse-bottom { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-collapse-bottom:before { + content: "\f0d7"; +} +.x-tool-expand-top { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-expand-top:before { + content: "\f0d8"; +} +.x-tool-collapse-top { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-collapse-top:before { + content: "\f0d8"; +} +.x-tool-expand-left { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-expand-left:before { + content: "\f0d9"; +} +.x-tool-collapse-left { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-collapse-left:before { + content: "\f0d9"; +} +.x-tool-expand-right { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-expand-right:before { + content: "\f0da"; +} +.x-tool-collapse-right { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-collapse-right:before { + content: "\f0da"; +} +.x-header-draggable, +.x-header-ghost { + cursor: move; +} +.x-header-text { + white-space: nowrap; +} +.x-collapse-el { + cursor: pointer; + color: #919191; + display: table; + table-layout: fixed; + background-color: #e0e0e0; +} +.x-collapse-el:before { + display: table-cell; + vertical-align: middle; + text-align: center; +} +.x-layout-split-left { + font: 16px/1 FontAwesome; +} +.x-layout-split-left:before { + content: "\f0d9"; +} +.x-layout-split-right { + font: 16px/1 FontAwesome; + padding: 0 0 0 2px; +} +.x-layout-split-right:before { + content: "\f0da"; +} +.x-layout-split-top { + font: 16px/1 FontAwesome; + padding: 0 0 2px 0; +} +.x-layout-split-top:before { + content: "\f0d8"; +} +.x-layout-split-bottom { + font: 16px/1 FontAwesome; +} +.x-layout-split-bottom:before { + content: "\f0d7"; +} +.x-splitter-collapsed .x-layout-split-left { + font: 16px/1 FontAwesome; + padding: 0 0 0 2px; +} +.x-splitter-collapsed .x-layout-split-left:before { + content: "\f0da"; +} +.x-splitter-collapsed .x-layout-split-right { + font: 16px/1 FontAwesome; +} +.x-splitter-collapsed .x-layout-split-right:before { + content: "\f0d9"; +} +.x-splitter-collapsed .x-layout-split-top { + font: 16px/1 FontAwesome; +} +.x-splitter-collapsed .x-layout-split-top:before { + content: "\f0d7"; +} +.x-splitter-collapsed .x-layout-split-bottom { + font: 16px/1 FontAwesome; + padding: 0 0 2px 0; +} +.x-splitter-collapsed .x-layout-split-bottom:before { + content: "\f0d8"; +} +.x-splitter-active { + background-color: #b4b4b4; + opacity: 0.8; +} +.x-splitter-active .x-collapse-el { + opacity: 0.3; +} +.x-layout-split-left, +.x-layout-split-right { + top: 50%; + margin-top: -24px; + width: 100%; + height: 48px; +} +.x-layout-split-top, +.x-layout-split-bottom { + left: 50%; + width: 48px; + height: 100%; + margin-left: -24px; +} +.x-layout-split-top:before, +.x-layout-split-bottom:before { + width: 100%; + line-height: 10px; +} +.x-keyboard-mode .x-splitter-focus:after { + position: absolute; + content: " "; + top: 1px; + right: 1px; + bottom: 1px; + left: 1px; + border: 1px solid #2a95c5; + pointer-events: none; +} +.x-toolbar-default { + padding: 0px 30px 0px 0px; + border-style: solid; + border-color: #d0d0d0; + border-width: 1px; + background-image: none; + background-color: #fff; +} +.x-toolbar-default .x-tool-img { + color: #919191; + background-color: #fff; +} +.x-toolbar-default .x-toolbar-item { + margin: 0 8px 0 0; +} +.x-toolbar-default .x-toolbar-separator-horizontal { + margin: 0 8px 0 0; + height: 14px; + border-style: solid; + border-width: 0 0 0 1px; + border-left-color: #d0d0d0; + border-right-color: #fff; +} +.x-toolbar-default .x-box-menu-after { + margin: 0 8px; +} +.x-toolbar-default-vertical { + padding: 6px 8px 0; +} +.x-toolbar-default-vertical .x-toolbar-item { + margin: 0 0 6px 0; +} +.x-toolbar-default-vertical .x-toolbar-separator-vertical { + margin: 0 5px 6px; + border-style: solid none; + border-width: 1px 0 0; + border-top-color: #d0d0d0; + border-bottom-color: #fff; +} +.x-toolbar-default-vertical .x-box-menu-after { + margin: 6px 0; +} +.x-toolbar-text-default { + padding: 0 4px; + color: #464a4c; + font: 400 14px/16px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; +} +.x-toolbar-spacer-default { + width: 2px; +} +.x-toolbar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 24px; +} +.x-toolbar-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 26px; +} +.x-box-scroller-toolbar-default { + cursor: pointer; + color: #919191; + opacity: 0.6; +} +.x-box-scroller-toolbar-default.x-box-scroller-hover { + opacity: 0.8; +} +.x-box-scroller-toolbar-default.x-box-scroller-pressed { + opacity: 1; +} +.x-box-scroller-toolbar-default.x-box-scroller-disabled { + opacity: 0.25; + cursor: default; +} +.x-box-scroller-toolbar-default.x-box-scroller-left, +.x-box-scroller-toolbar-default.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +.x-box-scroller-toolbar-default.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-default.x-box-scroller-left:before { + content: "\f053"; +} +.x-box-scroller-toolbar-default.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-default.x-box-scroller-right:before { + content: "\f054"; +} +.x-box-scroller-toolbar-default.x-box-scroller-top, +.x-box-scroller-toolbar-default.x-box-scroller-bottom { + height: 24px; + width: 24px; + left: 50%; + margin-left: -12px; +} +.x-box-scroller-toolbar-default.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-default.x-box-scroller-top:before { + content: "\f077"; +} +.x-box-scroller-toolbar-default.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-default.x-box-scroller-bottom:before { + content: "\f078"; +} +.x-ie8 .x-box-scroller-toolbar-default { + background-color: #fff; +} +.x-toolbar-more-icon { + font: 16px/1 FontAwesome; + color: #919191; +} +.x-toolbar-more-icon:before { + content: "\f0c9"; +} +.x-toolbar-footer { + padding: 6px 0 6px 6px; + border-style: solid; + border-color: #d0d0d0; + border-width: 0; + background-image: none; + background-color: #ececec; +} +.x-toolbar-footer .x-tool-img { + color: #919191; + background-color: #ececec; +} +.x-toolbar-footer .x-toolbar-item { + margin: 0 6px 0 0; +} +.x-toolbar-footer .x-toolbar-separator-horizontal { + margin: 0 8px 0 0; + height: 14px; + border-style: solid; + border-width: 0 0 0 1px; + border-left-color: #d0d0d0; + border-right-color: #fff; +} +.x-toolbar-footer .x-box-menu-after { + margin: 0 6px; +} +.x-toolbar-footer-vertical { + padding: 6px 6px 0; +} +.x-toolbar-footer-vertical .x-toolbar-item { + margin: 0 0 6px 0; +} +.x-toolbar-footer-vertical .x-toolbar-separator-vertical { + margin: 0 5px 6px; + border-style: solid none; + border-width: 1px 0 0; + border-top-color: #d0d0d0; + border-bottom-color: #fff; +} +.x-toolbar-footer-vertical .x-box-menu-after { + margin: 6px 0; +} +.x-toolbar-text-footer { + padding: 0 4px; + color: #464a4c; + font: 400 14px/16px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; +} +.x-toolbar-spacer-footer { + width: 2px; +} +.x-toolbar-footer-scroller .x-box-scroller-body-horizontal { + margin-left: 26px; +} +.x-toolbar-footer-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 26px; +} +.x-box-scroller-toolbar-footer { + cursor: pointer; + color: #919191; + opacity: 0.6; +} +.x-box-scroller-toolbar-footer.x-box-scroller-hover { + opacity: 0.8; +} +.x-box-scroller-toolbar-footer.x-box-scroller-pressed { + opacity: 1; +} +.x-box-scroller-toolbar-footer.x-box-scroller-disabled { + opacity: 0.25; + cursor: default; +} +.x-box-scroller-toolbar-footer.x-box-scroller-left, +.x-box-scroller-toolbar-footer.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +.x-box-scroller-toolbar-footer.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-footer.x-box-scroller-left:before { + content: "\f053"; +} +.x-box-scroller-toolbar-footer.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-footer.x-box-scroller-right:before { + content: "\f054"; +} +.x-ie8 .x-box-scroller-toolbar-footer { + background-color: #ececec; +} +.x-toolbar-more-icon { + font: 16px/1 FontAwesome; + color: #919191; +} +.x-toolbar-more-icon:before { + content: "\f0c9"; +} +.x-dd-drag-proxy { + color: #404040; + font: 400 14px/17px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + border: 1px solid #d0d0d0; + background-color: #fff; +} +.x-dd-drag-ghost, +.x-dd-drop-icon { + padding: 5px; +} +.x-dd-drag-ghost { + padding-left: 0; +} +.x-dd-drop-ok .x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #a4cf6d; +} +.x-dd-drop-ok .x-dd-drop-icon:before { + content: "\f058"; +} +.x-dd-drop-ok-add .x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #a4cf6d; +} +.x-dd-drop-ok-add .x-dd-drop-icon:before { + content: "\f058"; +} +.x-dd-drop-nodrop div.x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #d9705d; +} +.x-dd-drop-nodrop div.x-dd-drop-icon:before { + content: "\f057"; +} +.x-panel-ghost { + opacity: 0.5; +} +.x-panel-default { + border-color: #5aaed4; + border-radius: 9px; + padding: 0; +} + +.x-panel-default.x-masked { + border-color: #9addfb; +} +.x-panel-header-default { + font-size: 16px; + border: 1px solid #5aaed4; +} +.x-panel-header-default .x-tool-tool-el { + background-color: #5aaed4; +} +.x-panel-header-default-horizontal { + padding: 11px 15px 12px; +} +.x-panel-header-default-horizontal .x-panel-header-default-tab-bar { + margin-top: -11px; + margin-bottom: -12px; +} +.x-panel-header-default-horizontal.x-header-noborder { + padding: 12px 16px 12px 16px; +} +.x-panel-header-default-horizontal.x-header-noborder + .x-panel-header-default-tab-bar { + margin-top: -12px; + margin-bottom: -12px; +} +.x-panel-header-default-vertical { + padding: 15px 11px 15px 12px; +} +.x-panel-header-default-vertical .x-panel-header-default-tab-bar { + margin-right: -11px; + margin-left: -12px; +} +.x-panel-header-default-vertical.x-header-noborder { + padding: 16px 12px 16px 12px; +} +.x-panel-header-default-vertical.x-header-noborder + .x-panel-header-default-tab-bar { + margin-right: -12px; + margin-left: -12px; +} +.x-panel-header-title-default { + color: #f0f0f0; + font-size: 16px; + font-weight: 500; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + line-height: 20px; +} +.x-keyboard-mode .x-panel-header-title-default.x-title-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-panel-header-title-default > .x-title-text-default { + text-transform: none; + padding: 0; +} +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +.x-panel-header-title-default + > .x-title-icon-wrap-default + > .x-title-icon-default { + width: 16px; + height: 16px; + font-size: 16px; + color: #f0f0f0; + background-position: center center; +} +.x-ie8 + .x-panel-header-title-default + > .x-title-icon-wrap-default + > .x-title-icon-default.x-title-glyph { + color: #f0f0f0; +} +.x-panel-body-default { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 14px; + font-weight: 400; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + border-width: 1px; + border-style: solid; +} +.x-panel-body-filter { + background: #fafafad6; + border-color: #d0d0d0; + color: #404040; + font-size: 14px; + font-weight: 400; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + border-width: 1px; + border-style: solid; +} +.x-panel-header-default { + background-image: none; + background-color: #5aaed4; +} +.x-panel-header-default-vertical { + background-image: none; + background-color: #5aaed4; +} +.x-panel .x-panel-header-default-collapsed-border-top { + border-bottom-width: 1px !important; +} +.x-panel .x-panel-header-default-collapsed-border-right { + border-left-width: 1px !important; +} +.x-panel .x-panel-header-default-collapsed-border-bottom { + border-top-width: 1px !important; +} +.x-panel .x-panel-header-default-collapsed-border-left { + border-right-width: 1px !important; +} +.x-panel-header-default-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-panel-header-default-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-panel-header-default-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +.x-panel-header-default-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +.x-keyboard-mode .x-panel-header-default .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-panel-default-resizable .x-panel-handle { + opacity: 0; +} +.x-panel-default-outer-border-l { + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-b { + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-panel-default-outer-border-bl { + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-r { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; +} +.x-panel-default-outer-border-rl { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-rb { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-panel-default-outer-border-rbl { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-t { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; +} +.x-panel-default-outer-border-tl { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-tb { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-panel-default-outer-border-tbl { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-tr { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; +} +.x-panel-default-outer-border-trl { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-trb { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-panel-default-outer-border-trbl { + border-color: #5aaed4 !important; + border-width: 1px !important; +} +.x-panel-default-framed { + border-color: #5aaed4; + padding: 0; +} +.x-panel-default-framed.x-masked { + border-color: #9addfb; +} +.x-panel-header-default-framed { + font-size: 16px; + border: 2px solid #5aaed4; +} +.x-panel-header-default-framed .x-tool-tool-el { + background-color: #5aaed4; +} +.x-panel-header-default-framed-horizontal { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-horizontal + .x-panel-header-default-framed-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +.x-panel-header-default-framed-horizontal.x-header-noborder { + padding: 12px 16px 10px 16px; +} +.x-panel-header-default-framed-horizontal.x-header-noborder + .x-panel-header-default-framed-tab-bar { + margin-top: -12px; + margin-bottom: -10px; +} +.x-panel-header-default-framed-vertical { + padding: 14px 10px 14px 10px; +} +.x-panel-header-default-framed-vertical .x-panel-header-default-framed-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +.x-panel-header-default-framed-vertical.x-header-noborder { + padding: 16px 12px 16px 10px; +} +.x-panel-header-default-framed-vertical.x-header-noborder + .x-panel-header-default-framed-tab-bar { + margin-right: -12px; + margin-left: -10px; +} +.x-panel-header-title-default-framed { + color: #f0f0f0; + font-size: 16px; + font-weight: 500; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + line-height: 20px; +} +.x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after, +.x-ie10p + .x-keyboard-mode + .x-panel-header-title-default-framed.x-title-focus:after, +.x-edge + .x-keyboard-mode + .x-panel-header-title-default-framed.x-title-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-panel-header-title-default-framed > .x-title-text-default-framed { + text-transform: none; + padding: 0; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed + > .x-title-icon-default-framed { + width: 16px; + height: 16px; + font-size: 16px; + color: #f0f0f0; + background-position: center center; +} +.x-ie8 + .x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed + > .x-title-icon-default-framed.x-title-glyph { + color: #f0f0f0; +} +.x-panel-body-default-framed { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 14px; + font-weight: 400; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + border-width: 1px; + border-style: solid; +} +.x-panel-default-framed { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 0 0 0 0; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-default-framed-mc { + background-color: #fff; +} +.x-nbr .x-panel-default-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-default-framed-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-0px-0px-0px-0px; +} +.x-panel-default-framed-tl { + background-position: 0 -4px; +} +.x-panel-default-framed-tr { + background-position: right -6px; +} +.x-panel-default-framed-bl { + background-position: 0 -8px; +} +.x-panel-default-framed-br { + background-position: right -10px; +} +.x-panel-default-framed-ml { + background-position: 0 top; +} +.x-panel-default-framed-mr { + background-position: right top; +} +.x-panel-default-framed-tc { + background-position: 0 0; +} +.x-panel-default-framed-bc { + background-position: 0 -2px; +} +.x-panel-default-framed-tr, +.x-panel-default-framed-br, +.x-panel-default-framed-mr { + padding-right: 2px; +} +.x-panel-default-framed-tl, +.x-panel-default-framed-bl, +.x-panel-default-framed-ml { + padding-left: 2px; +} +.x-panel-default-framed-tc { + height: 2px; +} +.x-panel-default-framed-bc { + height: 2px; +} +.x-panel-default-framed-tl, +.x-panel-default-framed-bl, +.x-panel-default-framed-tr, +.x-panel-default-framed-br, +.x-panel-default-framed-tc, +.x-panel-default-framed-bc, +.x-panel-default-framed-ml, +.x-panel-default-framed-mr { + background-image: url(images/panel/panel-default-framed-corners.gif); +} +.x-panel-default-framed-ml, +.x-panel-default-framed-mr { + background-image: url(images/panel/panel-default-framed-sides.gif); + background-repeat: repeat-y; +} +.x-panel-default-framed-mc { + padding: 0px 0px 0px 0px; +} +.x-panel-header-default-framed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 0 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-panel-header-default-framed-top-mc { + background-color: #5aaed4; +} +.x-nbr .x-panel-header-default-framed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-top-frameInfo { + font-family: dh-2-2-0-2-2-2-0-2-10-14-10-14; +} +.x-panel-header-default-framed-top-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-top-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-top-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-top-br { + background-position: right -10px; +} +.x-panel-header-default-framed-top-ml { + background-position: 0 top; +} +.x-panel-header-default-framed-top-mr { + background-position: right top; +} +.x-panel-header-default-framed-top-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-top-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-top-tr, +.x-panel-header-default-framed-top-br, +.x-panel-header-default-framed-top-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-top-tl, +.x-panel-header-default-framed-top-bl, +.x-panel-header-default-framed-top-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-top-tc { + height: 2px; +} +.x-panel-header-default-framed-top-bc { + height: 0; +} +.x-panel-header-default-framed-top-tl, +.x-panel-header-default-framed-top-bl, +.x-panel-header-default-framed-top-tr, +.x-panel-header-default-framed-top-br, +.x-panel-header-default-framed-top-tc, +.x-panel-header-default-framed-top-bc, +.x-panel-header-default-framed-top-ml, +.x-panel-header-default-framed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-top-corners.gif); +} +.x-panel-header-default-framed-top-ml, +.x-panel-header-default-framed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-top-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-top-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 0; + border-style: solid; + background-color: #5aaed4; +} +.x-panel-header-default-framed-right-mc { + background-color: #5aaed4; +} +.x-nbr .x-panel-header-default-framed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-right-frameInfo { + font-family: dh-2-2-2-0-2-2-2-0-14-10-14-10; +} +.x-panel-header-default-framed-right-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-right-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-right-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-right-br { + background-position: right -10px; +} +.x-panel-header-default-framed-right-ml { + background-position: right 0; +} +.x-panel-header-default-framed-right-mr { + background-position: right 0; +} +.x-panel-header-default-framed-right-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-right-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-right-tr, +.x-panel-header-default-framed-right-br, +.x-panel-header-default-framed-right-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-right-tl, +.x-panel-header-default-framed-right-bl, +.x-panel-header-default-framed-right-ml { + padding-left: 0; +} +.x-panel-header-default-framed-right-tc { + height: 2px; +} +.x-panel-header-default-framed-right-bc { + height: 2px; +} +.x-panel-header-default-framed-right-tl, +.x-panel-header-default-framed-right-bl, +.x-panel-header-default-framed-right-tr, +.x-panel-header-default-framed-right-br, +.x-panel-header-default-framed-right-tc, +.x-panel-header-default-framed-right-bc, +.x-panel-header-default-framed-right-ml, +.x-panel-header-default-framed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-right-corners.gif); +} +.x-panel-header-default-framed-right-ml, +.x-panel-header-default-framed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-right-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-right-mc { + padding: 14px 10px 14px 10px; +} +.x-panel-header-default-framed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 0 2px 2px 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-panel-header-default-framed-bottom-mc { + background-color: #5aaed4; +} +.x-nbr .x-panel-header-default-framed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-bottom-frameInfo { + font-family: dh-0-2-2-2-0-2-2-2-10-14-10-14; +} +.x-panel-header-default-framed-bottom-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-bottom-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-bottom-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-bottom-br { + background-position: right -10px; +} +.x-panel-header-default-framed-bottom-ml { + background-position: 0 bottom; +} +.x-panel-header-default-framed-bottom-mr { + background-position: right bottom; +} +.x-panel-header-default-framed-bottom-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-bottom-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-bottom-tr, +.x-panel-header-default-framed-bottom-br, +.x-panel-header-default-framed-bottom-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-bottom-tl, +.x-panel-header-default-framed-bottom-bl, +.x-panel-header-default-framed-bottom-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-bottom-tc { + height: 0; +} +.x-panel-header-default-framed-bottom-bc { + height: 2px; +} +.x-panel-header-default-framed-bottom-tl, +.x-panel-header-default-framed-bottom-bl, +.x-panel-header-default-framed-bottom-tr, +.x-panel-header-default-framed-bottom-br, +.x-panel-header-default-framed-bottom-tc, +.x-panel-header-default-framed-bottom-bc, +.x-panel-header-default-framed-bottom-ml, +.x-panel-header-default-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-bottom-corners.gif); +} +.x-panel-header-default-framed-bottom-ml, +.x-panel-header-default-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 0 2px 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-panel-header-default-framed-left-mc { + background-color: #5aaed4; +} +.x-nbr .x-panel-header-default-framed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-left-frameInfo { + font-family: dh-2-0-2-2-2-0-2-2-14-10-14-10; +} +.x-panel-header-default-framed-left-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-left-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-left-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-left-br { + background-position: right -10px; +} +.x-panel-header-default-framed-left-ml { + background-position: left 0; +} +.x-panel-header-default-framed-left-mr { + background-position: left 0; +} +.x-panel-header-default-framed-left-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-left-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-left-tr, +.x-panel-header-default-framed-left-br, +.x-panel-header-default-framed-left-mr { + padding-right: 0; +} +.x-panel-header-default-framed-left-tl, +.x-panel-header-default-framed-left-bl, +.x-panel-header-default-framed-left-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-left-tc { + height: 2px; +} +.x-panel-header-default-framed-left-bc { + height: 2px; +} +.x-panel-header-default-framed-left-tl, +.x-panel-header-default-framed-left-bl, +.x-panel-header-default-framed-left-tr, +.x-panel-header-default-framed-left-br, +.x-panel-header-default-framed-left-tc, +.x-panel-header-default-framed-left-bc, +.x-panel-header-default-framed-left-ml, +.x-panel-header-default-framed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-left-corners.gif); +} +.x-panel-header-default-framed-left-ml, +.x-panel-header-default-framed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-left-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-left-mc { + padding: 14px 10px 14px 10px; +} +.x-panel-header-default-framed-collapsed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-panel-header-default-framed-collapsed-top-mc { + background-color: #5aaed4; +} +.x-nbr .x-panel-header-default-framed-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-collapsed-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-panel-header-default-framed-collapsed-top-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-collapsed-top-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-collapsed-top-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-collapsed-top-br { + background-position: right -10px; +} +.x-panel-header-default-framed-collapsed-top-ml { + background-position: 0 top; +} +.x-panel-header-default-framed-collapsed-top-mr { + background-position: right top; +} +.x-panel-header-default-framed-collapsed-top-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-collapsed-top-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-collapsed-top-tr, +.x-panel-header-default-framed-collapsed-top-br, +.x-panel-header-default-framed-collapsed-top-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-collapsed-top-tl, +.x-panel-header-default-framed-collapsed-top-bl, +.x-panel-header-default-framed-collapsed-top-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-collapsed-top-tc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-top-bc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-top-tl, +.x-panel-header-default-framed-collapsed-top-bl, +.x-panel-header-default-framed-collapsed-top-tr, +.x-panel-header-default-framed-collapsed-top-br, +.x-panel-header-default-framed-collapsed-top-tc, +.x-panel-header-default-framed-collapsed-top-bc, +.x-panel-header-default-framed-collapsed-top-ml, +.x-panel-header-default-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-top-corners.gif); +} +.x-panel-header-default-framed-collapsed-top-ml, +.x-panel-header-default-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-collapsed-top-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-collapsed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-panel-header-default-framed-collapsed-right-mc { + background-color: #5aaed4; +} +.x-nbr .x-panel-header-default-framed-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-collapsed-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-panel-header-default-framed-collapsed-right-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-collapsed-right-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-collapsed-right-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-collapsed-right-br { + background-position: right -10px; +} +.x-panel-header-default-framed-collapsed-right-ml { + background-position: right 0; +} +.x-panel-header-default-framed-collapsed-right-mr { + background-position: right 0; +} +.x-panel-header-default-framed-collapsed-right-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-collapsed-right-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-collapsed-right-tr, +.x-panel-header-default-framed-collapsed-right-br, +.x-panel-header-default-framed-collapsed-right-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-collapsed-right-tl, +.x-panel-header-default-framed-collapsed-right-bl, +.x-panel-header-default-framed-collapsed-right-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-collapsed-right-tc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-right-bc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-right-tl, +.x-panel-header-default-framed-collapsed-right-bl, +.x-panel-header-default-framed-collapsed-right-tr, +.x-panel-header-default-framed-collapsed-right-br, +.x-panel-header-default-framed-collapsed-right-tc, +.x-panel-header-default-framed-collapsed-right-bc, +.x-panel-header-default-framed-collapsed-right-ml, +.x-panel-header-default-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-right-corners.gif); +} +.x-panel-header-default-framed-collapsed-right-ml, +.x-panel-header-default-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-collapsed-right-mc { + padding: 14px 10px 14px 10px; +} +.x-panel-header-default-framed-collapsed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-panel-header-default-framed-collapsed-bottom-mc { + background-color: #5aaed4; +} +.x-nbr .x-panel-header-default-framed-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-collapsed-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-panel-header-default-framed-collapsed-bottom-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-collapsed-bottom-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-collapsed-bottom-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-collapsed-bottom-br { + background-position: right -10px; +} +.x-panel-header-default-framed-collapsed-bottom-ml { + background-position: 0 bottom; +} +.x-panel-header-default-framed-collapsed-bottom-mr { + background-position: right bottom; +} +.x-panel-header-default-framed-collapsed-bottom-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-collapsed-bottom-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-collapsed-bottom-tr, +.x-panel-header-default-framed-collapsed-bottom-br, +.x-panel-header-default-framed-collapsed-bottom-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-collapsed-bottom-tl, +.x-panel-header-default-framed-collapsed-bottom-bl, +.x-panel-header-default-framed-collapsed-bottom-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-collapsed-bottom-tc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-bottom-bc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-bottom-tl, +.x-panel-header-default-framed-collapsed-bottom-bl, +.x-panel-header-default-framed-collapsed-bottom-tr, +.x-panel-header-default-framed-collapsed-bottom-br, +.x-panel-header-default-framed-collapsed-bottom-tc, +.x-panel-header-default-framed-collapsed-bottom-bc, +.x-panel-header-default-framed-collapsed-bottom-ml, +.x-panel-header-default-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif); +} +.x-panel-header-default-framed-collapsed-bottom-ml, +.x-panel-header-default-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-collapsed-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-collapsed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-panel-header-default-framed-collapsed-left-mc { + background-color: #5aaed4; +} +.x-nbr .x-panel-header-default-framed-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-collapsed-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-panel-header-default-framed-collapsed-left-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-collapsed-left-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-collapsed-left-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-collapsed-left-br { + background-position: right -10px; +} +.x-panel-header-default-framed-collapsed-left-ml { + background-position: left 0; +} +.x-panel-header-default-framed-collapsed-left-mr { + background-position: left 0; +} +.x-panel-header-default-framed-collapsed-left-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-collapsed-left-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-collapsed-left-tr, +.x-panel-header-default-framed-collapsed-left-br, +.x-panel-header-default-framed-collapsed-left-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-collapsed-left-tl, +.x-panel-header-default-framed-collapsed-left-bl, +.x-panel-header-default-framed-collapsed-left-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-collapsed-left-tc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-left-bc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-left-tl, +.x-panel-header-default-framed-collapsed-left-bl, +.x-panel-header-default-framed-collapsed-left-tr, +.x-panel-header-default-framed-collapsed-left-br, +.x-panel-header-default-framed-collapsed-left-tc, +.x-panel-header-default-framed-collapsed-left-bc, +.x-panel-header-default-framed-collapsed-left-ml, +.x-panel-header-default-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-left-corners.gif); +} +.x-panel-header-default-framed-collapsed-left-ml, +.x-panel-header-default-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-collapsed-left-mc { + padding: 14px 10px 14px 10px; +} +.x-panel .x-panel-header-default-framed-top { + border-bottom-width: 2px !important; +} +.x-panel .x-panel-header-default-framed-right { + border-left-width: 2px !important; +} +.x-panel .x-panel-header-default-framed-bottom { + border-top-width: 2px !important; +} +.x-panel .x-panel-header-default-framed-left { + border-right-width: 2px !important; +} +.x-nbr .x-panel-header-default-framed-collapsed-top { + border-bottom-width: 0 !important; +} +.x-nbr .x-panel-header-default-framed-collapsed-right { + border-left-width: 0 !important; +} +.x-nbr .x-panel-header-default-framed-collapsed-bottom { + border-top-width: 0 !important; +} +.x-nbr .x-panel-header-default-framed-collapsed-left { + border-right-width: 0 !important; +} +.x-panel-header-default-framed-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-panel-header-default-framed-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-panel-header-default-framed-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +.x-panel-header-default-framed-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +.x-keyboard-mode .x-panel-header-default-framed .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-panel-default-framed-resizable .x-panel-handle { + opacity: 0; +} +.x-panel-default-framed-outer-border-l { + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-b { + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-panel-default-framed-outer-border-bl { + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-r { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; +} +.x-panel-default-framed-outer-border-rl { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-rb { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-panel-default-framed-outer-border-rbl { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-t { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; +} +.x-panel-default-framed-outer-border-tl { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-tb { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-panel-default-framed-outer-border-tbl { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-tr { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; +} +.x-panel-default-framed-outer-border-trl { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-trb { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-panel-default-framed-outer-border-trbl { + border-color: #5aaed4 !important; + border-width: 1px !important; +} +.x-window-ghost { + opacity: 0.5; +} +.x-window-default { + border-color: #5aaed4; + -webkit-border-radius: 0 0 0 0; + -moz-border-radius: 0 0 0 0; + -ms-border-radius: 0 0 0 0; + -o-border-radius: 0 0 0 0; + border-radius: 0 0 0 0; +} +.x-window-default { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 0 0 0 0; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +.x-window-default-mc { + background-color: #fff; +} +.x-nbr .x-window-default { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-default-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-0px-0px-0px-0px; +} +.x-window-default-tl { + background-position: 0 -4px; +} +.x-window-default-tr { + background-position: right -6px; +} +.x-window-default-bl { + background-position: 0 -8px; +} +.x-window-default-br { + background-position: right -10px; +} +.x-window-default-ml { + background-position: 0 top; +} +.x-window-default-mr { + background-position: right top; +} +.x-window-default-tc { + background-position: 0 0; +} +.x-window-default-bc { + background-position: 0 -2px; +} +.x-window-default-tr, +.x-window-default-br, +.x-window-default-mr { + padding-right: 2px; +} +.x-window-default-tl, +.x-window-default-bl, +.x-window-default-ml { + padding-left: 2px; +} +.x-window-default-tc { + height: 2px; +} +.x-window-default-bc { + height: 2px; +} +.x-window-default-tl, +.x-window-default-bl, +.x-window-default-tr, +.x-window-default-br, +.x-window-default-tc, +.x-window-default-bc, +.x-window-default-ml, +.x-window-default-mr { + background-image: url(images/window/window-default-corners.gif); +} +.x-window-default-ml, +.x-window-default-mr { + background-image: url(images/window/window-default-sides.gif); + background-repeat: repeat-y; +} +.x-window-default-mc { + padding: 0px 0px 0px 0px; +} +.x-window-body-default { + border-color: #5aaed4; + border-width: 1px; + border-style: solid; + background: #fff; + color: #000; + font-size: 14px; + font-weight: 400; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; +} +.x-window-header-default { + font-size: 16px; + border-color: #5aaed4; + background-color: #5aaed4; +} +.x-window-header-default .x-tool-img { + background-color: #5aaed4; +} +.x-window-header-default-horizontal .x-window-header-default-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +.x-window-header-default-vertical .x-window-header-default-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +.x-window-header-title-default { + color: #f0f0f0; + font-size: 16px; + font-weight: 500; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + line-height: 20px; +} +.x-window-header-title-default > .x-title-text-default { + padding: 0; + text-transform: none; +} +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +.x-window-header-title-default + > .x-title-icon-wrap-default.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +.x-window-header-title-default + > .x-title-icon-wrap-default + > .x-title-icon-default { + width: 16px; + height: 16px; + font-size: 16px; + color: #f0f0f0; + background-position: center center; +} +.x-ie8 + .x-window-header-title-default + > .x-title-icon-wrap-default + > .x-title-icon-default.x-title-glyph { + color: #f0f0f0; +} +.x-window-header-default-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-window-header-default-top-mc { + background-color: #5aaed4; +} +.x-nbr .x-window-header-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-window-header-default-top-tl { + background-position: 0 -4px; +} +.x-window-header-default-top-tr { + background-position: right -6px; +} +.x-window-header-default-top-bl { + background-position: 0 -8px; +} +.x-window-header-default-top-br { + background-position: right -10px; +} +.x-window-header-default-top-ml { + background-position: 0 top; +} +.x-window-header-default-top-mr { + background-position: right top; +} +.x-window-header-default-top-tc { + background-position: 0 0; +} +.x-window-header-default-top-bc { + background-position: 0 -2px; +} +.x-window-header-default-top-tr, +.x-window-header-default-top-br, +.x-window-header-default-top-mr { + padding-right: 2px; +} +.x-window-header-default-top-tl, +.x-window-header-default-top-bl, +.x-window-header-default-top-ml { + padding-left: 2px; +} +.x-window-header-default-top-tc { + height: 2px; +} +.x-window-header-default-top-bc { + height: 2px; +} +.x-window-header-default-top-tl, +.x-window-header-default-top-bl, +.x-window-header-default-top-tr, +.x-window-header-default-top-br, +.x-window-header-default-top-tc, +.x-window-header-default-top-bc, +.x-window-header-default-top-ml, +.x-window-header-default-top-mr { + background-image: url(images/window-header/window-header-default-top-corners.gif); +} +.x-window-header-default-top-ml, +.x-window-header-default-top-mr { + background-image: url(images/window-header/window-header-default-top-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-top-mc { + padding: 10px 14px 10px 14px; +} +.x-window-header-default-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-window-header-default-right-mc { + background-color: #5aaed4; +} +.x-nbr .x-window-header-default-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-window-header-default-right-tl { + background-position: 0 -4px; +} +.x-window-header-default-right-tr { + background-position: right -6px; +} +.x-window-header-default-right-bl { + background-position: 0 -8px; +} +.x-window-header-default-right-br { + background-position: right -10px; +} +.x-window-header-default-right-ml { + background-position: 0 top; +} +.x-window-header-default-right-mr { + background-position: right top; +} +.x-window-header-default-right-tc { + background-position: 0 0; +} +.x-window-header-default-right-bc { + background-position: 0 -2px; +} +.x-window-header-default-right-tr, +.x-window-header-default-right-br, +.x-window-header-default-right-mr { + padding-right: 2px; +} +.x-window-header-default-right-tl, +.x-window-header-default-right-bl, +.x-window-header-default-right-ml { + padding-left: 2px; +} +.x-window-header-default-right-tc { + height: 2px; +} +.x-window-header-default-right-bc { + height: 2px; +} +.x-window-header-default-right-tl, +.x-window-header-default-right-bl, +.x-window-header-default-right-tr, +.x-window-header-default-right-br, +.x-window-header-default-right-tc, +.x-window-header-default-right-bc, +.x-window-header-default-right-ml, +.x-window-header-default-right-mr { + background-image: url(images/window-header/window-header-default-right-corners.gif); +} +.x-window-header-default-right-ml, +.x-window-header-default-right-mr { + background-image: url(images/window-header/window-header-default-right-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-right-mc { + padding: 14px 10px 14px 10px; +} +.x-window-header-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-window-header-default-bottom-mc { + background-color: #5aaed4; +} +.x-nbr .x-window-header-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-window-header-default-bottom-tl { + background-position: 0 -4px; +} +.x-window-header-default-bottom-tr { + background-position: right -6px; +} +.x-window-header-default-bottom-bl { + background-position: 0 -8px; +} +.x-window-header-default-bottom-br { + background-position: right -10px; +} +.x-window-header-default-bottom-ml { + background-position: 0 top; +} +.x-window-header-default-bottom-mr { + background-position: right top; +} +.x-window-header-default-bottom-tc { + background-position: 0 0; +} +.x-window-header-default-bottom-bc { + background-position: 0 -2px; +} +.x-window-header-default-bottom-tr, +.x-window-header-default-bottom-br, +.x-window-header-default-bottom-mr { + padding-right: 2px; +} +.x-window-header-default-bottom-tl, +.x-window-header-default-bottom-bl, +.x-window-header-default-bottom-ml { + padding-left: 2px; +} +.x-window-header-default-bottom-tc { + height: 2px; +} +.x-window-header-default-bottom-bc { + height: 2px; +} +.x-window-header-default-bottom-tl, +.x-window-header-default-bottom-bl, +.x-window-header-default-bottom-tr, +.x-window-header-default-bottom-br, +.x-window-header-default-bottom-tc, +.x-window-header-default-bottom-bc, +.x-window-header-default-bottom-ml, +.x-window-header-default-bottom-mr { + background-image: url(images/window-header/window-header-default-bottom-corners.gif); +} +.x-window-header-default-bottom-ml, +.x-window-header-default-bottom-mr { + background-image: url(images/window-header/window-header-default-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-window-header-default-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-window-header-default-left-mc { + background-color: #5aaed4; +} +.x-nbr .x-window-header-default-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-window-header-default-left-tl { + background-position: 0 -4px; +} +.x-window-header-default-left-tr { + background-position: right -6px; +} +.x-window-header-default-left-bl { + background-position: 0 -8px; +} +.x-window-header-default-left-br { + background-position: right -10px; +} +.x-window-header-default-left-ml { + background-position: 0 top; +} +.x-window-header-default-left-mr { + background-position: right top; +} +.x-window-header-default-left-tc { + background-position: 0 0; +} +.x-window-header-default-left-bc { + background-position: 0 -2px; +} +.x-window-header-default-left-tr, +.x-window-header-default-left-br, +.x-window-header-default-left-mr { + padding-right: 2px; +} +.x-window-header-default-left-tl, +.x-window-header-default-left-bl, +.x-window-header-default-left-ml { + padding-left: 2px; +} +.x-window-header-default-left-tc { + height: 2px; +} +.x-window-header-default-left-bc { + height: 2px; +} +.x-window-header-default-left-tl, +.x-window-header-default-left-bl, +.x-window-header-default-left-tr, +.x-window-header-default-left-br, +.x-window-header-default-left-tc, +.x-window-header-default-left-bc, +.x-window-header-default-left-ml, +.x-window-header-default-left-mr { + background-image: url(images/window-header/window-header-default-left-corners.gif); +} +.x-window-header-default-left-ml, +.x-window-header-default-left-mr { + background-image: url(images/window-header/window-header-default-left-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-left-mc { + padding: 14px 10px 14px 10px; +} +.x-window-header-default-collapsed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-window-header-default-collapsed-top-mc { + background-color: #5aaed4; +} +.x-nbr .x-window-header-default-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-collapsed-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-window-header-default-collapsed-top-tl { + background-position: 0 -4px; +} +.x-window-header-default-collapsed-top-tr { + background-position: right -6px; +} +.x-window-header-default-collapsed-top-bl { + background-position: 0 -8px; +} +.x-window-header-default-collapsed-top-br { + background-position: right -10px; +} +.x-window-header-default-collapsed-top-ml { + background-position: 0 top; +} +.x-window-header-default-collapsed-top-mr { + background-position: right top; +} +.x-window-header-default-collapsed-top-tc { + background-position: 0 0; +} +.x-window-header-default-collapsed-top-bc { + background-position: 0 -2px; +} +.x-window-header-default-collapsed-top-tr, +.x-window-header-default-collapsed-top-br, +.x-window-header-default-collapsed-top-mr { + padding-right: 2px; +} +.x-window-header-default-collapsed-top-tl, +.x-window-header-default-collapsed-top-bl, +.x-window-header-default-collapsed-top-ml { + padding-left: 2px; +} +.x-window-header-default-collapsed-top-tc { + height: 2px; +} +.x-window-header-default-collapsed-top-bc { + height: 2px; +} +.x-window-header-default-collapsed-top-tl, +.x-window-header-default-collapsed-top-bl, +.x-window-header-default-collapsed-top-tr, +.x-window-header-default-collapsed-top-br, +.x-window-header-default-collapsed-top-tc, +.x-window-header-default-collapsed-top-bc, +.x-window-header-default-collapsed-top-ml, +.x-window-header-default-collapsed-top-mr { + background-image: url(images/window-header/window-header-default-collapsed-top-corners.gif); +} +.x-window-header-default-collapsed-top-ml, +.x-window-header-default-collapsed-top-mr { + background-image: url(images/window-header/window-header-default-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-collapsed-top-mc { + padding: 10px 14px 10px 14px; +} +.x-window-header-default-collapsed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-window-header-default-collapsed-right-mc { + background-color: #5aaed4; +} +.x-nbr .x-window-header-default-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-collapsed-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-window-header-default-collapsed-right-tl { + background-position: 0 -4px; +} +.x-window-header-default-collapsed-right-tr { + background-position: right -6px; +} +.x-window-header-default-collapsed-right-bl { + background-position: 0 -8px; +} +.x-window-header-default-collapsed-right-br { + background-position: right -10px; +} +.x-window-header-default-collapsed-right-ml { + background-position: 0 top; +} +.x-window-header-default-collapsed-right-mr { + background-position: right top; +} +.x-window-header-default-collapsed-right-tc { + background-position: 0 0; +} +.x-window-header-default-collapsed-right-bc { + background-position: 0 -2px; +} +.x-window-header-default-collapsed-right-tr, +.x-window-header-default-collapsed-right-br, +.x-window-header-default-collapsed-right-mr { + padding-right: 2px; +} +.x-window-header-default-collapsed-right-tl, +.x-window-header-default-collapsed-right-bl, +.x-window-header-default-collapsed-right-ml { + padding-left: 2px; +} +.x-window-header-default-collapsed-right-tc { + height: 2px; +} +.x-window-header-default-collapsed-right-bc { + height: 2px; +} +.x-window-header-default-collapsed-right-tl, +.x-window-header-default-collapsed-right-bl, +.x-window-header-default-collapsed-right-tr, +.x-window-header-default-collapsed-right-br, +.x-window-header-default-collapsed-right-tc, +.x-window-header-default-collapsed-right-bc, +.x-window-header-default-collapsed-right-ml, +.x-window-header-default-collapsed-right-mr { + background-image: url(images/window-header/window-header-default-collapsed-right-corners.gif); +} +.x-window-header-default-collapsed-right-ml, +.x-window-header-default-collapsed-right-mr { + background-image: url(images/window-header/window-header-default-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-collapsed-right-mc { + padding: 14px 10px 14px 10px; +} +.x-window-header-default-collapsed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-window-header-default-collapsed-bottom-mc { + background-color: #5aaed4; +} +.x-nbr .x-window-header-default-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-collapsed-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-window-header-default-collapsed-bottom-tl { + background-position: 0 -4px; +} +.x-window-header-default-collapsed-bottom-tr { + background-position: right -6px; +} +.x-window-header-default-collapsed-bottom-bl { + background-position: 0 -8px; +} +.x-window-header-default-collapsed-bottom-br { + background-position: right -10px; +} +.x-window-header-default-collapsed-bottom-ml { + background-position: 0 top; +} +.x-window-header-default-collapsed-bottom-mr { + background-position: right top; +} +.x-window-header-default-collapsed-bottom-tc { + background-position: 0 0; +} +.x-window-header-default-collapsed-bottom-bc { + background-position: 0 -2px; +} +.x-window-header-default-collapsed-bottom-tr, +.x-window-header-default-collapsed-bottom-br, +.x-window-header-default-collapsed-bottom-mr { + padding-right: 2px; +} +.x-window-header-default-collapsed-bottom-tl, +.x-window-header-default-collapsed-bottom-bl, +.x-window-header-default-collapsed-bottom-ml { + padding-left: 2px; +} +.x-window-header-default-collapsed-bottom-tc { + height: 2px; +} +.x-window-header-default-collapsed-bottom-bc { + height: 2px; +} +.x-window-header-default-collapsed-bottom-tl, +.x-window-header-default-collapsed-bottom-bl, +.x-window-header-default-collapsed-bottom-tr, +.x-window-header-default-collapsed-bottom-br, +.x-window-header-default-collapsed-bottom-tc, +.x-window-header-default-collapsed-bottom-bc, +.x-window-header-default-collapsed-bottom-ml, +.x-window-header-default-collapsed-bottom-mr { + background-image: url(images/window-header/window-header-default-collapsed-bottom-corners.gif); +} +.x-window-header-default-collapsed-bottom-ml, +.x-window-header-default-collapsed-bottom-mr { + background-image: url(images/window-header/window-header-default-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-collapsed-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-window-header-default-collapsed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5aaed4; +} +.x-window-header-default-collapsed-left-mc { + background-color: #5aaed4; +} +.x-nbr .x-window-header-default-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-collapsed-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-window-header-default-collapsed-left-tl { + background-position: 0 -4px; +} +.x-window-header-default-collapsed-left-tr { + background-position: right -6px; +} +.x-window-header-default-collapsed-left-bl { + background-position: 0 -8px; +} +.x-window-header-default-collapsed-left-br { + background-position: right -10px; +} +.x-window-header-default-collapsed-left-ml { + background-position: 0 top; +} +.x-window-header-default-collapsed-left-mr { + background-position: right top; +} +.x-window-header-default-collapsed-left-tc { + background-position: 0 0; +} +.x-window-header-default-collapsed-left-bc { + background-position: 0 -2px; +} +.x-window-header-default-collapsed-left-tr, +.x-window-header-default-collapsed-left-br, +.x-window-header-default-collapsed-left-mr { + padding-right: 2px; +} +.x-window-header-default-collapsed-left-tl, +.x-window-header-default-collapsed-left-bl, +.x-window-header-default-collapsed-left-ml { + padding-left: 2px; +} +.x-window-header-default-collapsed-left-tc { + height: 2px; +} +.x-window-header-default-collapsed-left-bc { + height: 2px; +} +.x-window-header-default-collapsed-left-tl, +.x-window-header-default-collapsed-left-bl, +.x-window-header-default-collapsed-left-tr, +.x-window-header-default-collapsed-left-br, +.x-window-header-default-collapsed-left-tc, +.x-window-header-default-collapsed-left-bc, +.x-window-header-default-collapsed-left-ml, +.x-window-header-default-collapsed-left-mr { + background-image: url(images/window-header/window-header-default-collapsed-left-corners.gif); +} +.x-window-header-default-collapsed-left-ml, +.x-window-header-default-collapsed-left-mr { + background-image: url(images/window-header/window-header-default-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-collapsed-left-mc { + padding: 14px 10px 14px 10px; +} +.x-window-header-default .x-window-header-icon { + width: 16px; + height: 16px; + color: #f0f0f0; + font-size: 16px; + line-height: 16px; + background-position: center center; +} +.x-window-header-default .x-window-header-glyph { + color: #f0f0f0; + font-size: 16px; + line-height: 16px; +} +.x-ie8 .x-window-header-default .x-window-header-glyph { + color: #f0f0f0; +} +.x-window-header-default-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-window-header-default-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-window-header-default-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +.x-window-header-default-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +.x-keyboard-mode .x-window-header-default .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus, +.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-window-header-default { + border-width: 2px !important; +} +.x-nbr .x-window-default-collapsed .x-window-header { + border-width: 0 !important; +} +.x-window-default-outer-border-l { + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-b { + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-window-default-outer-border-bl { + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-r { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; +} +.x-window-default-outer-border-rl { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-rb { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-window-default-outer-border-rbl { + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-t { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; +} +.x-window-default-outer-border-tl { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-tb { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-window-default-outer-border-tbl { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-tr { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; +} +.x-window-default-outer-border-trl { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-left-color: #5aaed4 !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-trb { + border-top-color: #5aaed4 !important; + border-top-width: 1px !important; + border-right-color: #5aaed4 !important; + border-right-width: 1px !important; + border-bottom-color: #5aaed4 !important; + border-bottom-width: 1px !important; +} +.x-window-default-outer-border-trbl { + border-color: #5aaed4 !important; + border-width: 1px !important; +} +.x-window-body-plain { + background-color: transparent; +} +.x-form-item-label-default { + color: #404040; + font: 400 14px/17px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + min-height: 32px; + padding-top: 8px; + padding-right: 5px; +} +.x-ie8 .x-form-item-label-default { + min-height: 24px; +} +.x-form-item-label-default.x-form-item-label-top { + height: 1px; +} +.x-form-item-label-default.x-form-item-label-top > .x-form-item-label-inner { + padding-top: 8px; + padding-bottom: 5px; +} +.x-form-item-label-default.x-form-item-label-top-side-error:after { + width: 26px; +} +.x-form-item-body-default { + min-height: 32px; +} +.x-form-invalid-icon-default { + width: 16px; + height: 16px; + margin: 0 5px; + background: url(images/form/exclamation.png) no-repeat; +} +.x-form-invalid-under-default { + padding: 2px 2px 2px 20px; + color: #cf4c35; + font: 400 14px/16px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + background: no-repeat 0 2px; + background-image: url(images/form/exclamation.png); +} +.x-form-error-wrap-default.x-form-error-wrap-side { + width: 26px; +} +.x-form-item-default.x-item-disabled { + opacity: 0.3; +} +.x-autocontainer-form-item, +.x-anchor-form-item, +.x-vbox-form-item, +.x-table-form-item { + margin-bottom: 10px; +} +.x-form-text-field-body-default { + min-width: 170px; + max-width: 170px; +} +.x-form-trigger-wrap-default { + border-width: 1px; + border-style: solid; + border-color: #d0d0d0; +} +.x-form-trigger-wrap-default.x-form-trigger-wrap-focus { + border-color: #53c4f7; +} +.x-form-trigger-wrap-default.x-form-trigger-wrap-invalid { + border-color: #cf4c35; +} +.x-form-text-default { + color: #404040; + padding: 5px 10px 4px; + background-color: #fff; + font: 400 14px/21px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + min-height: 30px; +} +.x-ie8 .x-form-text-default { + min-height: 21px; +} +.x-form-text-default.x-form-textarea { + line-height: 20px; + min-height: 45px; +} +.x-ie8 .x-form-text-default.x-form-textarea { + min-height: 71px; +} +.x-form-text-message.x-form-textarea { + line-height: 20px; + min-height: 45px; + border-radius: 21px; + background-color: #fff; + color: #404040; + font: 400 14px/21px "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + padding: 10px; +} +.x-ie8 .x-form-text-message.x-form-textarea { + min-height: 71px; +} +.x-form-text-default.x-form-text-file { + color: grey; +} +.x-form-text-default.x-webkit-border-box-bug { + height: calc(100% + 9px); +} +.x-placeholder-label-default { + padding: 5px 10px 4px; +} +.x-form-empty-field-default + .x-placeholder-label-default { + color: grey; +} +.x-form-text-default:-ms-input-placeholder { + color: grey; +} +.x-form-invalid-field-default { + background-color: #fff; +} +.x-form-trigger-default { + width: 32px; + font: 16px/30px FontAwesome; + background: #fff; + color: #919191; +} +.x-form-trigger-default:before { + content: "\f0d7"; +} +.x-form-trigger-default.x-form-trigger-over { + background-position: -32px center; +} +.x-form-trigger-default.x-form-trigger-over.x-form-trigger-focus { + background-position: -128px center; +} +.x-form-trigger-default.x-form-trigger-focus { + background-position: -96px center; +} +.x-form-trigger.x-form-trigger-default.x-form-trigger-click { + background-position: -64px center; +} +.x-form-clear-trigger { + font-size: 16px; + font-family: FontAwesome; +} +.x-form-clear-trigger:before { + content: "\f00d"; +} +.x-form-search-trigger { + font-size: 16px; + font-family: FontAwesome; +} +.x-form-search-trigger:before { + content: "\f002"; +} +.x-message-box .x-window-body { + background-color: #fff; + border-width: 0; +} +.x-message-box-info, +.x-message-box-warning, +.x-message-box-question, +.x-message-box-error { + background-position: left top; + background-repeat: no-repeat; +} +.x-message-box-icon { + height: 44px; + width: 44px; + margin-right: 10px; +} +.x-message-box-info { + font: 44px/1 FontAwesome; + color: grey; +} +.x-message-box-info:before { + content: "\f05a"; +} +.x-message-box-warning { + font: 44px/1 FontAwesome; + color: #f8d400; +} +.x-message-box-warning:before { + content: "\f071"; +} +.x-message-box-question { + font: 44px/1 FontAwesome; + color: grey; +} +.x-message-box-question:before { + content: "\f059"; +} +.x-message-box-error { + font: 44px/1 FontAwesome; + color: #ee611f; +} +.x-message-box-error:before { + content: "\f057"; +} +.x-form-cb-wrap-default { + height: 32px; + min-width: 18px; +} +.x-form-cb-default { + margin-top: 7px; +} +.x-form-checkbox-default, +.x-form-radio-default { + width: 18px; + height: 18px; +} +.x-form-radio-default { + font: 18px/1 FontAwesome; + color: #919191; +} +.x-form-radio-default:before { + content: "\f10c"; +} +.x-form-cb-checked .x-form-radio-default { + font: 18px/1 FontAwesome; +} +.x-form-cb-checked .x-form-radio-default:before { + content: "\f192"; +} +.x-form-checkbox-default { + font: 18px/1 ExtJS; + color: #919191; +} +.x-form-checkbox-default:before { + content: "\e614"; +} +.x-form-cb-checked .x-form-checkbox-default { + font: 18px/1 ExtJS; +} +.x-form-cb-checked .x-form-checkbox-default:before { + content: "\e613"; +} +.x-keyboard-mode .x-form-checkbox-focus.x-form-radio-default { + color: #53c4f7; +} +.x-keyboard-mode .x-form-checkbox-focus.x-form-checkbox-default { + color: #53c4f7; +} +.x-keyboard-mode + .x-form-cb-checked + .x-form-checkbox-focus.x-form-radio-default { + color: #53c4f7; +} +.x-keyboard-mode + .x-form-cb-checked + .x-form-checkbox-focus.x-form-checkbox-default { + color: #53c4f7; +} +.x-form-cb-label-default { + margin-top: 8px; + font: 400 14px/17px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #404040; +} +.x-form-cb-label-default.x-form-cb-label-before { + padding-right: 22px; +} +.x-form-cb-label-default.x-form-cb-label-after { + padding-left: 22px; +} +.x-form-trigger-spinner-default { + width: 32px; +} +.x-form-trigger-spinner-default:before { + content: ""; +} +.x-form-spinner-default { + background-color: #fff; + width: 32px; + height: 15px; + color: #919191; +} +.x-form-spinner-up-default { + font: 16px/1 ExtJS; +} +.x-form-spinner-up-default:before { + content: "\e61c"; +} +.x-form-spinner-down-default { + font: 16px/1 ExtJS; +} +.x-form-spinner-down-default:before { + content: "\e61b"; +} +.x-form-spinner-up-default { + background-position: 0 0; +} +.x-form-spinner-up-default.x-form-spinner-over { + background-position: -32px 0; +} +.x-form-spinner-up-default.x-form-spinner-over.x-form-spinner-focus { + background-position: -128px 0; +} +.x-form-spinner-up-default.x-form-spinner-focus { + background-position: -96px 0; +} +.x-form-spinner-up-default.x-form-spinner.x-form-spinner-click { + background-position: -64px 0; +} +.x-form-spinner-down-default { + background-position: 0 -15px; +} +.x-form-spinner-down-default.x-form-spinner-over { + background-position: -32px -15px; +} +.x-form-spinner-down-default.x-form-spinner-over.x-form-spinner-focus { + background-position: -128px -15px; +} +.x-form-spinner-down-default.x-form-spinner-focus { + background-position: -96px -15px; +} +.x-form-spinner-down-default.x-form-spinner.x-form-spinner-click { + background-position: -64px -15px; +} +.x-tbar-page-number { + width: 30px; +} +.x-btn-icon-el.x-tbar-page-first { + font: 16px/16px ExtJS; + color: #919191; +} +.x-btn-icon-el.x-tbar-page-first:before { + content: "\e617"; +} +.x-btn-icon-el.x-tbar-page-prev { + font: 16px/16px ExtJS; + color: #919191; +} +.x-btn-icon-el.x-tbar-page-prev:before { + content: "\e615"; +} +.x-btn-icon-el.x-tbar-page-next { + font: 16px/16px ExtJS; + color: #919191; +} +.x-btn-icon-el.x-tbar-page-next:before { + content: "\e616"; +} +.x-btn-icon-el.x-tbar-page-last { + font: 16px/16px ExtJS; + color: #919191; +} +.x-btn-icon-el.x-tbar-page-last:before { + content: "\e618"; +} +.x-btn-icon-el.x-tbar-loading { + font: 16px/16px FontAwesome; + color: #919191; +} +.x-btn-icon-el.x-tbar-loading:before { + content: "\f021"; +} +.x-form-display-field-default { + min-height: 32px; + font: 400 14px/17px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #404040; + margin-top: 8px; +} +.x-keyboard-mode .x-form-display-field-default.x-field-form-focus { + outline: 1px solid #53c4f7; + outline-offset: -1px; +} +.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus, +.x-ie10p .x-keyboard-mode .x-form-display-field-default.x-field-form-focus, +.x-edge .x-keyboard-mode .x-form-display-field-default.x-field-form-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after, +.x-ie10p + .x-keyboard-mode + .x-form-display-field-default.x-field-form-focus:after, +.x-edge + .x-keyboard-mode + .x-form-display-field-default.x-field-form-focus:after { + position: absolute; + content: " "; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + border: 1px solid #53c4f7; + pointer-events: none; +} +.x-ie8 .x-form-display-field-default.x-field-form-focus { + position: relative; +} +.x-tip-default { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #747474; +} +.x-tip-default-mc { + background-color: #747474; +} +.x-nbr .x-tip-default { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tip-default-frameInfo { + font-family: th-2-2-2-2-1-1-1-1-1-1-1-1; +} +.x-tip-default-tl { + background-position: 0 -4px; +} +.x-tip-default-tr { + background-position: right -6px; +} +.x-tip-default-bl { + background-position: 0 -8px; +} +.x-tip-default-br { + background-position: right -10px; +} +.x-tip-default-ml { + background-position: 0 top; +} +.x-tip-default-mr { + background-position: right top; +} +.x-tip-default-tc { + background-position: 0 0; +} +.x-tip-default-bc { + background-position: 0 -2px; +} +.x-tip-default-tr, +.x-tip-default-br, +.x-tip-default-mr { + padding-right: 2px; +} +.x-tip-default-tl, +.x-tip-default-bl, +.x-tip-default-ml { + padding-left: 2px; +} +.x-tip-default-tc { + height: 2px; +} +.x-tip-default-bc { + height: 2px; +} +.x-tip-default-tl, +.x-tip-default-bl, +.x-tip-default-tr, +.x-tip-default-br, +.x-tip-default-tc, +.x-tip-default-bc, +.x-tip-default-ml, +.x-tip-default-mr { + background-image: url(images/tip/tip-default-corners.gif); +} +.x-tip-default-ml, +.x-tip-default-mr { + background-image: url(images/tip/tip-default-sides.gif); + background-repeat: repeat-y; +} +.x-tip-default-mc { + padding: 0px 0px 0px 0px; +} +.x-tip-default { + background-color: #747474; + border-color: #747474; +} +.x-tip-default .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #747474; +} +.x-tip-header-default .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-tip-header-default .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-tip-header-default { + padding: 3px 3px 0 3px; +} +.x-tip-header-title-default { + color: #f0f0f0; + font-size: 14px; + font-weight: bold; +} +.x-tip-body-default { + padding: 6px 8px; + color: #f0f0f0; + font-size: 14px; + font-weight: 400; +} +.x-tip-body-default a { + color: #f0f0f0; +} +.x-tip-default .x-tip-anchor { + border: 10px solid transparent; + _border-color: pink; + _filter: chroma(color=pink); +} +.x-tip-default .x-tip-anchor-top { + border-top-width: 0; + border-bottom: 10px solid #747474; + top: -10px; +} +.x-tip-default .x-tip-anchor-bottom { + border-bottom-width: 0; + border-top: 10px solid #747474; + bottom: -10px; +} +.x-tip-default .x-tip-anchor-left { + border-left-width: 0; + border-right: 10px solid #747474; + left: -10px; +} +.x-tip-default .x-tip-anchor-right { + border-right-width: 0; + border-left: 10px solid #747474; + right: -10px; +} +.x-tip-form-invalid { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #747474; +} +.x-tip-form-invalid-mc { + background-color: #747474; +} +.x-nbr .x-tip-form-invalid { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tip-form-invalid-frameInfo { + font-family: th-2-2-2-2-1-1-1-1-1-1-1-1; +} +.x-tip-form-invalid-tl { + background-position: 0 -4px; +} +.x-tip-form-invalid-tr { + background-position: right -6px; +} +.x-tip-form-invalid-bl { + background-position: 0 -8px; +} +.x-tip-form-invalid-br { + background-position: right -10px; +} +.x-tip-form-invalid-ml { + background-position: 0 top; +} +.x-tip-form-invalid-mr { + background-position: right top; +} +.x-tip-form-invalid-tc { + background-position: 0 0; +} +.x-tip-form-invalid-bc { + background-position: 0 -2px; +} +.x-tip-form-invalid-tr, +.x-tip-form-invalid-br, +.x-tip-form-invalid-mr { + padding-right: 2px; +} +.x-tip-form-invalid-tl, +.x-tip-form-invalid-bl, +.x-tip-form-invalid-ml { + padding-left: 2px; +} +.x-tip-form-invalid-tc { + height: 2px; +} +.x-tip-form-invalid-bc { + height: 2px; +} +.x-tip-form-invalid-tl, +.x-tip-form-invalid-bl, +.x-tip-form-invalid-tr, +.x-tip-form-invalid-br, +.x-tip-form-invalid-tc, +.x-tip-form-invalid-bc, +.x-tip-form-invalid-ml, +.x-tip-form-invalid-mr { + background-image: url(images/tip/tip-form-invalid-corners.gif); +} +.x-tip-form-invalid-ml, +.x-tip-form-invalid-mr { + background-image: url(images/tip/tip-form-invalid-sides.gif); + background-repeat: repeat-y; +} +.x-tip-form-invalid-mc { + padding: 0px 0px 0px 0px; +} +.x-tip-form-invalid { + background-color: #747474; + border-color: #747474; +} +.x-tip-form-invalid .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #747474; +} +.x-tip-header-form-invalid .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-tip-header-form-invalid .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-tip-header-form-invalid { + padding: 3px 3px 0 3px; +} +.x-tip-header-title-form-invalid { + color: #f0f0f0; + font-size: 14px; + font-weight: bold; +} +.x-tip-body-form-invalid { + padding: 3px 3px 3px 22px; + color: #f0f0f0; + font-size: 14px; + font-weight: 400; +} +.x-tip-body-form-invalid a { + color: #f0f0f0; +} +.x-tip-form-invalid .x-tip-anchor { + border: 10px solid transparent; + _border-color: pink; + _filter: chroma(color=pink); +} +.x-tip-form-invalid .x-tip-anchor-top { + border-top-width: 0; + border-bottom: 10px solid #747474; + top: -10px; +} +.x-tip-form-invalid .x-tip-anchor-bottom { + border-bottom-width: 0; + border-top: 10px solid #747474; + bottom: -10px; +} +.x-tip-form-invalid .x-tip-anchor-left { + border-left-width: 0; + border-right: 10px solid #747474; + left: -10px; +} +.x-tip-form-invalid .x-tip-anchor-right { + border-right-width: 0; + border-left: 10px solid #747474; + right: -10px; +} +.x-tip-body-form-invalid { + background: 1px 1px no-repeat; + background-image: url(images/form/exclamation.png); +} +.x-tip-body-form-invalid li { + margin-bottom: 4px; +} +.x-tip-body-form-invalid li.last { + margin-bottom: 0; +} +.x-color-picker { + width: 192px; + height: 120px; + background-color: #fff; + border-color: #fff; + border-width: 0; + border-style: solid; +} +.x-color-picker-item { + width: 24px; + height: 24px; + border-width: 1px; + border-color: #fff; + border-style: solid; + background-color: #fff; + cursor: pointer; + padding: 2px; +} +a.x-color-picker-item:hover { + border-color: #8bb8f3; + background-color: #d9d9d9; +} +.x-color-picker-selected { + border-color: #8bb8f3; + background-color: #d9d9d9; +} +.x-color-picker-item-inner { + line-height: 16px; + border-color: #d0d0d0; + border-width: 1px; + border-style: solid; +} +.x-html-editor-tb .x-btn-icon-el { + color: #919191; +} +.x-html-editor-tb .x-edit-bold, +.x-menu-item div.x-edit-bold { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-bold:before, +.x-menu-item div.x-edit-bold:before { + content: "\f032"; +} +.x-html-editor-tb .x-edit-italic, +.x-menu-item div.x-edit-italic { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-italic:before, +.x-menu-item div.x-edit-italic:before { + content: "\f033"; +} +.x-html-editor-tb .x-edit-underline, +.x-menu-item div.x-edit-underline { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-underline:before, +.x-menu-item div.x-edit-underline:before { + content: "\f0cd"; +} +.x-html-editor-tb .x-edit-forecolor, +.x-menu-item div.x-edit-forecolor { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-forecolor:before, +.x-menu-item div.x-edit-forecolor:before { + content: "\e60e"; +} +.x-html-editor-tb .x-edit-backcolor, +.x-menu-item div.x-edit-backcolor { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-backcolor:before, +.x-menu-item div.x-edit-backcolor:before { + content: "\e60d"; +} +.x-html-editor-tb .x-edit-justifyleft, +.x-menu-item div.x-edit-justifyleft { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-justifyleft:before, +.x-menu-item div.x-edit-justifyleft:before { + content: "\f036"; +} +.x-html-editor-tb .x-edit-justifycenter, +.x-menu-item div.x-edit-justifycenter { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-justifycenter:before, +.x-menu-item div.x-edit-justifycenter:before { + content: "\f037"; +} +.x-html-editor-tb .x-edit-justifyright, +.x-menu-item div.x-edit-justifyright { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-justifyright:before, +.x-menu-item div.x-edit-justifyright:before { + content: "\f038"; +} +.x-html-editor-tb .x-edit-insertorderedlist, +.x-menu-item div.x-edit-insertorderedlist { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-insertorderedlist:before, +.x-menu-item div.x-edit-insertorderedlist:before { + content: "\f0cb"; +} +.x-html-editor-tb .x-edit-insertunorderedlist, +.x-menu-item div.x-edit-insertunorderedlist { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-insertunorderedlist:before, +.x-menu-item div.x-edit-insertunorderedlist:before { + content: "\f0ca"; +} +.x-html-editor-tb .x-edit-increasefontsize, +.x-menu-item div.x-edit-increasefontsize { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-increasefontsize:before, +.x-menu-item div.x-edit-increasefontsize:before { + content: "\e610"; +} +.x-html-editor-tb .x-edit-decreasefontsize, +.x-menu-item div.x-edit-decreasefontsize { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-decreasefontsize:before, +.x-menu-item div.x-edit-decreasefontsize:before { + content: "\e60f"; +} +.x-html-editor-tb .x-edit-sourceedit, +.x-menu-item div.x-edit-sourceedit { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-sourceedit:before, +.x-menu-item div.x-edit-sourceedit:before { + content: "\e604"; +} +.x-html-editor-tb .x-edit-createlink, +.x-menu-item div.x-edit-createlink { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-createlink:before, +.x-menu-item div.x-edit-createlink:before { + content: "\f0c1"; +} +.x-html-editor-tip .x-tip-bd .x-tip-bd-inner { + padding: 5px; + padding-bottom: 1px; +} +.x-html-editor-tb .x-font-select { + font-size: 14px; + font-family: inherit; +} +.x-html-editor-wrap textarea { + font: 400 14px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + background-color: #fff; + resize: none; +} +.x-htmleditor-iframe { + background-color: #fff; +} +.x-grid-view, +.x-tree-view { + z-index: 1; +} +.x-theme-row-height-el { + height: 32px; +} +.x-grid-body { + background: #fff; + border-width: 2px 1px 1px; + border-style: solid; + border-color: #d0d0d0; +} +.x-grid-empty { + padding: 10px; + color: grey; + background-color: #fff; + font: 400 14px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; +} +.x-grid-item { + color: #404040; + font: 400 14px/19px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + background-color: #fff; +} +.x-grid-item-alt { + background-color: #f6f6f6; +} +.x-grid-item-over { + color: #404040; + background-color: #e6f1f6; +} +.x-grid-item-focused { + outline: 0; +} +.x-grid-item-focused .x-grid-cell-inner { + z-index: 1; +} +.x-keyboard-mode .x-grid-item-focused { + color: #404040; +} +.x-keyboard-mode .x-grid-item-focused .x-grid-cell-inner:before { + content: ""; + position: absolute; + z-index: -1; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + pointer-events: none; + border: 1px solid #5aaed4; +} +.x-grid-item-selected { + color: #404040; + background-color: #ffefbb; +} +.x-grid-with-row-lines .x-grid-item { + border-style: solid; + border-width: 1px 0 0; + border-color: #e9e9e9; +} +.x-grid-with-row-lines .x-grid-item:first-child { + border-top-color: #fff; +} +.x-grid-with-row-lines .x-grid-item.x-grid-item-over { + border-style: solid; + border-color: #dbe5ea; +} +.x-grid-with-row-lines .x-grid-item-over + .x-grid-item { + border-top-style: solid; + border-top-color: #dbe5ea; +} +.x-grid-with-row-lines .x-grid-item.x-grid-item-selected { + border-style: solid; + border-color: #f2e3b2; +} +.x-grid-with-row-lines .x-grid-item-selected + .x-grid-item { + border-top-style: solid; + border-top-color: #f2e3b2; +} +.x-grid-with-row-lines .x-grid-item:last-child { + border-bottom-width: 1px; +} +.x-ie8 .x-grid-with-row-lines .x-grid-item { + border-width: 1px 0; + margin-top: -1px; +} +.x-ie8 .x-grid-with-row-lines .x-grid-item:first-child { + margin-top: 0; +} +.x-grid-cell-inner { + position: relative; + text-overflow: ellipsis; + padding: 7px 10px 6px; +} +.x-grid-cell-special { + border-color: #e9e9e9; + border-style: solid; + border-right-width: 1px; +} +.x-grid-dirty-cell > .x-grid-cell-inner:after { + content: "\e602"; + font: 14px/1 ExtJS; + color: #cf4c35; + position: absolute; + top: 0; + left: 0; +} +.x-grid-row .x-grid-cell-selected { + color: #404040; + background-color: #ffefbb; +} +.x-grid-with-col-lines .x-grid-cell { + border-style: solid; + border-color: #e9e9e9; + border-width: 0 1px 0 0; +} +.x-grid-with-col-lines .x-grid-item-over .x-grid-cell { + border-color: #dbe5ea; + border-style: solid; +} +.x-grid-with-col-lines .x-grid-item-selected .x-grid-cell { + border-color: #f2e3b2; + border-style: solid; +} +.x-grid-resize-marker { + width: 1px; + background-color: #0f0f0f; +} +.x-col-move-top, +.x-col-move-bottom { + width: 9px; + height: 9px; +} +.x-col-move-top { + background-image: url(images/grid/col-move-top.png); +} +.x-col-move-bottom { + background-image: url(images/grid/col-move-bottom.png); +} +.x-grid-header-ct { + border: 1px solid #d0d0d0; + border-bottom-color: #fff; + background-color: #fff; +} +.x-accordion-item .x-grid-header-ct { + border-width: 0 0 1px !important; +} +.x-grid-header-ct-hidden { + border-top: 0 !important; + border-bottom: 0 !important; +} +.x-grid-body { + border-top-color: #d0d0d0; +} +.x-hmenu-sort-asc { + font: 16px/24px ExtJS; +} +.x-hmenu-sort-asc:before { + content: "\e61a"; +} +.x-hmenu-sort-desc { + font: 16px/24px ExtJS; +} +.x-hmenu-sort-desc:before { + content: "\e619"; +} +.x-cols-icon { + font: 16px/24px ExtJS; +} +.x-cols-icon:before { + content: "\e601"; +} +.x-column-header { + border-right: 1px solid #d0d0d0; + color: #404040; + font: 500 14px/19px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + outline: 0; + background-color: #fff; +} +.x-group-sub-header { + background: transparent; + border-top: 1px solid #d0d0d0; +} +.x-group-sub-header .x-column-header-inner { + padding: 6px 10px 6px 10px; +} +.x-column-header-inner { + padding: 7px 10px 6px; +} +.x-column-header-inner-empty { + text-overflow: clip; +} +.x-keyboard-mode .x-column-header.x-column-header-focus { + color: #404040; +} +.x-keyboard-mode + .x-column-header.x-column-header-focus + .x-column-header-inner:after { + content: ""; + position: absolute; + z-index: 5; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + border: 1px solid #5dc8f8; + pointer-events: none; +} +.x-keyboard-mode + .x-column-header.x-column-header-focus.x-group-sub-header + .x-column-header-inner:before { + bottom: 0px; +} +.x-column-header-over { + background-image: none; + background-color: #e6f1f6; +} +.x-column-header-sort-ASC, +.x-column-header-sort-DESC { + background-image: none; + background-color: #fff; +} +.x-column-header-open { + background-color: #e6f1f6; +} +.x-column-header-open .x-column-header-trigger { + background-color: #dbe5ea; +} +.x-column-header-over .x-column-header-trigger, +.x-column-header-open .x-column-header-trigger { + width: 24px; + cursor: pointer; + font: 16px/1 FontAwesome; + color: #919191; +} +.x-column-header-over .x-column-header-trigger:before, +.x-column-header-open .x-column-header-trigger:before { + content: "\f0d7"; +} +.x-column-header-over .x-column-header-trigger:before, +.x-column-header-open .x-column-header-trigger:before { + top: 50%; + margin-top: -8px; + text-align: center; + position: relative; + display: block; +} +.x-column-header-align-right .x-column-header-text { + margin-right: 18px; +} +.x-column-header-sort-ASC .x-column-header-text-inner, +.x-column-header-sort-DESC .x-column-header-text-inner { + background-position: right center; +} +.x-column-header-sort-ASC .x-column-header-text-inner:after, +.x-column-header-sort-DESC .x-column-header-text-inner:after { + display: inline-block; + text-align: center; + margin-left: 5px; + width: 14px; +} +.x-column-header-sort-ASC .x-column-header-text-inner:after { + content: "\f176"; + font: 14px/1 FontAwesome; + color: #919191; +} +.x-column-header-sort-DESC .x-column-header-text-inner:after { + content: "\f175"; + font: 14px/1 FontAwesome; + color: #919191; +} +.x-no-header-borders .x-column-header { + border: 0 none; +} +.x-no-header-borders .x-column-header .x-column-header-inner { + padding-top: 7px; +} +.x-grid-cell-inner-action-col { + padding: 7px 4px 7px 4px; +} +.x-action-col-cell .x-item-disabled { + opacity: 0.3; +} +.x-action-col-icon { + color: #919191; + font-size: 18px; + height: 18px; + width: 18px; + cursor: pointer; +} +.x-column-header-checkbox .x-column-header-inner, +.x-grid-checkcolumn-cell-inner { + padding: 7px 4px 7px 4px; + text-overflow: clip; +} +.x-column-header-checkbox { + border-color: #fff; +} +.x-column-header-checkbox .x-column-header-text { + overflow: visible; +} +.x-column-header-checkbox .x-column-header-checkbox:after, +.x-grid-checkcolumn:after { + content: "\e614"; + font: 18px/1 ExtJS; + color: #919191; +} +.x-item-disabled .x-column-header-checkbox .x-column-header-checkbox, +.x-item-disabled .x-grid-checkcolumn { + opacity: 0.3; +} +.x-grid-hd-checker-on .x-column-header-checkbox:after, +.x-grid-checkcolumn-checked:after { + content: "\e613"; + font: 18px/1 ExtJS; + color: #919191; +} +.x-grid-item-selected .x-selmodel-column .x-grid-checkcolumn:after { + content: "\e613"; + font: 18px/1 ExtJS; + color: #919191; +} +.x-gecko .x-selmodel-checkbox .x-grid-checkcolumn { + pointer-events: none; +} +.x-menu-default { + border-style: solid; + border-width: 1px; + border-color: #d0d0d0; +} +.x-menu-body-default { + background: #fff; + padding: 0; +} +.x-menu-icon-separator-default { + left: 32px; + border-left: solid 1px #d0d0d0; + background-color: #fff; + width: 1px; +} +.x-menu-item-default { + border-width: 0; + cursor: pointer; +} +.x-menu-item-default.x-menu-item-focus, +.x-menu-item-default.x-menu-item-active { + background-image: none; + background-color: #5dc8f8; +} +.x-nlg .x-menu-item-default.x-menu-item-focus, +.x-nlg .x-menu-item-default.x-menu-item-active { + background: #5dc8f8 repeat-x left top; + background-image: url(images/menu/menu-item-default-active-bg.gif); +} +.x-menu-item-default.x-menu-item-disabled { + cursor: default; +} +.x-menu-item-default.x-menu-item-disabled a { + cursor: default; +} +.x-menu-item-default.x-menu-item-separator { + height: 1px; + border-top: solid 1px #d0d0d0; + background-color: #fff; + margin: 2px 0; + padding: 0; +} +.x-menu-item-default.x-menu-item-disabled { + opacity: 0.5; +} +.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-icon-ui { + opacity: 0.5; +} +.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-text-default { + background-color: transparent; +} +.x-menu-item-default .x-form-item-label { + font-size: 14px; + color: #000; +} +.x-menu-item-text-default, +.x-menu-item-cmp-default { + margin: 0 8px 0 8px; +} +.x-menu-item-text-default { + font: 400 14px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + line-height: 31px; + padding-top: 1px; + color: #000; + cursor: pointer; +} +.x-menu-item-focus .x-menu-item-text-default, +.x-menu-item-active .x-menu-item-text-default { + color: #fff; +} +.x-menu-item-text-default.x-menu-item-indent { + margin-left: 41px; +} +.x-menu-item-text-default.x-menu-item-indent-no-separator { + margin-left: 36px; +} +.x-menu-item-text-default.x-menu-item-indent-right-icon { + margin-right: 40px; +} +.x-menu-item-text-default.x-menu-item-indent-right-arrow { + margin-right: 29px; +} +.x-menu-item-disabled .x-menu-item-text-default { + cursor: default; +} +.x-menu-item-indent-default { + margin-left: 41px; +} +.x-menu-item-icon-default { + width: 24px; + height: 24px; + top: 4px; + left: 4px; + line-height: 24px; + font-size: 16px; + color: #919191; + background-position: center center; +} +.x-menu-item-focus .x-menu-item-icon-default, +.x-menu-item-active .x-menu-item-icon-default { + color: #fff; +} +.x-ie8 .x-menu-item-focus .x-menu-item-icon-default, +.x-ie8 .x-menu-item-active .x-menu-item-icon-default { + color: #fff !important; +} +.x-ie8 .x-menu-item-icon-default.x-menu-item-glyph { + color: #919191; +} +.x-menu-item-icon-default.x-menu-item-icon-right { + width: 24px; + height: 24px; + top: 4px; + right: 4px; + left: auto; + background-position: center center; +} +.x-menu-item-icon-default.x-menu-item-checkbox { + color: #919191; +} +.x-menu-item-focus .x-menu-item-icon-default.x-menu-item-checkbox, +.x-menu-item-active .x-menu-item-icon-default.x-menu-item-checkbox { + color: #fff; +} +.x-menu-item-checked .x-menu-item-icon-default.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +.x-menu-item-checked .x-menu-item-icon-default.x-menu-item-checkbox:before { + content: "\f046"; +} +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-item-checkbox:before { + content: "\f096"; +} +.x-menu-item-focus .x-menu-item-icon-default.x-menu-group-icon, +.x-menu-item-active .x-menu-item-icon-default.x-menu-group-icon { + color: #fff; +} +.x-menu-item-checked .x-menu-item-icon-default.x-menu-group-icon { + font: 18px/24px FontAwesome; +} +.x-menu-item-checked .x-menu-item-icon-default.x-menu-group-icon:before { + content: "\f00c"; +} +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-group-icon { + background-image: none; +} +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-group-icon:before { + content: ""; +} +.x-menu-item-arrow-default { + width: 16px; + height: 16px; + top: 8px; + right: 0; + margin: 0 4px 0; + font: 16px/1 FontAwesome; + color: #919191; +} +.x-menu-item-arrow-default:before { + content: "\f0da"; +} +.x-menu-item-focus .x-menu-item-arrow-default, +.x-menu-item-active .x-menu-item-arrow-default { + color: #fff; +} +.x-menu-item-focus .x-menu-item-arrow-default, +.x-menu-item-active .x-menu-item-arrow-default { + top: 8px; + right: 0; +} +.x-menu-default-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +.x-menu-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +.x-box-scroller-menu-default { + cursor: pointer; + color: #919191; + opacity: 0.5; +} +.x-box-scroller-menu-default.x-box-scroller-hover { + opacity: 0.6; +} +.x-box-scroller-menu-default.x-box-scroller-pressed { + opacity: 0.7; +} +.x-box-scroller-menu-default.x-box-scroller-disabled { + opacity: 0.25; + cursor: default; +} +.x-box-scroller-menu-default.x-box-scroller-top, +.x-box-scroller-menu-default.x-box-scroller-bottom { + height: 16px; + width: 16px; + left: 50%; + margin-left: -8px; +} +.x-box-scroller-menu-default.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +.x-box-scroller-menu-default.x-box-scroller-top:before { + content: "\f077"; +} +.x-box-scroller-menu-default.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +.x-box-scroller-menu-default.x-box-scroller-bottom:before { + content: "\f078"; +} +.x-ie8 .x-box-scroller-menu-default { + background-color: #fff; +} +.x-menu-default-menubar { + border-style: solid; + border-width: 1px; + border-color: #d0d0d0; +} +.x-menu-body-default-menubar { + background: #fff; + padding: 0; +} +.x-menu-icon-separator-default-menubar { + left: 32px; + border-left: solid 1px #d0d0d0; + background-color: #fff; + width: 1px; +} +.x-menu-item-default-menubar { + border-width: 0; + cursor: pointer; +} +.x-menu-item-default-menubar.x-menu-item-focus, +.x-menu-item-default-menubar.x-menu-item-active { + background-image: none; + background-color: #5dc8f8; +} +.x-nlg .x-menu-item-default-menubar.x-menu-item-focus, +.x-nlg .x-menu-item-default-menubar.x-menu-item-active { + background: #5dc8f8 repeat-x left top; + background-image: url(images/menu/menu-item-default-menubar-active-bg.gif); +} +.x-menu-item-default-menubar.x-menu-item-disabled { + cursor: default; +} +.x-menu-item-default-menubar.x-menu-item-disabled a { + cursor: default; +} +.x-menu-item-default-menubar.x-menu-item-separator { + height: 1px; + border-top: solid 1px #d0d0d0; + background-color: #fff; + margin: 2px 0; + padding: 0; +} +.x-menu-item-default-menubar.x-menu-item-disabled { + opacity: 0.5; +} +.x-ie9m .x-menu-item-default-menubar.x-menu-item-disabled .x-menu-item-icon-ui { + opacity: 0.5; +} +.x-ie9m + .x-menu-item-default-menubar.x-menu-item-disabled + .x-menu-item-text-default-menubar { + background-color: transparent; +} +.x-menu-item-default-menubar .x-form-item-label { + font-size: 14px; + color: #000; +} +.x-menu-item-text-default-menubar, +.x-menu-item-cmp-default-menubar { + margin: 0 8px 0 8px; +} +.x-menu-item-text-default-menubar { + font: 400 14px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + line-height: 31px; + padding-top: 1px; + color: #000; + cursor: pointer; +} +.x-menu-item-focus .x-menu-item-text-default-menubar, +.x-menu-item-active .x-menu-item-text-default-menubar { + color: #fff; +} +.x-menu-item-text-default-menubar.x-menu-item-indent { + margin-left: 41px; +} +.x-menu-item-text-default-menubar.x-menu-item-indent-no-separator { + margin-left: 36px; +} +.x-menu-item-text-default-menubar.x-menu-item-indent-right-icon { + margin-right: 40px; +} +.x-menu-item-text-default-menubar.x-menu-item-indent-right-arrow { + margin-right: 27px; +} +.x-menu-item-disabled .x-menu-item-text-default-menubar { + cursor: default; +} +.x-menu-item-indent-default-menubar { + margin-left: 41px; +} +.x-menu-item-icon-default-menubar { + width: 24px; + height: 24px; + top: 4px; + left: 4px; + line-height: 24px; + font-size: 16px; + color: #919191; + background-position: center center; +} +.x-menu-item-focus .x-menu-item-icon-default-menubar, +.x-menu-item-active .x-menu-item-icon-default-menubar { + color: #fff; +} +.x-ie8 .x-menu-item-focus .x-menu-item-icon-default-menubar, +.x-ie8 .x-menu-item-active .x-menu-item-icon-default-menubar { + color: #fff !important; +} +.x-ie8 .x-menu-item-icon-default-menubar.x-menu-item-glyph { + color: #919191; +} +.x-menu-item-icon-default-menubar.x-menu-item-icon-right { + width: 24px; + height: 24px; + top: 4px; + right: 4px; + left: auto; + background-position: center center; +} +.x-menu-item-icon-default-menubar.x-menu-item-checkbox { + color: #919191; +} +.x-menu-item-focus .x-menu-item-icon-default-menubar.x-menu-item-checkbox, +.x-menu-item-active .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + color: #fff; +} +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +.x-menu-item-checked + .x-menu-item-icon-default-menubar.x-menu-item-checkbox:before { + content: "\f046"; +} +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +.x-menu-item-unchecked + .x-menu-item-icon-default-menubar.x-menu-item-checkbox:before { + content: "\f096"; +} +.x-menu-item-focus .x-menu-item-icon-default-menubar.x-menu-group-icon, +.x-menu-item-active .x-menu-item-icon-default-menubar.x-menu-group-icon { + color: #fff; +} +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-group-icon { + font: 18px/24px FontAwesome; +} +.x-menu-item-checked + .x-menu-item-icon-default-menubar.x-menu-group-icon:before { + content: "\f00c"; +} +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-group-icon { + background-image: none; +} +.x-menu-item-unchecked + .x-menu-item-icon-default-menubar.x-menu-group-icon:before { + content: ""; +} +.x-menu-item-arrow-default-menubar { + width: 9px; + height: 6px; + top: 9px; + right: 5px; + margin: 0 4px 0; + font: 16px/1 FontAwesome; + color: #919191; +} +.x-menu-item-arrow-default-menubar:before { + content: "\f0d7"; +} +.x-menu-item-focus .x-menu-item-arrow-default-menubar, +.x-menu-item-active .x-menu-item-arrow-default-menubar { + color: #fff; +} +.x-menu-item-focus .x-menu-item-arrow-default-menubar, +.x-menu-item-active .x-menu-item-arrow-default-menubar { + top: 9px; + right: 5px; +} +.x-menu-default-menubar-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +.x-menu-default-menubar-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +.x-box-scroller-menu-default-menubar { + cursor: pointer; + color: #919191; + opacity: 0.5; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-hover { + opacity: 0.6; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-pressed { + opacity: 0.7; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-disabled { + opacity: 0.25; + cursor: default; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-top, +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom { + height: 16px; + width: 16px; + left: 50%; + margin-left: -8px; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-top:before { + content: "\f077"; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom:before { + content: "\f078"; +} +.x-ie8 .x-box-scroller-menu-default-menubar { + background-color: #fff; +} +.x-grid-locked .x-grid-inner-locked { + border-width: 0 2px 0 0; + border-style: solid; +} +.x-grid-locked-split .x-grid-inner-normal { + border-width: 0 0 0 2px; + border-style: solid; + border-left-color: #d0d0d0; +} +.x-grid-locking-body { + border-width: 1px; +} +.x-grid-locking-body > .x-splitter { + background-color: #ececec; +} +.x-grid-locking-body > .x-splitter-active { + background-color: #b4b4b4; +} +.x-grid-inner-locked { + border-right-color: #d0d0d0; +} +.x-grid-inner-locked .x-column-header-last, +.x-grid-inner-locked .x-grid-cell-last { + border-right-width: 0 !important; +} +.x-hmenu-lock { + font: 16px/24px FontAwesome; +} +.x-hmenu-lock:before { + content: "\f023"; +} +.x-hmenu-unlock { + font: 16px/24px FontAwesome; +} +.x-hmenu-unlock:before { + content: "\f09c"; +} +.x-grid-scrollbar-clipper > .x-grid-view, +.x-grid-scrollbar-clipper > .x-tree-view { + background-color: #fff; +} +.x-grid-scrollbar-clipper-locked, +.x-grid-scrollbar-locked { + border-width: 0 2px 0 0; + border-style: solid; + border-color: #d0d0d0; +} +.x-grid-scroll-container { + background-color: #fff; +} +.x-accordion-layout-ct { + background-color: #5aaed4; + padding: 5px 5px 0; +} +.x-accordion-hd .x-panel-header-title { + color: #333; + font-weight: 400; + font-family: "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + text-transform: none; +} +.x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus { + outline: 1px solid #5aaed4; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus, +.x-edge .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus { + outline: none; +} +.x-ie + .x-keyboard-mode + .x-accordion-hd + .x-panel-header-title.x-title-focus:after, +.x-ie10p + .x-keyboard-mode + .x-accordion-hd + .x-panel-header-title.x-title-focus:after, +.x-edge + .x-keyboard-mode + .x-accordion-hd + .x-panel-header-title.x-title-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5aaed4; + pointer-events: none; +} +.x-accordion-item { + margin: 0 0 5px; +} +.x-accordion-item .x-accordion-hd { + background: #f7f7f7; + border-width: 0; + border-color: #5aaed4; + padding: 12px 10px; +} +.x-accordion-item .x-accordion-hd-over { + background-color: #f6f6f6; +} +.x-accordion-item .x-accordion-hd-over .x-tool-tool-el { + background-color: #f6f6f6; +} +.x-accordion-item .x-accordion-hd-sibling-expanded { + border-top-color: #5aaed4; + border-top-width: 0; +} +.x-accordion-item .x-accordion-hd-last-collapsed { + border-bottom-color: #fff; +} +.x-accordion-item .x-accordion-body { + border-width: 0; +} +.x-accordion-hd .x-tool-tool-el { + background-color: #fff; + color: #5aaed4; +} +.x-accordion-hd .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-image: none; +} +.x-accordion-hd .x-tool-collapse-top, +.x-accordion-hd .x-tool-collapse-bottom { + font: 16px/1 FontAwesome; + background-image: none; +} +.x-accordion-hd .x-tool-collapse-top:before, +.x-accordion-hd .x-tool-collapse-bottom:before { + content: "\f068"; +} +.x-accordion-hd .x-tool-expand-top, +.x-accordion-hd .x-tool-expand-bottom { + font: 16px/1 FontAwesome; + background-image: none; +} +.x-accordion-hd .x-tool-expand-top:before, +.x-accordion-hd .x-tool-expand-bottom:before { + content: "\f067"; +} +.x-keyboard-mode .x-accordion-hd .x-tool-focus { + outline: 1px solid #5aaed4; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus, +.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5aaed4; + pointer-events: none; +} +.x-resizable-handle { + position: absolute; + z-index: 100; + font-size: 1px; + line-height: 10px; + opacity: 0; + background-color: #ececec; + color: #919191; + text-align: center; +} +.x-collapsed .x-resizable-handle { + display: none; +} +.x-resizable-handle-southeast { + cursor: se-resize; +} +.x-resizable-handle-southeast:before { + position: absolute; + bottom: 0; + right: 0; +} +.x-resizable-handle-northwest { + cursor: nw-resize; +} +.x-resizable-handle-northwest:before { + position: absolute; + top: 0; + left: 0; +} +.x-resizable-handle-northeast { + cursor: ne-resize; +} +.x-resizable-handle-northeast:before { + position: absolute; + top: 0; + right: 0; +} +.x-resizable-handle-southwest { + cursor: sw-resize; +} +.x-resizable-handle-southwest:before { + position: absolute; + bottom: 0; + left: 0; +} +.x-resizable-handle-east:before, +.x-resizable-handle-west:before { + display: block; + position: absolute; + top: 50%; + margin-top: -0.5em; + width: 100%; +} +.x-resizable-handle-east { + cursor: e-resize; + width: 10px; + right: 0; + top: 0; + bottom: 0; +} +.x-resizable-handle-south { + cursor: s-resize; + height: 10px; + left: 0; + right: 0; + bottom: 0; +} +.x-resizable-handle-west { + cursor: w-resize; + width: 10px; + left: 0; + top: 0; + bottom: 0; +} +.x-resizable-handle-north { + cursor: n-resize; + height: 10px; + left: 0; + right: 0; + top: 0; +} +.x-resizable-handle-southeast { + width: 10px; + height: 10px; + right: 0; + bottom: 0; + z-index: 101; +} +.x-resizable-handle-northwest { + width: 10px; + height: 10px; + left: 0; + top: 0; + z-index: 101; +} +.x-resizable-handle-northeast { + width: 10px; + height: 10px; + right: 0; + top: 0; + z-index: 101; +} +.x-resizable-handle-southwest { + width: 10px; + height: 10px; + left: 0; + bottom: 0; + z-index: 101; +} +.x-tablet .x-resizable-handle-north, +.x-tablet .x-resizable-handle-south { + height: 20px; +} +.x-tablet .x-resizable-handle-east, +.x-tablet .x-resizable-handle-west { + width: 20px; +} +.x-tablet .x-resizable-handle-northwest, +.x-tablet .x-resizable-handle-northeast, +.x-tablet .x-resizable-handle-southwest, +.x-tablet .x-resizable-handle-southeast { + width: 20px; + height: 20px; +} +.x-window .x-window-handle { + opacity: 0; +} +.x-window-collapsed .x-window-handle { + display: none; +} +.x-resizable-proxy { + border: 1px dashed #3b5a82; + position: absolute; + overflow: hidden; + z-index: 50000; +} +.x-resizable-handle-over, +.x-resizable-pinned .x-resizable-handle { + opacity: 1; +} +.x-resizable-handle-east-over, +.x-resizable-handle-west-over, +.x-resizable-pinned > .x-resizable-handle-east, +.x-resizable-pinned > .x-resizable-handle-west { + font: 16px/1 FontAwesome; +} +.x-resizable-handle-east-over:before, +.x-resizable-handle-west-over:before, +.x-resizable-pinned > .x-resizable-handle-east:before, +.x-resizable-pinned > .x-resizable-handle-west:before { + content: "\f142"; +} +.x-resizable-handle-south-over, +.x-resizable-handle-north-over, +.x-resizable-pinned > .x-resizable-handle-south, +.x-resizable-pinned > .x-resizable-handle-north { + font: 16px/10px FontAwesome; +} +.x-resizable-handle-south-over:before, +.x-resizable-handle-north-over:before, +.x-resizable-pinned > .x-resizable-handle-south:before, +.x-resizable-pinned > .x-resizable-handle-north:before { + content: "\f141"; +} +.x-resizable-handle-southeast-over, +.x-resizable-pinned > .x-resizable-handle-southeast { + font: 16px/1 ExtJS; +} +.x-resizable-handle-southeast-over:before, +.x-resizable-pinned > .x-resizable-handle-southeast:before { + content: "\e60c"; +} +.x-resizable-handle-northwest-over, +.x-resizable-pinned > .x-resizable-handle-northwest { + font: 16px/1 ExtJS; +} +.x-resizable-handle-northwest-over:before, +.x-resizable-pinned > .x-resizable-handle-northwest:before { + content: "\e609"; +} +.x-resizable-handle-northeast-over, +.x-resizable-pinned > .x-resizable-handle-northeast { + font: 16px/1 ExtJS; +} +.x-resizable-handle-northeast-over:before, +.x-resizable-pinned > .x-resizable-handle-northeast:before { + content: "\e60a"; +} +.x-resizable-handle-southwest-over, +.x-resizable-pinned > .x-resizable-handle-southwest { + font: 16px/1 ExtJS; +} +.x-resizable-handle-southwest-over:before, +.x-resizable-pinned > .x-resizable-handle-southwest:before { + content: "\e60b"; +} +.x-slider:before { + border: 1px solid #d0d0d0; + content: ""; + position: absolute; + border-radius: 2px; + background-color: #eee; + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +.x-slider-thumb { + background-color: #f6f6f6; + border: 1px solid #d0d0d0; + border-radius: 2px; +} +.x-slider-thumb:before { + color: #d0d0d0; +} +.x-slider-thumb-over { + background-color: #fcfcfc; + border-color: #c5cfd4; +} +.x-slider-thumb-over:before { + color: #d0d0d0; +} +.x-keyboard-mode .x-slider-focus .x-slider-thumb { + background-color: #f6f6f6; + border-color: #5aaed4; +} +.x-keyboard-mode .x-slider-focus .x-slider-thumb:before { + color: #91d3f1; +} +.x-keyboard-mode .x-slider-focus .x-slider-thumb-over { + background-color: #fcfcfc; +} +.x-slider-thumb-drag { + background-color: #f1f1f1; + border-color: #bbcbd2; +} +.x-slider-thumb-drag:before { + color: #d0d0d0; +} +.x-keyboard-mode .x-slider-focus .x-slider-thumb-drag { + background-color: #f1f1f1; +} +.x-slider-horz { + padding-left: 10px; + background: no-repeat 0 -20px; + margin: 6px 0 6px; +} +.x-slider-horz .x-slider-end { + padding-right: 10px; + background: no-repeat right -40px; +} +.x-slider-horz .x-slider-inner { + height: 20px; +} +.x-slider-horz:before { + height: 10px; + width: 100%; + top: 50%; + left: 0; + margin-top: -5px; +} +.x-slider-horz .x-slider-thumb { + width: 20px; + height: 20px; + margin-left: -10px; + font: 12px/1 ExtJS; +} +.x-slider-horz .x-slider-thumb:before { + content: "\e612"; +} +.x-slider-ct-vert { + height: 100%; +} +.x-slider-vert { + padding-top: 10px; + height: 100%; +} +.x-slider-vert > .x-slider-end { + height: 100%; +} +.x-slider-vert > .x-slider-end > .x-slider-inner { + height: 100%; +} +.x-slider-vert:before { + width: 10px; + height: 100%; + left: 10px; + top: 0; + margin-left: -5px; +} +.x-slider-vert .x-slider-end { + padding-bottom: 10px; + background: no-repeat -20px bottom; + width: 20px; +} +.x-slider-vert .x-slider-inner { + width: 20px; +} +.x-slider-vert .x-slider-thumb { + width: 20px; + height: 20px; + margin-bottom: -10px; + font: 12px/1 ExtJS; +} +.x-slider-vert .x-slider-thumb:before { + content: "\e605"; +} +.x-slider-default-cell > .x-grid-cell-inner, +.x-sliderwidget-default-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +.x-tab-default-top { + -webkit-border-top-right-radius: 5px; + -webkit-border-top-left-radius: 5px; + -moz-border-top-right-radius: 5px; + -moz-border-top-left-radius: 5px; + -ms-border-top-right-radius: 5px; + -ms-border-top-left-radius: 5px; + -o-border-top-right-radius: 5px; + -o-border-top-left-radius: 5px; + border-top-right-radius: 5px; + border-top-left-radius: 5px; + padding: 8px 20px 8px 20px; + border-width: 0; + border-style: solid; + background-color: transparent; +} +.x-tab-default-top-mc { + background-color: transparent; +} +.x-nbr .x-tab-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tab-default-top-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +.x-tab-default-top-tl { + background-position: 0 0; +} +.x-tab-default-top-tr { + background-position: right 0; +} +.x-tab-default-top-bl { + background-position: 0 0; +} +.x-tab-default-top-br { + background-position: right 0; +} +.x-tab-default-top-ml { + background-position: 0 top; +} +.x-tab-default-top-mr { + background-position: right top; +} +.x-tab-default-top-tc { + background-position: 0 0; +} +.x-tab-default-top-bc { + background-position: 0 0; +} +.x-tab-default-top-tr, +.x-tab-default-top-br, +.x-tab-default-top-mr { + padding-right: 0; +} +.x-tab-default-top-tl, +.x-tab-default-top-bl, +.x-tab-default-top-ml { + padding-left: 0; +} +.x-tab-default-top-tc { + height: 0; +} +.x-tab-default-top-bc { + height: 0; +} +.x-tab-default-top-mc { + padding: 8px 10px 8px 10px; +} +.x-tab-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0 0 0 0; + border-style: solid; + background-color: transparent; +} +.x-tab-default-bottom-mc { + background-color: transparent; +} +.x-nbr .x-tab-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tab-default-bottom-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +.x-tab-default-bottom-tl { + background-position: 0 0; +} +.x-tab-default-bottom-tr { + background-position: right 0; +} +.x-tab-default-bottom-bl { + background-position: 0 0; +} +.x-tab-default-bottom-br { + background-position: right 0; +} +.x-tab-default-bottom-ml { + background-position: 0 bottom; +} +.x-tab-default-bottom-mr { + background-position: right bottom; +} +.x-tab-default-bottom-tc { + background-position: 0 0; +} +.x-tab-default-bottom-bc { + background-position: 0 0; +} +.x-tab-default-bottom-tr, +.x-tab-default-bottom-br, +.x-tab-default-bottom-mr { + padding-right: 0; +} +.x-tab-default-bottom-tl, +.x-tab-default-bottom-bl, +.x-tab-default-bottom-ml { + padding-left: 0; +} +.x-tab-default-bottom-tc { + height: 0; +} +.x-tab-default-bottom-bc { + height: 0; +} +.x-tab-default-bottom-mc { + padding: 8px 10px 8px 10px; +} +.x-tab-default-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0 0 0 0; + border-style: solid; + background-color: transparent; +} +.x-tab-default-left-mc { + background-color: transparent; +} +.x-nbr .x-tab-default-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tab-default-left-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +.x-tab-default-left-tl { + background-position: 0 0; +} +.x-tab-default-left-tr { + background-position: right 0; +} +.x-tab-default-left-bl { + background-position: 0 0; +} +.x-tab-default-left-br { + background-position: right 0; +} +.x-tab-default-left-ml { + background-position: 0 top; +} +.x-tab-default-left-mr { + background-position: right top; +} +.x-tab-default-left-tc { + background-position: 0 0; +} +.x-tab-default-left-bc { + background-position: 0 0; +} +.x-tab-default-left-tr, +.x-tab-default-left-br, +.x-tab-default-left-mr { + padding-right: 0; +} +.x-tab-default-left-tl, +.x-tab-default-left-bl, +.x-tab-default-left-ml { + padding-left: 0; +} +.x-tab-default-left-tc { + height: 0; +} +.x-tab-default-left-bc { + height: 0; +} +.x-tab-default-left-mc { + padding: 8px 10px 8px 10px; +} +.x-tab-default-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0 0 0 0; + border-style: solid; + background-color: transparent; +} +.x-tab-default-right-mc { + background-color: transparent; +} +.x-nbr .x-tab-default-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tab-default-right-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +.x-tab-default-right-tl { + background-position: 0 0; +} +.x-tab-default-right-tr { + background-position: right 0; +} +.x-tab-default-right-bl { + background-position: 0 0; +} +.x-tab-default-right-br { + background-position: right 0; +} +.x-tab-default-right-ml { + background-position: 0 top; +} +.x-tab-default-right-mr { + background-position: right top; +} +.x-tab-default-right-tc { + background-position: 0 0; +} +.x-tab-default-right-bc { + background-position: 0 0; +} +.x-tab-default-right-tr, +.x-tab-default-right-br, +.x-tab-default-right-mr { + padding-right: 0; +} +.x-tab-default-right-tl, +.x-tab-default-right-bl, +.x-tab-default-right-ml { + padding-left: 0; +} +.x-tab-default-right-tc { + height: 0; +} +.x-tab-default-right-bc { + height: 0; +} +.x-tab-default-right-mc { + padding: 8px 10px 8px 10px; +} +.x-tab-default { + border-color: transparent; + cursor: pointer; +} +.x-tab-default-top { + margin: 0 4px 0 0; +} +.x-tab-default-top.x-tab-rotate-left { + margin: 0 0 0 4px; +} +.x-keyboard-mode .x-tab-default-top.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-tab-default-right { + margin: 0 0 4px 0; +} +.x-tab-default-right.x-tab-rotate-right { + margin: 4px 0 0 0; +} +.x-keyboard-mode .x-tab-default-right.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-tab-default-bottom { + margin: 0 4px 0 0; +} +.x-tab-default-bottom.x-tab-rotate-left { + margin: 0 0 0 4px; +} +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-tab-default-left { + margin: 0 0 4px 0; +} +.x-tab-default-left.x-tab-rotate-right { + margin: 4px 0 0 0; +} +.x-keyboard-mode .x-tab-default-left.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-tab-button-default { + height: 20px; +} +.x-tab-inner-default { + font: 500 14px/20px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #f0f0f0; + max-width: 100%; +} +.x-tab-bar-plain .x-tab-inner-default { + color: #606060; +} +.x-tab-icon-right > .x-tab-inner-default, +.x-tab-icon-left > .x-tab-inner-default { + max-width: calc(100% - 20px); +} +.x-tab-icon-el-default { + min-height: 20px; + background-position: center center; + font-size: 20px; + line-height: 20px; + color: #f0f0f0; +} +.x-tab-icon-left > .x-tab-icon-el-default, +.x-tab-icon-right > .x-tab-icon-el-default { + width: 20px; +} +.x-tab-icon-top > .x-tab-icon-el-default, +.x-tab-icon-bottom > .x-tab-icon-el-default { + min-width: 20px; +} +.x-tab-bar-plain .x-tab-icon-el-default { + color: #606060; +} +.x-tab-icon-el-default.x-tab-glyph { + opacity: 0.7; +} +.x-tab-text.x-tab-icon-left > .x-tab-icon-el-default { + margin-right: 6px; +} +.x-tab-text.x-tab-icon-right > .x-tab-icon-el-default { + margin-left: 6px; +} +.x-tab-text.x-tab-icon-top > .x-tab-icon-el-default { + margin-bottom: 6px; +} +.x-tab-text.x-tab-icon-bottom > .x-tab-icon-el-default { + margin-top: 6px; +} +.x-keyboard-mode .x-tab-focus.x-tab-default { + border-color: transparent; + background-color: transparent; + outline: 1px solid #5aaed4; + outline-offset: -3px; +} +.x-ie .x-keyboard-mode .x-tab-focus.x-tab-default, +.x-ie10p .x-keyboard-mode .x-tab-focus.x-tab-default, +.x-edge .x-keyboard-mode .x-tab-focus.x-tab-default { + outline: none; +} +.x-ie .x-keyboard-mode .x-tab-focus.x-tab-default:after, +.x-ie10p .x-keyboard-mode .x-tab-focus.x-tab-default:after, +.x-edge .x-keyboard-mode .x-tab-focus.x-tab-default:after { + position: absolute; + content: " "; + top: 2px; + right: 2px; + bottom: 2px; + left: 2px; + border: 1px solid #5aaed4; + pointer-events: none; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-default + .x-tab-inner-default { + color: #606060; +} +.x-keyboard-mode .x-tab-bar-plain .x-tab-focus.x-tab-default .x-tab-icon-el { + color: #606060; +} +.x-tab-over.x-tab-default { + border-color: #000; + background-image: none; + background-color: rgba(0, 0, 0, 0.08); +} +.x-ie8 .x-tab-over.x-tab-default { + zoom: 1; +} +.x-tab-bar-plain .x-tab-over.x-tab-default .x-tab-inner-default { + color: #606060; +} +.x-tab-bar-plain .x-tab-over.x-tab-default .x-tab-icon-el { + color: #606060; +} +.x-keyboard-mode .x-tab-focus.x-tab-over.x-tab-default { + border-color: #000; + background-image: none; + background-color: rgba(0, 0, 0, 0.08); +} +.x-ie8 .x-keyboard-mode .x-tab-focus.x-tab-over.x-tab-default { + zoom: 1; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-over.x-tab-default + .x-tab-inner-default { + color: #606060; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-over.x-tab-default + .x-tab-icon-el { + color: #606060; +} +.x-tab.x-tab-active.x-tab-default { + border-color: #fff; + background-color: #fff; +} +.x-tab.x-tab-active.x-tab-default .x-tab-inner-default { + color: #2a95c5; +} +.x-tab-bar-plain .x-tab.x-tab-active.x-tab-default .x-tab-inner-default { + color: #404040; +} +.x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #2a95c5; +} +.x-ie8 .x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #6ab5d6; +} +.x-tab-bar-plain .x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #404040; +} +.x-keyboard-mode .x-tab-focus.x-tab-active.x-tab-default { + border-color: #fff; + background-color: #fff; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-active.x-tab-default + .x-tab-inner-default { + color: #404040; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-active.x-tab-default + .x-tab-icon-el { + color: #404040; +} +.x-tab.x-tab-disabled.x-tab-default { + border-color: transparent; + background-color: transparent; + cursor: default; +} +.x-tab.x-tab-disabled.x-tab-default .x-tab-inner-default { + opacity: 0.3; +} +.x-tab-bar-plain .x-tab.x-tab-disabled.x-tab-default .x-tab-inner-default { + color: #606060; +} +.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el-default { + opacity: 0.5; +} +.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el { + color: #f0f0f0; + opacity: 0.3; + filter: none; +} +.x-tab-bar-plain .x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el { + color: #606060; +} +.x-nbr .x-tab-default { + background-image: none; +} +.x-tab-over .x-tab-default-top-tl, +.x-tab-over .x-tab-default-top-bl, +.x-tab-over .x-tab-default-top-tr, +.x-tab-over .x-tab-default-top-br, +.x-tab-over .x-tab-default-top-tc, +.x-tab-over .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-over-corners.gif); +} +.x-tab-over .x-tab-default-top-ml, +.x-tab-over .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-over-sides.gif); +} +.x-tab-over .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-over-fbg.gif); +} +.x-tab-focus .x-tab-default-top-tl, +.x-tab-focus .x-tab-default-top-bl, +.x-tab-focus .x-tab-default-top-tr, +.x-tab-focus .x-tab-default-top-br, +.x-tab-focus .x-tab-default-top-tc, +.x-tab-focus .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-corners.gif); +} +.x-tab-focus .x-tab-default-top-ml, +.x-tab-focus .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-sides.gif); +} +.x-tab-focus .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-fbg.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-top-tl, +.x-tab-focus.x-tab-over .x-tab-default-top-bl, +.x-tab-focus.x-tab-over .x-tab-default-top-tr, +.x-tab-focus.x-tab-over .x-tab-default-top-br, +.x-tab-focus.x-tab-over .x-tab-default-top-tc, +.x-tab-focus.x-tab-over .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-over-corners.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-top-ml, +.x-tab-focus.x-tab-over .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-over-sides.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-over-fbg.gif); +} +.x-tab.x-tab-active .x-tab-default-top-tl, +.x-tab.x-tab-active .x-tab-default-top-bl, +.x-tab.x-tab-active .x-tab-default-top-tr, +.x-tab.x-tab-active .x-tab-default-top-br, +.x-tab.x-tab-active .x-tab-default-top-tc, +.x-tab.x-tab-active .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-active-corners.gif); +} +.x-tab.x-tab-active .x-tab-default-top-ml, +.x-tab.x-tab-active .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-active-sides.gif); +} +.x-tab.x-tab-active .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-active-fbg.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-top-tl, +.x-tab-focus.x-tab-active .x-tab-default-top-bl, +.x-tab-focus.x-tab-active .x-tab-default-top-tr, +.x-tab-focus.x-tab-active .x-tab-default-top-br, +.x-tab-focus.x-tab-active .x-tab-default-top-tc, +.x-tab-focus.x-tab-active .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-active-corners.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-top-ml, +.x-tab-focus.x-tab-active .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-active-sides.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-active-fbg.gif); +} +.x-tab.x-tab-disabled .x-tab-default-top-tl, +.x-tab.x-tab-disabled .x-tab-default-top-bl, +.x-tab.x-tab-disabled .x-tab-default-top-tr, +.x-tab.x-tab-disabled .x-tab-default-top-br, +.x-tab.x-tab-disabled .x-tab-default-top-tc, +.x-tab.x-tab-disabled .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-disabled-corners.gif); +} +.x-tab.x-tab-disabled .x-tab-default-top-ml, +.x-tab.x-tab-disabled .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-disabled-sides.gif); +} +.x-tab.x-tab-disabled .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-disabled-fbg.gif); +} +.x-tab-over .x-tab-default-right-tl, +.x-tab-over .x-tab-default-right-bl, +.x-tab-over .x-tab-default-right-tr, +.x-tab-over .x-tab-default-right-br, +.x-tab-over .x-tab-default-right-tc, +.x-tab-over .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-over-corners.gif); +} +.x-tab-over .x-tab-default-right-ml, +.x-tab-over .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-over-sides.gif); +} +.x-tab-over .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-over-fbg.gif); +} +.x-tab-focus .x-tab-default-right-tl, +.x-tab-focus .x-tab-default-right-bl, +.x-tab-focus .x-tab-default-right-tr, +.x-tab-focus .x-tab-default-right-br, +.x-tab-focus .x-tab-default-right-tc, +.x-tab-focus .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-corners.gif); +} +.x-tab-focus .x-tab-default-right-ml, +.x-tab-focus .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-sides.gif); +} +.x-tab-focus .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-fbg.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-right-tl, +.x-tab-focus.x-tab-over .x-tab-default-right-bl, +.x-tab-focus.x-tab-over .x-tab-default-right-tr, +.x-tab-focus.x-tab-over .x-tab-default-right-br, +.x-tab-focus.x-tab-over .x-tab-default-right-tc, +.x-tab-focus.x-tab-over .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-over-corners.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-right-ml, +.x-tab-focus.x-tab-over .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-over-sides.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-over-fbg.gif); +} +.x-tab.x-tab-active .x-tab-default-right-tl, +.x-tab.x-tab-active .x-tab-default-right-bl, +.x-tab.x-tab-active .x-tab-default-right-tr, +.x-tab.x-tab-active .x-tab-default-right-br, +.x-tab.x-tab-active .x-tab-default-right-tc, +.x-tab.x-tab-active .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-active-corners.gif); +} +.x-tab.x-tab-active .x-tab-default-right-ml, +.x-tab.x-tab-active .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-active-sides.gif); +} +.x-tab.x-tab-active .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-active-fbg.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-right-tl, +.x-tab-focus.x-tab-active .x-tab-default-right-bl, +.x-tab-focus.x-tab-active .x-tab-default-right-tr, +.x-tab-focus.x-tab-active .x-tab-default-right-br, +.x-tab-focus.x-tab-active .x-tab-default-right-tc, +.x-tab-focus.x-tab-active .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-active-corners.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-right-ml, +.x-tab-focus.x-tab-active .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-active-sides.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-active-fbg.gif); +} +.x-tab.x-tab-disabled .x-tab-default-right-tl, +.x-tab.x-tab-disabled .x-tab-default-right-bl, +.x-tab.x-tab-disabled .x-tab-default-right-tr, +.x-tab.x-tab-disabled .x-tab-default-right-br, +.x-tab.x-tab-disabled .x-tab-default-right-tc, +.x-tab.x-tab-disabled .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-disabled-corners.gif); +} +.x-tab.x-tab-disabled .x-tab-default-right-ml, +.x-tab.x-tab-disabled .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-disabled-sides.gif); +} +.x-tab.x-tab-disabled .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-disabled-fbg.gif); +} +.x-tab-over .x-tab-default-bottom-tl, +.x-tab-over .x-tab-default-bottom-bl, +.x-tab-over .x-tab-default-bottom-tr, +.x-tab-over .x-tab-default-bottom-br, +.x-tab-over .x-tab-default-bottom-tc, +.x-tab-over .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-over-corners.gif); +} +.x-tab-over .x-tab-default-bottom-ml, +.x-tab-over .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-over-sides.gif); +} +.x-tab-over .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-over-fbg.gif); +} +.x-tab-focus .x-tab-default-bottom-tl, +.x-tab-focus .x-tab-default-bottom-bl, +.x-tab-focus .x-tab-default-bottom-tr, +.x-tab-focus .x-tab-default-bottom-br, +.x-tab-focus .x-tab-default-bottom-tc, +.x-tab-focus .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-corners.gif); +} +.x-tab-focus .x-tab-default-bottom-ml, +.x-tab-focus .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-sides.gif); +} +.x-tab-focus .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-fbg.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-bottom-tl, +.x-tab-focus.x-tab-over .x-tab-default-bottom-bl, +.x-tab-focus.x-tab-over .x-tab-default-bottom-tr, +.x-tab-focus.x-tab-over .x-tab-default-bottom-br, +.x-tab-focus.x-tab-over .x-tab-default-bottom-tc, +.x-tab-focus.x-tab-over .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-over-corners.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-bottom-ml, +.x-tab-focus.x-tab-over .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-over-sides.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-over-fbg.gif); +} +.x-tab.x-tab-active .x-tab-default-bottom-tl, +.x-tab.x-tab-active .x-tab-default-bottom-bl, +.x-tab.x-tab-active .x-tab-default-bottom-tr, +.x-tab.x-tab-active .x-tab-default-bottom-br, +.x-tab.x-tab-active .x-tab-default-bottom-tc, +.x-tab.x-tab-active .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-active-corners.gif); +} +.x-tab.x-tab-active .x-tab-default-bottom-ml, +.x-tab.x-tab-active .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-active-sides.gif); +} +.x-tab.x-tab-active .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-active-fbg.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-bottom-tl, +.x-tab-focus.x-tab-active .x-tab-default-bottom-bl, +.x-tab-focus.x-tab-active .x-tab-default-bottom-tr, +.x-tab-focus.x-tab-active .x-tab-default-bottom-br, +.x-tab-focus.x-tab-active .x-tab-default-bottom-tc, +.x-tab-focus.x-tab-active .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-active-corners.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-bottom-ml, +.x-tab-focus.x-tab-active .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-active-sides.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-active-fbg.gif); +} +.x-tab.x-tab-disabled .x-tab-default-bottom-tl, +.x-tab.x-tab-disabled .x-tab-default-bottom-bl, +.x-tab.x-tab-disabled .x-tab-default-bottom-tr, +.x-tab.x-tab-disabled .x-tab-default-bottom-br, +.x-tab.x-tab-disabled .x-tab-default-bottom-tc, +.x-tab.x-tab-disabled .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-disabled-corners.gif); +} +.x-tab.x-tab-disabled .x-tab-default-bottom-ml, +.x-tab.x-tab-disabled .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-disabled-sides.gif); +} +.x-tab.x-tab-disabled .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-disabled-fbg.gif); +} +.x-tab-over .x-tab-default-left-tl, +.x-tab-over .x-tab-default-left-bl, +.x-tab-over .x-tab-default-left-tr, +.x-tab-over .x-tab-default-left-br, +.x-tab-over .x-tab-default-left-tc, +.x-tab-over .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-over-corners.gif); +} +.x-tab-over .x-tab-default-left-ml, +.x-tab-over .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-over-sides.gif); +} +.x-tab-over .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-over-fbg.gif); +} +.x-tab-focus .x-tab-default-left-tl, +.x-tab-focus .x-tab-default-left-bl, +.x-tab-focus .x-tab-default-left-tr, +.x-tab-focus .x-tab-default-left-br, +.x-tab-focus .x-tab-default-left-tc, +.x-tab-focus .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-focus-corners.gif); +} +.x-tab-focus .x-tab-default-left-ml, +.x-tab-focus .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-focus-sides.gif); +} +.x-tab-focus .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-focus-fbg.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-left-tl, +.x-tab-focus.x-tab-over .x-tab-default-left-bl, +.x-tab-focus.x-tab-over .x-tab-default-left-tr, +.x-tab-focus.x-tab-over .x-tab-default-left-br, +.x-tab-focus.x-tab-over .x-tab-default-left-tc, +.x-tab-focus.x-tab-over .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-focus-over-corners.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-left-ml, +.x-tab-focus.x-tab-over .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-focus-over-sides.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-focus-over-fbg.gif); +} +.x-tab.x-tab-active .x-tab-default-left-tl, +.x-tab.x-tab-active .x-tab-default-left-bl, +.x-tab.x-tab-active .x-tab-default-left-tr, +.x-tab.x-tab-active .x-tab-default-left-br, +.x-tab.x-tab-active .x-tab-default-left-tc, +.x-tab.x-tab-active .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-active-corners.gif); +} +.x-tab.x-tab-active .x-tab-default-left-ml, +.x-tab.x-tab-active .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-active-sides.gif); +} +.x-tab.x-tab-active .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-active-fbg.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-left-tl, +.x-tab-focus.x-tab-active .x-tab-default-left-bl, +.x-tab-focus.x-tab-active .x-tab-default-left-tr, +.x-tab-focus.x-tab-active .x-tab-default-left-br, +.x-tab-focus.x-tab-active .x-tab-default-left-tc, +.x-tab-focus.x-tab-active .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-focus-active-corners.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-left-ml, +.x-tab-focus.x-tab-active .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-focus-active-sides.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-focus-active-fbg.gif); +} +.x-tab.x-tab-disabled .x-tab-default-left-tl, +.x-tab.x-tab-disabled .x-tab-default-left-bl, +.x-tab.x-tab-disabled .x-tab-default-left-tr, +.x-tab.x-tab-disabled .x-tab-default-left-br, +.x-tab.x-tab-disabled .x-tab-default-left-tc, +.x-tab.x-tab-disabled .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-disabled-corners.gif); +} +.x-tab.x-tab-disabled .x-tab-default-left-ml, +.x-tab.x-tab-disabled .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-disabled-sides.gif); +} +.x-tab.x-tab-disabled .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-disabled-fbg.gif); +} +.x-tab-default .x-tab-close-btn { + top: 0; + right: 0; + width: 16px; + height: 16px; + font: 12px/1 FontAwesome; + color: #fff; +} +.x-tab-default .x-tab-close-btn:before { + content: "\f00d"; +} +.x-tab-bar-plain .x-tab-default .x-tab-close-btn { + color: #919191; +} +.x-tab-default .x-tab-close-btn-over { + background-position: -16px 0; +} +.x-tab-default .x-tab-close-btn-pressed { + background-position: -32px 0; +} +.x-keyboard-mode .x-tab-default.x-tab-focus .x-tab-close-btn { + color: #fff; +} +.x-keyboard-mode .x-tab-bar-plain .x-tab-default.x-tab-focus .x-tab-close-btn { + color: #919191; +} +.x-tab-default.x-tab-over .x-tab-close-btn { + color: #fff; +} +.x-tab-bar-plain .x-tab-default.x-tab-over .x-tab-close-btn { + color: #919191; +} +.x-keyboard-mode .x-tab-default.x-tab-focus.x-tab-over .x-tab-close-btn { + color: #fff; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-default.x-tab-focus.x-tab-over + .x-tab-close-btn { + color: #919191; +} +.x-tab-default.x-tab-active .x-tab-close-btn { + color: #919191; +} +.x-keyboard-mode .x-tab-default.x-tab-focus.x-tab-active .x-tab-close-btn { + color: #919191; +} +.x-tab-default.x-tab-disabled .x-tab-close-btn { + color: #fff; + opacity: 0.3; + background-position: 0 0; +} +.x-tab-bar-plain .x-tab-default.x-tab-disabled .x-tab-close-btn { + color: #919191; +} +.x-tab-closable.x-tab-default .x-tab-button { + padding-right: 16px; +} +.x-tab-bar-default { + background-color: #5aaed4; +} + +.x-tab-bar-default-top > .x-tab-bar-body-default { + padding: 8px 4px 0 8px; +} +.x-tab-bar-default-bottom > .x-tab-bar-body-default { + padding: 0 4px 8px 8px; +} +.x-tab-bar-default-left > .x-tab-bar-body-default { + padding: 4px 0 8px 8px; +} +.x-tab-bar-default-right > .x-tab-bar-body-default { + padding: 8px 8px 4px 0; +} +.x-tab-bar-plain.x-tab-bar-default-top > .x-tab-bar-body-default { + padding: 8px 0 0; +} +.x-tab-bar-plain.x-tab-bar-default-bottom > .x-tab-bar-body-default { + padding: 0 0 8px 0; +} +.x-tab-bar-plain.x-tab-bar-default-left > .x-tab-bar-body-default { + padding: 0 0 0 8px; +} +.x-tab-bar-plain.x-tab-bar-default-right > .x-tab-bar-body-default { + padding: 0 8px 0 0; +} +.x-tab-bar-plain.x-tab-bar-default-horizontal { + border-top-color: transparent; + border-bottom-color: transparent; + border-left-width: 0; + border-right-width: 0; +} +.x-tab-bar-plain.x-tab-bar-default-vertical { + border-right-color: transparent; + border-left-color: transparent; + border-top-width: 0; + border-bottom-width: 0; +} +.x-tab-bar-horizontal > .x-tab-bar-body-default { + min-height: 44px; +} +.x-ie8m .x-tab-bar-horizontal > .x-tab-bar-body-default { + min-height: 36px; +} +.x-tab-bar-vertical > .x-tab-bar-body-default { + min-width: 44px; +} +.x-ie8m .x-tab-bar-vertical > .x-tab-bar-body-default { + min-width: 36px; +} +.x-tab-bar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +.x-tab-bar-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 16px; +} +.x-box-scroller-tab-bar-default { + cursor: pointer; + color: #fff; + opacity: 0.5; +} +.x-box-scroller-tab-bar-default.x-box-scroller-hover { + opacity: 0.6; +} +.x-box-scroller-tab-bar-default.x-box-scroller-pressed { + opacity: 0.7; +} +.x-box-scroller-tab-bar-default.x-box-scroller-disabled { + opacity: 0.25; + cursor: default; +} +.x-box-scroller-tab-bar-default.x-box-scroller-left, +.x-box-scroller-tab-bar-default.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +.x-box-scroller-tab-bar-default.x-box-scroller-left { + margin-left: 0; + margin-right: 0; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-tab-bar-default.x-box-scroller-left:before { + content: "\f053"; +} +.x-box-scroller-tab-bar-default.x-box-scroller-right { + margin-left: 0; + margin-right: 0; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-tab-bar-default.x-box-scroller-right:before { + content: "\f054"; +} +.x-box-scroller-tab-bar-default.x-box-scroller-top, +.x-box-scroller-tab-bar-default.x-box-scroller-bottom { + height: 24px; + width: 24px; + left: 50%; + margin-left: -12px; +} +.x-box-scroller-tab-bar-default.x-box-scroller-top { + margin-top: 0; + margin-right: 0; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-tab-bar-default.x-box-scroller-top:before { + content: "\f077"; +} +.x-box-scroller-tab-bar-default.x-box-scroller-bottom { + margin-top: 0; + margin-right: 0; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-tab-bar-default.x-box-scroller-bottom:before { + content: "\f078"; +} +.x-tab-bar-more-icon { + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-tab-bar-more-icon:before { + content: "\f0c9"; +} +.x-tab-bar-plain.x-tab-bar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 24px; +} +.x-tab-bar-plain.x-tab-bar-default-vertical-scroller + .x-box-scroller-body-vertical { + margin-top: 16px; +} +.x-tab-bar-plain .x-box-scroller-tab-bar-default { + color: #919191; +} +.x-tab-bar-default-top .x-box-scroller-tab-bar-default { + margin-top: -8px; +} +.x-tab-bar-default-right .x-box-scroller-tab-bar-default { + margin-left: -16px; +} +.x-tab-bar-default-bottom .x-box-scroller-tab-bar-default { + margin-top: -16px; +} +.x-tab-bar-default-left .x-box-scroller-tab-bar-default { + margin-left: -8px; +} +.x-box-scroller-tab-bar-default { + background-color: #5aaed4; +} +.x-box-scroller-tab-bar-default .x-ie8 .x-box-scroller-plain { + background-color: #fff; +} +.x-btn-plain-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: transparent; +} +.x-btn-plain-toolbar-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-plain-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-plain-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-plain-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-plain-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-plain-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-plain-toolbar-small-br { + background-position: right -5px; +} +.x-btn-plain-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-plain-toolbar-small-mr { + background-position: right top; +} +.x-btn-plain-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-plain-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-plain-toolbar-small-tr, +.x-btn-plain-toolbar-small-br, +.x-btn-plain-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-plain-toolbar-small-tl, +.x-btn-plain-toolbar-small-bl, +.x-btn-plain-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-plain-toolbar-small-tc { + height: 1px; +} +.x-btn-plain-toolbar-small-bc { + height: 1px; +} +.x-btn-plain-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-plain-toolbar-small { + border-color: transparent; +} +.x-btn-button-plain-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-plain-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-plain-toolbar-small { + font: 500 12px/16px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-plain-toolbar-small { + max-width: none; +} +.x-btn-icon-el-plain-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-plain-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-plain-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-small, +.x-btn-split-bottom > .x-btn-button-plain-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-plain-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-plain-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-plain-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-plain-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-plain-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-plain-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-small { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-plain-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-plain-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-plain-toolbar-small { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-plain-toolbar-small, +.x-btn.x-btn-pressed.x-btn-plain-toolbar-small { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-plain-toolbar-small { + background-image: none; + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mc { + background-color: transparent; +} +.x-btn-over .x-btn-plain-toolbar-small-tl, +.x-btn-over .x-btn-plain-toolbar-small-bl, +.x-btn-over .x-btn-plain-toolbar-small-tr, +.x-btn-over .x-btn-plain-toolbar-small-br, +.x-btn-over .x-btn-plain-toolbar-small-tc, +.x-btn-over .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-plain-toolbar-small-ml, +.x-btn-over .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-plain-toolbar-small-mc { + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mc { + background-color: #ececec; +} +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mc { + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mc { + background-color: #e2e2e2; +} +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-plain-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-plain-toolbar-small { + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first + .x-btn-plain-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle + .x-btn-plain-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last + .x-btn-plain-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first + .x-btn-plain-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle + .x-btn-plain-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last + .x-btn-plain-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-plain-toolbar-medium { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 8px 8px 8px; + border-width: 1px; + border-style: solid; + background-color: transparent; +} +.x-btn-plain-toolbar-medium-mc { + background-color: transparent; +} +.x-nbr .x-btn-plain-toolbar-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-plain-toolbar-medium-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-8-8-8-8; +} +.x-btn-plain-toolbar-medium-tl { + background-position: 0 -2px; +} +.x-btn-plain-toolbar-medium-tr { + background-position: right -3px; +} +.x-btn-plain-toolbar-medium-bl { + background-position: 0 -4px; +} +.x-btn-plain-toolbar-medium-br { + background-position: right -5px; +} +.x-btn-plain-toolbar-medium-ml { + background-position: 0 top; +} +.x-btn-plain-toolbar-medium-mr { + background-position: right top; +} +.x-btn-plain-toolbar-medium-tc { + background-position: 0 0; +} +.x-btn-plain-toolbar-medium-bc { + background-position: 0 -1px; +} +.x-btn-plain-toolbar-medium-tr, +.x-btn-plain-toolbar-medium-br, +.x-btn-plain-toolbar-medium-mr { + padding-right: 1px; +} +.x-btn-plain-toolbar-medium-tl, +.x-btn-plain-toolbar-medium-bl, +.x-btn-plain-toolbar-medium-ml { + padding-left: 1px; +} +.x-btn-plain-toolbar-medium-tc { + height: 1px; +} +.x-btn-plain-toolbar-medium-bc { + height: 1px; +} +.x-btn-plain-toolbar-medium-mc { + padding: 8px 8px 8px 8px; +} +.x-btn-plain-toolbar-medium { + border-color: transparent; +} +.x-btn-button-plain-toolbar-medium { + min-height: 20px; +} +.x-ie9m .x-btn-button-plain-toolbar-medium { + min-height: auto; + height: 20px; +} +.x-btn-inner-plain-toolbar-medium { + font: 500 14px/18px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #606060; + padding: 0 8px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium { + max-width: calc(100% - 20px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium { + max-width: calc(100% - 19px); +} +.x-ie10p .x-btn-inner-plain-toolbar-medium { + max-width: none; +} +.x-btn-icon-el-plain-toolbar-medium { + font-size: 20px; + height: 20px; + color: #919191; + line-height: 20px; +} +.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium, +.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + width: 20px; +} +.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium, +.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium { + min-width: 20px; +} +.x-ie8 .x-btn-icon-el-plain-toolbar-medium.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium { + margin-right: 0px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + margin-left: 0px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-plain-toolbar-medium { + margin-right: 8px; +} +.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-medium, +.x-btn-split-bottom > .x-btn-button-plain-toolbar-medium { + padding-bottom: 8px; +} +.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-right:after { + width: 20px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-bottom:after { + height: 14px; + content: "\f0d7"; + font: 20px/14px FontAwesome; + color: #606060; +} +.x-btn-wrap-plain-toolbar-medium.x-btn-split-right > .x-btn-button { + padding-right: 8px; +} +.x-btn-wrap-plain-toolbar-medium.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-plain-toolbar-medium.x-btn-split-right:after { + width: 26px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; + padding-left: 8px; +} +.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom { + margin-bottom: -8px; +} +.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom:after { + height: 24px; + content: "\f0d7"; + font: 20px/24px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-plain-toolbar-medium { + margin-right: 8px; +} +.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-medium { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-plain-toolbar-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 34px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-plain-toolbar-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-plain-toolbar-medium { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-plain-toolbar-medium, +.x-btn.x-btn-pressed.x-btn-plain-toolbar-medium { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-plain-toolbar-medium { + background-image: none; + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mc { + background-color: transparent; +} +.x-btn-over .x-btn-plain-toolbar-medium-tl, +.x-btn-over .x-btn-plain-toolbar-medium-bl, +.x-btn-over .x-btn-plain-toolbar-medium-tr, +.x-btn-over .x-btn-plain-toolbar-medium-br, +.x-btn-over .x-btn-plain-toolbar-medium-tc, +.x-btn-over .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-over-corners.gif); +} +.x-btn-over .x-btn-plain-toolbar-medium-ml, +.x-btn-over .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-over-sides.gif); +} +.x-btn-over .x-btn-plain-toolbar-medium-mc { + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mc { + background-color: #ececec; +} +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tr, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-br, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tc, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-br, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-ml, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-ml, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mc { + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mc { + background-color: #e2e2e2; +} +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tr, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-br, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tc, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-ml, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mc { + background-color: transparent; +} +.x-nbr .x-btn-plain-toolbar-medium { + background-image: none; +} +.x-btn-disabled.x-btn-plain-toolbar-medium { + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first + .x-btn-plain-toolbar-medium-mc { + padding-right: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle + .x-btn-plain-toolbar-medium-mc { + padding-right: 8px !important; + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last + .x-btn-plain-toolbar-medium-mc { + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first + .x-btn-plain-toolbar-medium-mc { + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle + .x-btn-plain-toolbar-medium-mc { + padding-top: 8px !important; + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last + .x-btn-plain-toolbar-medium-mc { + padding-top: 8px !important; +} +.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-medium:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-medium:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-plain-toolbar-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: transparent; +} +.x-btn-plain-toolbar-large-mc { + background-color: transparent; +} +.x-nbr .x-btn-plain-toolbar-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-plain-toolbar-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +.x-btn-plain-toolbar-large-tl { + background-position: 0 -2px; +} +.x-btn-plain-toolbar-large-tr { + background-position: right -3px; +} +.x-btn-plain-toolbar-large-bl { + background-position: 0 -4px; +} +.x-btn-plain-toolbar-large-br { + background-position: right -5px; +} +.x-btn-plain-toolbar-large-ml { + background-position: 0 top; +} +.x-btn-plain-toolbar-large-mr { + background-position: right top; +} +.x-btn-plain-toolbar-large-tc { + background-position: 0 0; +} +.x-btn-plain-toolbar-large-bc { + background-position: 0 -1px; +} +.x-btn-plain-toolbar-large-tr, +.x-btn-plain-toolbar-large-br, +.x-btn-plain-toolbar-large-mr { + padding-right: 1px; +} +.x-btn-plain-toolbar-large-tl, +.x-btn-plain-toolbar-large-bl, +.x-btn-plain-toolbar-large-ml { + padding-left: 1px; +} +.x-btn-plain-toolbar-large-tc { + height: 1px; +} +.x-btn-plain-toolbar-large-bc { + height: 1px; +} +.x-btn-plain-toolbar-large-mc { + padding: 9px 9px 9px 9px; +} +.x-btn-plain-toolbar-large { + border-color: transparent; +} +.x-btn-button-plain-toolbar-large { + min-height: 24px; +} +.x-ie9m .x-btn-button-plain-toolbar-large { + min-height: auto; + height: 24px; +} +.x-btn-inner-plain-toolbar-large { + font: 500 16px/20px "Helvetica Neue", helvetica, arial, verdana, + sans-serif ; + color: #606060; + padding: 0 10px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-large { + max-width: calc(100% - 24px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-large { + max-width: calc(100% - 23px); +} +.x-ie10p .x-btn-inner-plain-toolbar-large { + max-width: none; +} +.x-btn-icon-el-plain-toolbar-large { + font-size: 24px; + height: 24px; + color: #919191; + line-height: 24px; +} +.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large, +.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + width: 24px; +} +.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large, +.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large { + min-width: 24px; +} +.x-ie8 .x-btn-icon-el-plain-toolbar-large.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large { + margin-right: 0; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + margin-left: 0; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-plain-toolbar-large { + margin-right: 10px; +} +.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-large, +.x-btn-split-bottom > .x-btn-button-plain-toolbar-large { + padding-bottom: 9px; +} +.x-btn-wrap-plain-toolbar-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-plain-toolbar-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #606060; +} +.x-btn-wrap-plain-toolbar-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +.x-btn-wrap-plain-toolbar-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-plain-toolbar-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; + padding-left: 9px; +} +.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom { + margin-bottom: -9px; +} +.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-plain-toolbar-large { + margin-right: 10px; +} +.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-large { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-plain-toolbar-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-plain-toolbar-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-plain-toolbar-large { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-large { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-plain-toolbar-large, +.x-btn.x-btn-pressed.x-btn-plain-toolbar-large { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-plain-toolbar-large { + background-image: none; + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mc { + background-color: transparent; +} +.x-btn-over .x-btn-plain-toolbar-large-tl, +.x-btn-over .x-btn-plain-toolbar-large-bl, +.x-btn-over .x-btn-plain-toolbar-large-tr, +.x-btn-over .x-btn-plain-toolbar-large-br, +.x-btn-over .x-btn-plain-toolbar-large-tc, +.x-btn-over .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-over-corners.gif); +} +.x-btn-over .x-btn-plain-toolbar-large-ml, +.x-btn-over .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-over-sides.gif); +} +.x-btn-over .x-btn-plain-toolbar-large-mc { + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mc { + background-color: #ececec; +} +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tr, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-br, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tc, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-br, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-ml, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-ml, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mc { + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mc { + background-color: #e2e2e2; +} +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tr, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-br, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tc, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-disabled-corners.gif); +} +.x-toolbar-tools { + background-color: #f5f5f5; + background-image: none; + border-color: #767676; + box-shadow: 0 4px 2px -3px rgba(0, 0, 0, 0.2) inset; +} +.x-toolbar-tools .x-title { + color: #333; +} +.x-toolbar-flat { + background-color: transparent; + background-image: none; + border-color: transparent; +} + +.x-button .x-button-el { + opacity: 0; + outline: none; + cursor: pointer; + z-index: 3; + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; + width: 100%; + height: 100%; + border: 0; + margin: 0; + padding: 0; +} +.x-button-flat { + color: #f0f0f0; +} +.x-button-flat .x-inner-el { + border-width: 0; + border-color: transparent; + background-color: transparent; + background-image: none; +} +.x-button-flat .x-icon-el { + color: #f0f0f0; +} +.x-button-flat .x-arrow-el { + color: #f0f0f0; +} +.x-button-flat.x-hovered { + color: #f0f0f0; +} +.x-button-flat.x-hovered .x-inner-el { + border-color: transparent; + background-color: transparent; + background-image: none; +} +.x-button-flat.x-hovered .x-icon-el { + color: #f0f0f0; +} +.x-button-flat.x-hovered .x-arrow-el { + color: #f0f0f0; +} +.x-button-flat.x-pressing, +.x-button-flat.x-pressed { + color: #f0f0f0; +} +.x-button-flat.x-pressing .x-inner-el, +.x-button-flat.x-pressed .x-inner-el { + border-color: transparent; + background-color: transparent; + background-image: none; +} +.x-button-flat.x-pressing .x-icon-el, +.x-button-flat.x-pressed .x-icon-el { + color: #f0f0f0; +} +.x-button-flat.x-pressing .x-arrow-el, +.x-button-flat.x-pressed .x-arrow-el { + color: #f0f0f0; +} +.x-keyboard-mode .x-button-flat.x-focused:after { + border-color: rgba(240, 240, 240, 0.8); +} +/* Navigation */ + .navigationTabPanel .x-tab-bar-default-top { + background : transparent; + background-image: none !important; +} +.navigationTabPanel .x-tab-bar-default-top { + border-width: 0; + /* fix for border top */ +} +.navigationTabPanel .x-tab-bar-body a { + background-image: none !important; + box-shadow: none; + border: 0; + border-top-right-radius: 7px; + border-top-left-radius: 7px; + padding: 10px 25px 0; +} +.navigationTabPanel .x-tab-bar-body .x-table-plain td { + background : transparent !important; + background-image: none !important; +} +.navigationTabPanel .x-tab-bar-body .x-tab-default-top-active { + background : #f7fafc !important; + border-color: #ffffff !important; + border-width: 1px 1px 0 1px !important; + border-style: solid; +} +.navigationTabPanel .x-tab.x-tab-active.x-tab-default { + background : #f7fafc !important; +} + +.navigationTabPanel .x-tab-bar-body .x-tab-default-top { + background :#c4c4c4 ; +} +.navigationTabPanel .x-tab-bar-body-default-top { + padding-bottom :0; +} +.navigationTabPanel .x-tab-default-top { + border-bottom : 0; +} +/* change the height of tabs */ + .navigationTabPanel .x-tab-bar-strip { + display : none !important; + /* no border between */ +} +.navigationTabPanel .x-tab-bar .x-tab-bar-body { + height: 37px !important; + /* default is 23 */ + border: 0 !important; +} +.navigationTabPanel .x-tab-bar .x-tab-bar-body .x-box-inner { + height: 35px !important; + /* default is 21 */ +} +.navigationTabPanel .x-tab-bar .x-tab-bar-body .x-box-inner .x-tab { + height: 35px !important; + box-shadow: none; + /* default is 21 */ +} +.navigationTabPanel .x-tab-bar .x-tab-bar-body .x-box-inner .x-tab button { + height: 37px !important; + line-height: 37px !important; +} +.navigationTabPanel .x-tab-center { + margin-top: -10px; +} +.navigationTabPanelBody { + background : #f7fafc; + border-color: #ffffff; + border-width: 0 1px 1px 1px; + border-style: solid; + -webkit-border-radius: 5px; + -webkit-border-top-left-radius: 0; + -moz-border-radius: 5px; + -moz-border-radius-topleft: 0; + border-radius: 5px; + border-top-left-radius: 0; + padding : 20px 10px 10px; +} +.navigationTabPanelBody .x-panel-body-default { + background : transparent; +} +.wordWrap { + word-wrap: break-word; /* IE 5.5-7 */ + white-space: -moz-pre-wrap; /* Firefox 1.0-2.0 */ + white-space: pre-wrap; /* current browsers */ +} + +.triangle-left { + width: 0; + height: 0; + border-top: 20px solid transparent; + border-right: 20px solid red; + border-bottom: 20px solid transparent; +} + +.switch { + position: relative; + display: inline-block; + width: 40px; + height: 24px; +} + +.switch input { + opacity: 0; + width: 0; + height: 0; +} + +.slider { + position: absolute; + cursor: pointer; + top: 0; + left: 0; + right: 0; + bottom: 0; + background-color: #ccc; + -webkit-transition: .4s; + transition: .4s; +} + +.slider:before { + position: absolute; + content: ""; + height: 16px; + width: 16px; + left: 4px; + bottom: 4px; + background-color: white; + -webkit-transition: .4s; + transition: .4s; +} + +input:checked + .slider { + background-color: #2196F3; +} + +input:focus + .slider { + box-shadow: 0 0 1px #2196F3; +} + +input:checked + .slider:before { + -webkit-transform: translateX(16px); + -ms-transform: translateX(16px); + transform: translateX(16px); +} + +/* Rounded sliders */ +.slider.round { + border-radius: 34px; +} + +.slider.round:before { + border-radius: 50%; +} \ No newline at end of file diff --git a/src/main/webapp/resources/css/adminDashboardCSS/Admin-all_2.css b/src/main/webapp/resources/css/adminDashboardCSS/Admin-all_2.css new file mode 100644 index 0000000..cb7e18b --- /dev/null +++ b/src/main/webapp/resources/css/adminDashboardCSS/Admin-all_2.css @@ -0,0 +1,12178 @@ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-ml, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mc { + background-color: transparent; +} +.x-nbr .x-btn-plain-toolbar-large { + background-image: none; +} +.x-btn-disabled.x-btn-plain-toolbar-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first + .x-btn-plain-toolbar-large-mc { + padding-right: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle + .x-btn-plain-toolbar-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last + .x-btn-plain-toolbar-large-mc { + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first + .x-btn-plain-toolbar-large-mc { + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle + .x-btn-plain-toolbar-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last + .x-btn-plain-toolbar-large-mc { + padding-top: 9px !important; +} +.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-large:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-large:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-large:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-plain-toolbar-small-disabled .x-btn-icon-el, +.x-btn-plain-toolbar-medium-disabled .x-btn-icon-el, +.x-btn-plain-toolbar-large-disabled .x-btn-icon-el { + background-color: #fff; +} +.x-ie8 .x-btn-plain-toolbar-small-disabled .x-btn-icon-el, +.x-ie8 .x-btn-plain-toolbar-medium-disabled .x-btn-icon-el, +.x-ie8 .x-btn-plain-toolbar-large-disabled .x-btn-icon-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-panel-light { + border-color: #d0d0d0; + padding: 0; +} +.x-panel-light.x-masked { + border-color: #e8e8e8; +} +.x-panel-header-light { + font-size: 16px; + border: 1px solid #d0d0d0; +} +.x-panel-header-light .x-tool-tool-el { + color: #919191; +} +.x-panel-header-light .x-tool-tool-el { + background-color: #fff; +} +.x-panel-header-light-horizontal { + padding: 11px 15px 12px; +} +.x-panel-header-light-horizontal .x-panel-header-light-tab-bar { + margin-top: -11px; + margin-bottom: -12px; +} +.x-panel-header-light-horizontal.x-header-noborder { + padding: 12px 16px 12px 16px; +} +.x-panel-header-light-horizontal.x-header-noborder + .x-panel-header-light-tab-bar { + margin-top: -12px; + margin-bottom: -12px; +} +.x-panel-header-light-vertical { + padding: 15px 11px 15px 12px; +} +.x-panel-header-light-vertical .x-panel-header-light-tab-bar { + margin-right: -11px; + margin-left: -12px; +} +.x-panel-header-light-vertical.x-header-noborder { + padding: 16px 12px 16px 12px; +} +.x-panel-header-light-vertical.x-header-noborder .x-panel-header-light-tab-bar { + margin-right: -12px; + margin-left: -12px; +} +.x-panel-header-title-light { + color: #606060; + font-size: 16px; + font-weight: 500; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 20px; +} +.x-keyboard-mode .x-panel-header-title-light.x-title-focus { + outline: 1px solid #5aaed4; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5aaed4; + pointer-events: none; +} +.x-panel-header-title-light > .x-title-text-light { + text-transform: none; + padding: 0; +} +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +.x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light { + width: 16px; + height: 16px; + font-size: 16px; + color: #606060; + background-position: center center; +} +.x-ie8 + .x-panel-header-title-light + > .x-title-icon-wrap-light + > .x-title-icon-light.x-title-glyph { + color: #606060; +} +.x-panel-body-light { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 13px; + font-weight: 400; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + border-width: 1px; + border-style: solid; +} +.x-panel-header-light { + background-image: none; + background-color: #fff; +} +.x-panel-header-light-vertical { + background-image: none; + background-color: #fff; +} +.x-panel .x-panel-header-light-collapsed-border-top { + border-bottom-width: 1px !important; +} +.x-panel .x-panel-header-light-collapsed-border-right { + border-left-width: 1px !important; +} +.x-panel .x-panel-header-light-collapsed-border-bottom { + border-top-width: 1px !important; +} +.x-panel .x-panel-header-light-collapsed-border-left { + border-right-width: 1px !important; +} +.x-panel-header-light-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-panel-header-light-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-panel-header-light-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +.x-panel-header-light-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +.x-keyboard-mode .x-panel-header-light .x-tool-focus { + outline: 1px solid #5aaed4; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5aaed4; + pointer-events: none; +} +.x-panel-light-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +.x-panel-light-outer-border-l { + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +.x-panel-light-outer-border-b { + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; +} +.x-panel-light-outer-border-bl { + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +.x-panel-light-outer-border-r { + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; +} +.x-panel-light-outer-border-rl { + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +.x-panel-light-outer-border-rb { + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; +} +.x-panel-light-outer-border-rbl { + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +.x-panel-light-outer-border-t { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; +} +.x-panel-light-outer-border-tl { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +.x-panel-light-outer-border-tb { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; +} +.x-panel-light-outer-border-tbl { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +.x-panel-light-outer-border-tr { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; +} +.x-panel-light-outer-border-trl { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +.x-panel-light-outer-border-trb { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; +} +.x-panel-light-outer-border-trbl { + border-color: #d0d0d0 !important; + border-width: 1px !important; +} +.x-panel-light-framed { + border-color: #d0d0d0; + padding: 0; +} +.x-panel-light-framed.x-masked { + border-color: #e8e8e8; +} +.x-panel-header-light-framed { + font-size: 16px; + border: 2px solid #d0d0d0; +} +.x-panel-header-light-framed .x-tool-tool-el { + color: #919191; +} +.x-panel-header-light-framed .x-tool-tool-el { + background-color: #fff; +} +.x-panel-header-light-framed-horizontal { + padding: 10px 14px 10px 14px; +} +.x-panel-header-light-framed-horizontal .x-panel-header-light-framed-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +.x-panel-header-light-framed-horizontal.x-header-noborder { + padding: 12px 16px 10px 16px; +} +.x-panel-header-light-framed-horizontal.x-header-noborder + .x-panel-header-light-framed-tab-bar { + margin-top: -12px; + margin-bottom: -10px; +} +.x-panel-header-light-framed-vertical { + padding: 14px 10px 14px 10px; +} +.x-panel-header-light-framed-vertical .x-panel-header-light-framed-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +.x-panel-header-light-framed-vertical.x-header-noborder { + padding: 16px 12px 16px 10px; +} +.x-panel-header-light-framed-vertical.x-header-noborder + .x-panel-header-light-framed-tab-bar { + margin-right: -12px; + margin-left: -10px; +} +.x-panel-header-title-light-framed { + color: #606060; + font-size: 16px; + font-weight: 500; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 20px; +} +.x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus { + outline: 1px solid #5aaed4; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after, +.x-ie10p + .x-keyboard-mode + .x-panel-header-title-light-framed.x-title-focus:after, +.x-edge + .x-keyboard-mode + .x-panel-header-title-light-framed.x-title-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5aaed4; + pointer-events: none; +} +.x-panel-header-title-light-framed > .x-title-text-light-framed { + text-transform: none; + padding: 0; +} +.x-panel-header-title-light-framed + > .x-title-icon-wrap-light-framed.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +.x-panel-header-title-light-framed + > .x-title-icon-wrap-light-framed.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +.x-panel-header-title-light-framed + > .x-title-icon-wrap-light-framed.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +.x-panel-header-title-light-framed + > .x-title-icon-wrap-light-framed.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +.x-panel-header-title-light-framed + > .x-title-icon-wrap-light-framed + > .x-title-icon-light-framed { + width: 16px; + height: 16px; + font-size: 16px; + color: #606060; + background-position: center center; +} +.x-ie8 + .x-panel-header-title-light-framed + > .x-title-icon-wrap-light-framed + > .x-title-icon-light-framed.x-title-glyph { + color: #606060; +} +.x-panel-body-light-framed { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 13px; + font-weight: 400; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + border-width: 1px; + border-style: solid; +} +.x-panel-light-framed { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 0 0 0 0; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-light-framed-mc { + background-color: #fff; +} +.x-nbr .x-panel-light-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-light-framed-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-0px-0px-0px-0px; +} +.x-panel-light-framed-tl { + background-position: 0 -4px; +} +.x-panel-light-framed-tr { + background-position: right -6px; +} +.x-panel-light-framed-bl { + background-position: 0 -8px; +} +.x-panel-light-framed-br { + background-position: right -10px; +} +.x-panel-light-framed-ml { + background-position: 0 top; +} +.x-panel-light-framed-mr { + background-position: right top; +} +.x-panel-light-framed-tc { + background-position: 0 0; +} +.x-panel-light-framed-bc { + background-position: 0 -2px; +} +.x-panel-light-framed-tr, +.x-panel-light-framed-br, +.x-panel-light-framed-mr { + padding-right: 2px; +} +.x-panel-light-framed-tl, +.x-panel-light-framed-bl, +.x-panel-light-framed-ml { + padding-left: 2px; +} +.x-panel-light-framed-tc { + height: 2px; +} +.x-panel-light-framed-bc { + height: 2px; +} +.x-panel-light-framed-tl, +.x-panel-light-framed-bl, +.x-panel-light-framed-tr, +.x-panel-light-framed-br, +.x-panel-light-framed-tc, +.x-panel-light-framed-bc, +.x-panel-light-framed-ml, +.x-panel-light-framed-mr { + background-image: url(images/panel/panel-light-framed-corners.gif); +} +.x-panel-light-framed-ml, +.x-panel-light-framed-mr { + background-image: url(images/panel/panel-light-framed-sides.gif); + background-repeat: repeat-y; +} +.x-panel-light-framed-mc { + padding: 0px 0px 0px 0px; +} +.x-panel-header-light-framed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 0 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-header-light-framed-top-mc { + background-color: #fff; +} +.x-nbr .x-panel-header-light-framed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-light-framed-top-frameInfo { + font-family: dh-2-2-0-2-2-2-0-2-10-14-10-14; +} +.x-panel-header-light-framed-top-tl { + background-position: 0 -4px; +} +.x-panel-header-light-framed-top-tr { + background-position: right -6px; +} +.x-panel-header-light-framed-top-bl { + background-position: 0 -8px; +} +.x-panel-header-light-framed-top-br { + background-position: right -10px; +} +.x-panel-header-light-framed-top-ml { + background-position: 0 top; +} +.x-panel-header-light-framed-top-mr { + background-position: right top; +} +.x-panel-header-light-framed-top-tc { + background-position: 0 0; +} +.x-panel-header-light-framed-top-bc { + background-position: 0 -2px; +} +.x-panel-header-light-framed-top-tr, +.x-panel-header-light-framed-top-br, +.x-panel-header-light-framed-top-mr { + padding-right: 2px; +} +.x-panel-header-light-framed-top-tl, +.x-panel-header-light-framed-top-bl, +.x-panel-header-light-framed-top-ml { + padding-left: 2px; +} +.x-panel-header-light-framed-top-tc { + height: 2px; +} +.x-panel-header-light-framed-top-bc { + height: 0; +} +.x-panel-header-light-framed-top-tl, +.x-panel-header-light-framed-top-bl, +.x-panel-header-light-framed-top-tr, +.x-panel-header-light-framed-top-br, +.x-panel-header-light-framed-top-tc, +.x-panel-header-light-framed-top-bc, +.x-panel-header-light-framed-top-ml, +.x-panel-header-light-framed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-top-corners.gif); +} +.x-panel-header-light-framed-top-ml, +.x-panel-header-light-framed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-top-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-light-framed-top-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-light-framed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 0; + border-style: solid; + background-color: #fff; +} +.x-panel-header-light-framed-right-mc { + background-color: #fff; +} +.x-nbr .x-panel-header-light-framed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-light-framed-right-frameInfo { + font-family: dh-2-2-2-0-2-2-2-0-14-10-14-10; +} +.x-panel-header-light-framed-right-tl { + background-position: 0 -4px; +} +.x-panel-header-light-framed-right-tr { + background-position: right -6px; +} +.x-panel-header-light-framed-right-bl { + background-position: 0 -8px; +} +.x-panel-header-light-framed-right-br { + background-position: right -10px; +} +.x-panel-header-light-framed-right-ml { + background-position: right 0; +} +.x-panel-header-light-framed-right-mr { + background-position: right 0; +} +.x-panel-header-light-framed-right-tc { + background-position: 0 0; +} +.x-panel-header-light-framed-right-bc { + background-position: 0 -2px; +} +.x-panel-header-light-framed-right-tr, +.x-panel-header-light-framed-right-br, +.x-panel-header-light-framed-right-mr { + padding-right: 2px; +} +.x-panel-header-light-framed-right-tl, +.x-panel-header-light-framed-right-bl, +.x-panel-header-light-framed-right-ml { + padding-left: 0; +} +.x-panel-header-light-framed-right-tc { + height: 2px; +} +.x-panel-header-light-framed-right-bc { + height: 2px; +} +.x-panel-header-light-framed-right-tl, +.x-panel-header-light-framed-right-bl, +.x-panel-header-light-framed-right-tr, +.x-panel-header-light-framed-right-br, +.x-panel-header-light-framed-right-tc, +.x-panel-header-light-framed-right-bc, +.x-panel-header-light-framed-right-ml, +.x-panel-header-light-framed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-right-corners.gif); +} +.x-panel-header-light-framed-right-ml, +.x-panel-header-light-framed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-right-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-light-framed-right-mc { + padding: 14px 10px 14px 10px; +} +.x-panel-header-light-framed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 0 2px 2px 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-header-light-framed-bottom-mc { + background-color: #fff; +} +.x-nbr .x-panel-header-light-framed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-light-framed-bottom-frameInfo { + font-family: dh-0-2-2-2-0-2-2-2-10-14-10-14; +} +.x-panel-header-light-framed-bottom-tl { + background-position: 0 -4px; +} +.x-panel-header-light-framed-bottom-tr { + background-position: right -6px; +} +.x-panel-header-light-framed-bottom-bl { + background-position: 0 -8px; +} +.x-panel-header-light-framed-bottom-br { + background-position: right -10px; +} +.x-panel-header-light-framed-bottom-ml { + background-position: 0 bottom; +} +.x-panel-header-light-framed-bottom-mr { + background-position: right bottom; +} +.x-panel-header-light-framed-bottom-tc { + background-position: 0 0; +} +.x-panel-header-light-framed-bottom-bc { + background-position: 0 -2px; +} +.x-panel-header-light-framed-bottom-tr, +.x-panel-header-light-framed-bottom-br, +.x-panel-header-light-framed-bottom-mr { + padding-right: 2px; +} +.x-panel-header-light-framed-bottom-tl, +.x-panel-header-light-framed-bottom-bl, +.x-panel-header-light-framed-bottom-ml { + padding-left: 2px; +} +.x-panel-header-light-framed-bottom-tc { + height: 0; +} +.x-panel-header-light-framed-bottom-bc { + height: 2px; +} +.x-panel-header-light-framed-bottom-tl, +.x-panel-header-light-framed-bottom-bl, +.x-panel-header-light-framed-bottom-tr, +.x-panel-header-light-framed-bottom-br, +.x-panel-header-light-framed-bottom-tc, +.x-panel-header-light-framed-bottom-bc, +.x-panel-header-light-framed-bottom-ml, +.x-panel-header-light-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-bottom-corners.gif); +} +.x-panel-header-light-framed-bottom-ml, +.x-panel-header-light-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-light-framed-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-light-framed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 0 2px 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-header-light-framed-left-mc { + background-color: #fff; +} +.x-nbr .x-panel-header-light-framed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-light-framed-left-frameInfo { + font-family: dh-2-0-2-2-2-0-2-2-14-10-14-10; +} +.x-panel-header-light-framed-left-tl { + background-position: 0 -4px; +} +.x-panel-header-light-framed-left-tr { + background-position: right -6px; +} +.x-panel-header-light-framed-left-bl { + background-position: 0 -8px; +} +.x-panel-header-light-framed-left-br { + background-position: right -10px; +} +.x-panel-header-light-framed-left-ml { + background-position: left 0; +} +.x-panel-header-light-framed-left-mr { + background-position: left 0; +} +.x-panel-header-light-framed-left-tc { + background-position: 0 0; +} +.x-panel-header-light-framed-left-bc { + background-position: 0 -2px; +} +.x-panel-header-light-framed-left-tr, +.x-panel-header-light-framed-left-br, +.x-panel-header-light-framed-left-mr { + padding-right: 0; +} +.x-panel-header-light-framed-left-tl, +.x-panel-header-light-framed-left-bl, +.x-panel-header-light-framed-left-ml { + padding-left: 2px; +} +.x-panel-header-light-framed-left-tc { + height: 2px; +} +.x-panel-header-light-framed-left-bc { + height: 2px; +} +.x-panel-header-light-framed-left-tl, +.x-panel-header-light-framed-left-bl, +.x-panel-header-light-framed-left-tr, +.x-panel-header-light-framed-left-br, +.x-panel-header-light-framed-left-tc, +.x-panel-header-light-framed-left-bc, +.x-panel-header-light-framed-left-ml, +.x-panel-header-light-framed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-left-corners.gif); +} +.x-panel-header-light-framed-left-ml, +.x-panel-header-light-framed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-left-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-light-framed-left-mc { + padding: 14px 10px 14px 10px; +} +.x-panel-header-light-framed-collapsed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-header-light-framed-collapsed-top-mc { + background-color: #fff; +} +.x-nbr .x-panel-header-light-framed-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-light-framed-collapsed-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-panel-header-light-framed-collapsed-top-tl { + background-position: 0 -4px; +} +.x-panel-header-light-framed-collapsed-top-tr { + background-position: right -6px; +} +.x-panel-header-light-framed-collapsed-top-bl { + background-position: 0 -8px; +} +.x-panel-header-light-framed-collapsed-top-br { + background-position: right -10px; +} +.x-panel-header-light-framed-collapsed-top-ml { + background-position: 0 top; +} +.x-panel-header-light-framed-collapsed-top-mr { + background-position: right top; +} +.x-panel-header-light-framed-collapsed-top-tc { + background-position: 0 0; +} +.x-panel-header-light-framed-collapsed-top-bc { + background-position: 0 -2px; +} +.x-panel-header-light-framed-collapsed-top-tr, +.x-panel-header-light-framed-collapsed-top-br, +.x-panel-header-light-framed-collapsed-top-mr { + padding-right: 2px; +} +.x-panel-header-light-framed-collapsed-top-tl, +.x-panel-header-light-framed-collapsed-top-bl, +.x-panel-header-light-framed-collapsed-top-ml { + padding-left: 2px; +} +.x-panel-header-light-framed-collapsed-top-tc { + height: 2px; +} +.x-panel-header-light-framed-collapsed-top-bc { + height: 2px; +} +.x-panel-header-light-framed-collapsed-top-tl, +.x-panel-header-light-framed-collapsed-top-bl, +.x-panel-header-light-framed-collapsed-top-tr, +.x-panel-header-light-framed-collapsed-top-br, +.x-panel-header-light-framed-collapsed-top-tc, +.x-panel-header-light-framed-collapsed-top-bc, +.x-panel-header-light-framed-collapsed-top-ml, +.x-panel-header-light-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-top-corners.gif); +} +.x-panel-header-light-framed-collapsed-top-ml, +.x-panel-header-light-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-light-framed-collapsed-top-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-light-framed-collapsed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-header-light-framed-collapsed-right-mc { + background-color: #fff; +} +.x-nbr .x-panel-header-light-framed-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-light-framed-collapsed-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-panel-header-light-framed-collapsed-right-tl { + background-position: 0 -4px; +} +.x-panel-header-light-framed-collapsed-right-tr { + background-position: right -6px; +} +.x-panel-header-light-framed-collapsed-right-bl { + background-position: 0 -8px; +} +.x-panel-header-light-framed-collapsed-right-br { + background-position: right -10px; +} +.x-panel-header-light-framed-collapsed-right-ml { + background-position: right 0; +} +.x-panel-header-light-framed-collapsed-right-mr { + background-position: right 0; +} +.x-panel-header-light-framed-collapsed-right-tc { + background-position: 0 0; +} +.x-panel-header-light-framed-collapsed-right-bc { + background-position: 0 -2px; +} +.x-panel-header-light-framed-collapsed-right-tr, +.x-panel-header-light-framed-collapsed-right-br, +.x-panel-header-light-framed-collapsed-right-mr { + padding-right: 2px; +} +.x-panel-header-light-framed-collapsed-right-tl, +.x-panel-header-light-framed-collapsed-right-bl, +.x-panel-header-light-framed-collapsed-right-ml { + padding-left: 2px; +} +.x-panel-header-light-framed-collapsed-right-tc { + height: 2px; +} +.x-panel-header-light-framed-collapsed-right-bc { + height: 2px; +} +.x-panel-header-light-framed-collapsed-right-tl, +.x-panel-header-light-framed-collapsed-right-bl, +.x-panel-header-light-framed-collapsed-right-tr, +.x-panel-header-light-framed-collapsed-right-br, +.x-panel-header-light-framed-collapsed-right-tc, +.x-panel-header-light-framed-collapsed-right-bc, +.x-panel-header-light-framed-collapsed-right-ml, +.x-panel-header-light-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-right-corners.gif); +} +.x-panel-header-light-framed-collapsed-right-ml, +.x-panel-header-light-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-light-framed-collapsed-right-mc { + padding: 14px 10px 14px 10px; +} +.x-panel-header-light-framed-collapsed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-header-light-framed-collapsed-bottom-mc { + background-color: #fff; +} +.x-nbr .x-panel-header-light-framed-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-light-framed-collapsed-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-panel-header-light-framed-collapsed-bottom-tl { + background-position: 0 -4px; +} +.x-panel-header-light-framed-collapsed-bottom-tr { + background-position: right -6px; +} +.x-panel-header-light-framed-collapsed-bottom-bl { + background-position: 0 -8px; +} +.x-panel-header-light-framed-collapsed-bottom-br { + background-position: right -10px; +} +.x-panel-header-light-framed-collapsed-bottom-ml { + background-position: 0 bottom; +} +.x-panel-header-light-framed-collapsed-bottom-mr { + background-position: right bottom; +} +.x-panel-header-light-framed-collapsed-bottom-tc { + background-position: 0 0; +} +.x-panel-header-light-framed-collapsed-bottom-bc { + background-position: 0 -2px; +} +.x-panel-header-light-framed-collapsed-bottom-tr, +.x-panel-header-light-framed-collapsed-bottom-br, +.x-panel-header-light-framed-collapsed-bottom-mr { + padding-right: 2px; +} +.x-panel-header-light-framed-collapsed-bottom-tl, +.x-panel-header-light-framed-collapsed-bottom-bl, +.x-panel-header-light-framed-collapsed-bottom-ml { + padding-left: 2px; +} +.x-panel-header-light-framed-collapsed-bottom-tc { + height: 2px; +} +.x-panel-header-light-framed-collapsed-bottom-bc { + height: 2px; +} +.x-panel-header-light-framed-collapsed-bottom-tl, +.x-panel-header-light-framed-collapsed-bottom-bl, +.x-panel-header-light-framed-collapsed-bottom-tr, +.x-panel-header-light-framed-collapsed-bottom-br, +.x-panel-header-light-framed-collapsed-bottom-tc, +.x-panel-header-light-framed-collapsed-bottom-bc, +.x-panel-header-light-framed-collapsed-bottom-ml, +.x-panel-header-light-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif); +} +.x-panel-header-light-framed-collapsed-bottom-ml, +.x-panel-header-light-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-light-framed-collapsed-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-light-framed-collapsed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-header-light-framed-collapsed-left-mc { + background-color: #fff; +} +.x-nbr .x-panel-header-light-framed-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-light-framed-collapsed-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-panel-header-light-framed-collapsed-left-tl { + background-position: 0 -4px; +} +.x-panel-header-light-framed-collapsed-left-tr { + background-position: right -6px; +} +.x-panel-header-light-framed-collapsed-left-bl { + background-position: 0 -8px; +} +.x-panel-header-light-framed-collapsed-left-br { + background-position: right -10px; +} +.x-panel-header-light-framed-collapsed-left-ml { + background-position: left 0; +} +.x-panel-header-light-framed-collapsed-left-mr { + background-position: left 0; +} +.x-panel-header-light-framed-collapsed-left-tc { + background-position: 0 0; +} +.x-panel-header-light-framed-collapsed-left-bc { + background-position: 0 -2px; +} +.x-panel-header-light-framed-collapsed-left-tr, +.x-panel-header-light-framed-collapsed-left-br, +.x-panel-header-light-framed-collapsed-left-mr { + padding-right: 2px; +} +.x-panel-header-light-framed-collapsed-left-tl, +.x-panel-header-light-framed-collapsed-left-bl, +.x-panel-header-light-framed-collapsed-left-ml { + padding-left: 2px; +} +.x-panel-header-light-framed-collapsed-left-tc { + height: 2px; +} +.x-panel-header-light-framed-collapsed-left-bc { + height: 2px; +} +.x-panel-header-light-framed-collapsed-left-tl, +.x-panel-header-light-framed-collapsed-left-bl, +.x-panel-header-light-framed-collapsed-left-tr, +.x-panel-header-light-framed-collapsed-left-br, +.x-panel-header-light-framed-collapsed-left-tc, +.x-panel-header-light-framed-collapsed-left-bc, +.x-panel-header-light-framed-collapsed-left-ml, +.x-panel-header-light-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-left-corners.gif); +} +.x-panel-header-light-framed-collapsed-left-ml, +.x-panel-header-light-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-light-framed-collapsed-left-mc { + padding: 14px 10px 14px 10px; +} +.x-panel .x-panel-header-light-framed-top { + border-bottom-width: 2px !important; +} +.x-panel .x-panel-header-light-framed-right { + border-left-width: 2px !important; +} +.x-panel .x-panel-header-light-framed-bottom { + border-top-width: 2px !important; +} +.x-panel .x-panel-header-light-framed-left { + border-right-width: 2px !important; +} +.x-nbr .x-panel-header-light-framed-collapsed-top { + border-bottom-width: 0 !important; +} +.x-nbr .x-panel-header-light-framed-collapsed-right { + border-left-width: 0 !important; +} +.x-nbr .x-panel-header-light-framed-collapsed-bottom { + border-top-width: 0 !important; +} +.x-nbr .x-panel-header-light-framed-collapsed-left { + border-right-width: 0 !important; +} +.x-panel-header-light-framed-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-panel-header-light-framed-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-panel-header-light-framed-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +.x-panel-header-light-framed-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +.x-keyboard-mode .x-panel-header-light-framed .x-tool-focus { + outline: 1px solid #5aaed4; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5aaed4; + pointer-events: none; +} +.x-panel-light-framed-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +.x-panel-light-framed-outer-border-l { + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +.x-panel-light-framed-outer-border-b { + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; +} +.x-panel-light-framed-outer-border-bl { + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +.x-panel-light-framed-outer-border-r { + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; +} +.x-panel-light-framed-outer-border-rl { + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +.x-panel-light-framed-outer-border-rb { + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; +} +.x-panel-light-framed-outer-border-rbl { + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +.x-panel-light-framed-outer-border-t { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; +} +.x-panel-light-framed-outer-border-tl { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +.x-panel-light-framed-outer-border-tb { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; +} +.x-panel-light-framed-outer-border-tbl { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +.x-panel-light-framed-outer-border-tr { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; +} +.x-panel-light-framed-outer-border-trl { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +.x-panel-light-framed-outer-border-trb { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; +} +.x-panel-light-framed-outer-border-trbl { + border-color: #d0d0d0 !important; + border-width: 2px !important; +} +.x-form-file-wrap .x-form-trigger-wrap { + border: 0; +} +.x-form-file-wrap .x-form-trigger-wrap .x-form-text { + border: 1px solid; + border-color: #d0d0d0; + height: 32px; +} +.x-form-file-wrap .x-form-trigger-wrap .x-form-text.x-form-invalid-field { + border-color: #cf4c35; +} +.x-html-editor-container { + border: 1px solid; + border-color: #d0d0d0; +} +.x-grid-header-ct { + border: 1px solid #d0d0d0; +} +.x-column-header-trigger { + background-color: #e6f1f6; + border-left: 1px solid #d0d0d0; +} +.x-column-header-last { + border-right-width: 0; +} +.x-column-header-last .x-column-header-over .x-column-header-trigger { + border-right: 1px solid #d0d0d0; +} +.x-resizable-handle { + background-repeat: no-repeat; +} +.x-resizable-handle-east-over, +.x-resizable-handle-west-over { + background-position: center; +} +.x-resizable-handle-south-over, +.x-resizable-handle-north-over { + background-position: center; +} +.x-resizable-handle-southeast-over { + background-position: -2px -2px; +} +.x-resizable-handle-northwest-over { + background-position: 2px 2px; +} +.x-resizable-handle-northeast-over { + background-position: -2px 2px; +} +.x-resizable-handle-southwest-over { + background-position: 2px -2px; +} +.x-resizable-pinned .x-resizable-handle-east, +.x-resizable-pinned .x-resizable-handle-west { + background-position: center; +} +.x-resizable-pinned .x-resizable-handle-south, +.x-resizable-pinned .x-resizable-handle-north { + background-position: center; +} +.x-resizable-pinned .x-resizable-handle-southeast { + background-position: -2px -2px; +} +.x-resizable-pinned .x-resizable-handle-northwest { + background-position: 2px 2px; +} +.x-resizable-pinned .x-resizable-handle-northeast { + background-position: -2px 2px; +} +.x-resizable-pinned .x-resizable-handle-southwest { + background-position: 2px -2px; +} +@font-face { + font-family: "FontAwesome"; + src: url("../../ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.eot?v=4.7.0"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.eot?#iefix&v=4.7.0") + format("embedded-opentype"), + url("../../ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0") format("woff2"), + url("../../ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.woff?v=4.7.0") format("woff"), + url("../../ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.ttf?v=4.7.0") format("truetype"), + url("../../ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.svg?v=4.7.0#fontawesomeregular") + format("svg"); + font-weight: normal; + font-style: normal; +} +.fa { + display: inline-block; + font: normal normal normal 14px/1 FontAwesome; + font-size: inherit; + text-rendering: auto; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} +.fa-lg { + font-size: 1.33333em; + line-height: 0.75em; + vertical-align: -15%; +} +.fa-2x { + font-size: 2em; +} +.fa-3x { + font-size: 3em; +} +.fa-4x { + font-size: 4em; +} +.fa-5x { + font-size: 5em; +} +.fa-fw { + width: 1.28571em; + text-align: center; +} +.fa-ul { + padding-left: 0; + margin-left: 2.14286em; + list-style-type: none; +} +.fa-ul > li { + position: relative; +} +.fa-li { + position: absolute; + left: -2.14286em; + width: 2.14286em; + top: 0.14286em; + text-align: center; +} +.fa-li.fa-lg { + left: -1.85714em; +} +.fa-border { + padding: 0.2em 0.25em 0.15em; + border: solid 0.08em #eee; + border-radius: 0.1em; +} +.fa-pull-left { + float: left; +} +.fa-pull-right { + float: right; +} +.fa.fa-pull-left { + margin-right: 0.3em; +} +.fa.fa-pull-right { + margin-left: 0.3em; +} +.pull-right { + float: right; +} +.pull-left { + float: left; +} +.fa.pull-left { + margin-right: 0.3em; +} +.fa.pull-right { + margin-left: 0.3em; +} +.fa-spin { + -webkit-animation: fa-spin 2s infinite linear; + animation: fa-spin 2s infinite linear; +} +.fa-pulse { + -webkit-animation: fa-spin 1s infinite steps(8); + animation: fa-spin 1s infinite steps(8); +} +@-webkit-keyframes fa-spin { + 0% { + -webkit-transform: rotate(0deg); + transform: rotate(0deg); + } + 100% { + -webkit-transform: rotate(359deg); + transform: rotate(359deg); + } +} +@keyframes fa-spin { + 0% { + -webkit-transform: rotate(0deg); + transform: rotate(0deg); + } + 100% { + -webkit-transform: rotate(359deg); + transform: rotate(359deg); + } +} +.fa-rotate-90 { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; + -webkit-transform: rotate(90deg); + -ms-transform: rotate(90deg); + transform: rotate(90deg); +} +.fa-rotate-180 { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=2)"; + -webkit-transform: rotate(180deg); + -ms-transform: rotate(180deg); + transform: rotate(180deg); +} +.fa-rotate-270 { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; + -webkit-transform: rotate(270deg); + -ms-transform: rotate(270deg); + transform: rotate(270deg); +} +.fa-flip-horizontal { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=0, mirror=1)"; + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); +} +.fa-flip-vertical { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1)"; + -webkit-transform: scale(1, -1); + -ms-transform: scale(1, -1); + transform: scale(1, -1); +} +:root .fa-rotate-90, +:root .fa-rotate-180, +:root .fa-rotate-270, +:root .fa-flip-horizontal, +:root .fa-flip-vertical { + filter: none; +} +.fa-stack { + position: relative; + display: inline-block; + width: 2em; + height: 2em; + line-height: 2em; + vertical-align: middle; +} +.fa-stack-1x, +.fa-stack-2x { + position: absolute; + left: 0; + width: 100%; + text-align: center; +} +.fa-stack-1x { + line-height: inherit; +} +.fa-stack-2x { + font-size: 2em; +} +.fa-inverse { + color: #fff; +} +.fa-glass:before { + content: "\f000" !important; +} +.fa-music:before { + content: "\f001" !important; +} +.fa-search:before { + content: "\f002" !important; +} +.fa-envelope-o:before { + content: "\f003" !important; +} +.fa-heart:before { + content: "\f004" !important; +} +.fa-star:before { + content: "\f005" !important; +} +.fa-star-o:before { + content: "\f006" !important; +} +.fa-user:before { + content: "\f007" !important; +} +.fa-film:before { + content: "\f008" !important; +} +.fa-th-large:before { + content: "\f009" !important; + color: #a53bb7 !important; +} +.fa-th:before { + content: "\f00a" !important; +} +.fa-th-list:before { + content: "\f00b" !important; +} +.fa-check:before { + content: "\f00c" !important; +} +.fa-remove:before, +.fa-close:before, +.fa-times:before { + content: "\f00d" !important; +} +.fa-search-plus:before { + content: "\f00e" !important; +} +.fa-search-minus:before { + content: "\f010" !important; +} +.fa-power-off:before { + content: "\f011" !important; +} +.fa-signal:before { + content: "\f012" !important; +} +.fa-gear:before, +.fa-cog:before { + content: "\f013" !important; +} +.fa-trash-o:before { + content: "\f014" !important; +} +.fa-home:before { + content: "\f015" !important; +} +.fa-file-o:before { + content: "\f016" !important; +} +.fa-clock-o:before { + content: "\f017" !important; +} +.fa-road:before { + content: "\f018" !important; +} +.fa-download:before { + content: "\f019" !important; +} +.fa-arrow-circle-o-down:before { + content: "\f01a" !important; +} +.fa-arrow-circle-o-up:before { + content: "\f01b" !important; +} +.fa-inbox:before { + content: "\f01c" !important; +} +.fa-play-circle-o:before { + content: "\f01d" !important; +} +.fa-rotate-right:before, +.fa-repeat:before { + content: "\f01e" !important; +} +.fa-refresh:before { + content: "\f021" !important; +} +.fa-list-alt:before { + content: "\f022" !important; +} +.fa-lock:before { + content: "\f023" !important; +} +.fa-flag:before { + content: "\f024" !important; +} +.fa-headphones:before { + content: "\f025" !important; +} +.fa-volume-off:before { + content: "\f026" !important; +} +.fa-volume-down:before { + content: "\f027" !important; +} +.fa-volume-up:before { + content: "\f028" !important; +} +.fa-qrcode:before { + content: "\f029" !important; +} +.fa-barcode:before { + content: "\f02a" !important; +} +.fa-tag:before { + content: "\f02b" !important; +} +.fa-tags:before { + content: "\f02c" !important; +} +.fa-book:before { + content: "\f02d" !important; + color: #a0877d !important; +} +.fa-bookmark:before { + content: "\f02e" !important; +} +.fa-print:before { + content: "\f02f" !important; +} +.fa-camera:before { + content: "\f030" !important; +} +.fa-font:before { + content: "\f031" !important; +} +.fa-bold:before { + content: "\f032" !important; +} +.fa-italic:before { + content: "\f033" !important; +} +.fa-text-height:before { + content: "\f034" !important; +} +.fa-text-width:before { + content: "\f035" !important; +} +.fa-align-left:before { + content: "\f036" !important; +} +.fa-align-center:before { + content: "\f037" !important; +} +.fa-align-right:before { + content: "\f038" !important; +} +.fa-align-justify:before { + content: "\f039" !important; +} +.fa-list:before { + content: "\f03a" !important; +} +.fa-dedent:before, +.fa-outdent:before { + content: "\f03b" !important; +} +.fa-indent:before { + content: "\f03c" !important; +} +.fa-video-camera:before { + content: "\f03d" !important; +} +.fa-photo:before, +.fa-image:before, +.fa-picture-o:before { + content: "\f03e" !important; +} +.fa-pencil:before { + content: "\f040" !important; + color: #a0877d !important; +} +.fa-map-marker:before { + content: "\f041" !important; +} +.fa-adjust:before { + content: "\f042" !important; +} +.fa-tint:before { + content: "\f043" !important; +} +.fa-edit:before, +.fa-pencil-square-o:before { + content: "\f044" !important; +} +.fa-share-square-o:before { + content: "\f045" !important; +} +.fa-check-square-o:before { + content: "\f046" !important; + color: #a0877d !important; +} +.fa-arrows:before { + content: "\f047" !important; +} +.fa-step-backward:before { + content: "\f048" !important; +} +.fa-fast-backward:before { + content: "\f049" !important; +} +.fa-backward:before { + content: "\f04a" !important; +} +.fa-play:before { + content: "\f04b" !important; +} +.fa-pause:before { + content: "\f04c" !important; +} +.fa-stop:before { + content: "\f04d" !important; +} +.fa-forward:before { + content: "\f04e" !important; +} +.fa-fast-forward:before { + content: "\f050" !important; +} +.fa-step-forward:before { + content: "\f051" !important; +} +.fa-eject:before { + content: "\f052" !important; +} +.fa-chevron-left:before { + content: "\f053" !important; +} +.fa-chevron-right:before { + content: "\f054" !important; +} +.fa-plus-circle:before { + content: "\f055" !important; +} +.fa-minus-circle:before { + content: "\f056" !important; +} +.fa-times-circle:before { + content: "\f057" !important; +} +.fa-check-circle:before { + content: "\f058" !important; +} +.fa-question-circle:before { + content: "\f059" !important; +} +.fa-info-circle:before { + content: "\f05a" !important; +} +.fa-crosshairs:before { + content: "\f05b" !important; +} +.fa-times-circle-o:before { + content: "\f05c" !important; +} +.fa-check-circle-o:before { + content: "\f05d" !important; +} +.fa-ban:before { + content: "\f05e" !important; +} +.fa-arrow-left:before { + content: "\f060" !important; +} +.fa-arrow-right:before { + content: "\f061" !important; +} +.fa-arrow-up:before { + content: "\f062" !important; +} +.fa-arrow-down:before { + content: "\f063" !important; +} +.fa-mail-forward:before, +.fa-share:before { + content: "\f064" !important; +} +.fa-expand:before { + content: "\f065" !important; +} +.fa-compress:before { + content: "\f066" !important; +} +.fa-plus:before { + content: "\f067" !important; +} +.fa-minus:before { + content: "\f068" !important; +} +.fa-asterisk:before { + content: "\f069" !important; +} +.fa-exclamation-circle:before { + content: "\f06a" !important; +} +.fa-gift:before { + content: "\f06b" !important; +} +.fa-leaf:before { + content: "\f06c" !important; +} +.fa-fire:before { + content: "\f06d" !important; +} +.fa-eye:before { + content: "\f06e" !important; +} +.fa-eye-slash:before { + content: "\f070" !important; +} +.fa-warning:before, +.fa-exclamation-triangle:before { + content: "\f071" !important; + color: #a0877d !important; +} +.fa-plane:before { + content: "\f072" !important; +} +.fa-calendar:before { + content: "\f073" !important; +} +.fa-random:before { + content: "\f074" !important; +} +.fa-comment:before { + content: "\f075" !important; +} +.fa-magnet:before { + content: "\f076" !important; +} +.fa-chevron-up:before { + content: "\f077" !important; +} +.fa-chevron-down:before { + content: "\f078" !important; +} +.fa-retweet:before { + content: "\f079" !important; +} +.fa-shopping-cart:before { + content: "\f07a" !important; + color: #f6594e !important; +} +.fa-folder:before { + content: "\f07b" !important; +} +.fa-folder-open:before { + content: "\f07c" !important; +} +.fa-arrows-v:before { + content: "\f07d" !important; +} +.fa-arrows-h:before { + content: "\f07e" !important; +} +.fa-bar-chart-o:before, +.fa-bar-chart:before { + content: "\f080" !important; + color: #126398 !important; +} +.fa-twitter-square:before { + content: "\f081" !important; +} +.fa-facebook-square:before { + content: "\f082" !important; +} +.fa-camera-retro:before { + content: "\f083" !important; +} +.fa-key:before { + content: "\f084" !important; +} +.fa-gears:before, +.fa-cogs:before { + content: "\f085" !important; +} +.fa-comments:before { + content: "\f086" !important; +} +.fa-thumbs-o-up:before { + content: "\f087" !important; +} +.fa-thumbs-o-down:before { + content: "\f088" !important; +} +.fa-star-half:before { + content: "\f089" !important; +} +.fa-heart-o:before { + content: "\f08a" !important; +} +.fa-sign-out:before { + content: "\f08b" !important; +} +.fa-linkedin-square:before { + content: "\f08c" !important; +} +.fa-thumb-tack:before { + content: "\f08d" !important; +} +.fa-external-link:before { + content: "\f08e" !important; +} +.fa-sign-in:before { + content: "\f090" !important; + color: #f6594e !important; +} +.fa-trophy:before { + content: "\f091" !important; +} +.fa-github-square:before { + content: "\f092" !important; +} +.fa-upload:before { + content: "\f093" !important; +} +.fa-lemon-o:before { + content: "\f094" !important; +} +.fa-phone:before { + content: "\f095" !important; +} +.fa-square-o:before { + content: "\f096" !important; +} +.fa-bookmark-o:before { + content: "\f097" !important; +} +.fa-phone-square:before { + content: "\f098" !important; +} +.fa-twitter:before { + content: "\f099" !important; +} +.fa-facebook-f:before, +.fa-facebook:before { + content: "\f09a" !important; +} +.fa-github:before { + content: "\f09b" !important; +} +.fa-unlock:before { + content: "\f09c" !important; +} +.fa-credit-card:before { + content: "\f09d" !important; +} +.fa-feed:before, +.fa-rss:before { + content: "\f09e" !important; +} +.fa-hdd-o:before { + content: "\f0a0" !important; + color: #f6594e !important; +} +.fa-bullhorn:before { + content: "\f0a1" !important; +} +.fa-bell:before { + content: "\f0f3" !important; +} +.fa-certificate:before { + content: "\f0a3" !important; +} +.fa-hand-o-right:before { + content: "\f0a4" !important; +} +.fa-hand-o-left:before { + content: "\f0a5" !important; +} +.fa-hand-o-up:before { + content: "\f0a6" !important; +} +.fa-hand-o-down:before { + content: "\f0a7" !important; +} +.fa-arrow-circle-left:before { + content: "\f0a8" !important; +} +.fa-arrow-circle-right:before { + content: "\f0a9" !important; +} +.fa-arrow-circle-up:before { + content: "\f0aa" !important; +} +.fa-arrow-circle-down:before { + content: "\f0ab" !important; +} +.fa-globe:before { + content: "\f0ac" !important; +} +.fa-wrench:before { + content: "\f0ad" !important; + color: #a0877d !important; +} +.fa-tasks:before { + content: "\f0ae" !important; +} +.fa-filter:before { + content: "\f0b0" !important; +} +.fa-briefcase:before { + content: "\f0b1" !important; +} +.fa-arrows-alt:before { + content: "\f0b2" !important; +} +.fa-group:before, +.fa-users:before { + content: "\f0c0" !important; +} +.fa-chain:before, +.fa-link:before { + content: "\f0c1" !important; +} +.fa-cloud:before { + content: "\f0c2" !important; +} +.fa-flask:before { + content: "\f0c3" !important; +} +.fa-cut:before, +.fa-scissors:before { + content: "\f0c4" !important; +} +.fa-copy:before, +.fa-files-o:before { + content: "\f0c5" !important; +} +.fa-paperclip:before { + content: "\f0c6" !important; +} +.fa-save:before, +.fa-floppy-o:before { + content: "\f0c7" !important; +} +.fa-square:before { + content: "\f0c8" !important; +} +.fa-navicon:before, +.fa-reorder:before, +.fa-bars:before { + content: "\f0c9" !important; +} +.fa-list-ul:before { + content: "\f0ca" !important; +} +.fa-list-ol:before { + content: "\f0cb" !important; +} +.fa-strikethrough:before { + content: "\f0cc" !important; +} +.fa-underline:before { + content: "\f0cd" !important; +} +.fa-table:before { + content: "\f0ce" !important; +} +.fa-magic:before { + content: "\f0d0" !important; +} +.fa-truck:before { + content: "\f0d1" !important; + color: #a55ec7 !important; +} +.fa-pinterest:before { + content: "\f0d2" !important; +} +.fa-pinterest-square:before { + content: "\f0d3" !important; +} +.fa-google-plus-square:before { + content: "\f0d4" !important; +} +.fa-google-plus:before { + content: "\f0d5" !important; +} +.fa-money:before { + content: "\f0d6" !important; +} +.fa-caret-down:before { + content: "\f0d7" !important; +} +.fa-caret-up:before { + content: "\f0d8" !important; +} +.fa-caret-left:before { + content: "\f0d9" !important; +} +.fa-caret-right:before { + content: "\f0da" !important; +} +.fa-columns:before { + content: "\f0db" !important; +} +.fa-unsorted:before, +.fa-sort:before { + content: "\f0dc" !important; +} +.fa-sort-down:before, +.fa-sort-desc:before { + content: "\f0dd" !important; +} +.fa-sort-up:before, +.fa-sort-asc:before { + content: "\f0de" !important; +} +.fa-envelope:before { + content: "\f0e0" !important; + color: #ff855e !important; +} +.fa-linkedin:before { + content: "\f0e1" !important; +} +.fa-rotate-left:before, +.fa-undo:before { + content: "\f0e2" !important; +} +.fa-legal:before, +.fa-gavel:before { + content: "\f0e3" !important; +} +.fa-dashboard:before, +.fa-tachometer:before { + content: "\f0e4" !important; +} +.fa-comment-o:before { + content: "\f0e5" !important; +} +.fa-comments-o:before { + content: "\f0e6" !important; +} +.fa-flash:before, +.fa-bolt:before { + content: "\f0e7" !important; +} +.fa-sitemap:before { + content: "\f0e8" !important; +} +.fa-umbrella:before { + content: "\f0e9" !important; +} +.fa-paste:before, +.fa-clipboard:before { + content: "\f0ea" !important; +} +.fa-lightbulb-o:before { + content: "\f0eb" !important; + color:#fed212 !important; +} +.fa-exchange:before { + content: "\f0ec" !important; +} +.fa-cloud-download:before { + content: "\f0ed" !important; +} +.fa-cloud-upload:before { + content: "\f0ee" !important; +} +.fa-user-md:before { + content: "\f0f0" !important; +} +.fa-stethoscope:before { + content: "\f0f1" !important; +} +.fa-suitcase:before { + content: "\f0f2" !important; +} +.fa-bell-o:before { + content: "\f0a2" !important; +} +.fa-coffee:before { + content: "\f0f4" !important; +} +.fa-cutlery:before { + content: "\f0f5" !important; +} +.fa-file-text-o:before { + content: "\f0f6" !important; +} +.fa-building-o:before { + content: "\f0f7" !important; +} +.fa-hospital-o:before { + content: "\f0f8" !important; +} +.fa-ambulance:before { + content: "\f0f9" !important; +} +.fa-medkit:before { + content: "\f0fa" !important; +} +.fa-fighter-jet:before { + content: "\f0fb" !important; +} +.fa-beer:before { + content: "\f0fc" !important; +} +.fa-h-square:before { + content: "\f0fd" !important; +} +.fa-plus-square:before { + content: "\f0fe" !important; +} +.fa-angle-double-left:before { + content: "\f100" !important; +} +.fa-angle-double-right:before { + content: "\f101" !important; +} +.fa-angle-double-up:before { + content: "\f102" !important; +} +.fa-angle-double-down:before { + content: "\f103" !important; +} +.fa-angle-left:before { + content: "\f104" !important; +} +.fa-angle-right:before { + content: "\f105" !important; +} +.fa-angle-up:before { + content: "\f106" !important; +} +.fa-angle-down:before { + content: "\f107" !important; +} +.fa-desktop:before { + content: "\f108" !important; +} +.fa-laptop:before { + content: "\f109" !important; +} +.fa-tablet:before { + content: "\f10a" !important; +} +.fa-mobile-phone:before, +.fa-mobile:before { + content: "\f10b" !important; +} +.fa-circle-o:before { + content: "\f10c" !important; +} +.fa-quote-left:before { + content: "\f10d" !important; +} +.fa-quote-right:before { + content: "\f10e" !important; +} +.fa-spinner:before { + content: "\f110" !important; +} +.fa-circle:before { + content: "\f111" !important; +} +.fa-mail-reply:before, +.fa-reply:before { + content: "\f112" !important; +} +.fa-github-alt:before { + content: "\f113" !important; +} +.fa-folder-o:before { + content: "\f114" !important; +} +.fa-folder-open-o:before { + content: "\f115" !important; +} +.fa-smile-o:before { + content: "\f118" !important; +} +.fa-frown-o:before { + content: "\f119" !important; +} +.fa-meh-o:before { + content: "\f11a" !important; +} +.fa-gamepad:before { + content: "\f11b" !important; +} +.fa-keyboard-o:before { + content: "\f11c" !important; +} +.fa-flag-o:before { + content: "\f11d" !important; +} +.fa-flag-checkered:before { + content: "\f11e" !important; +} +.fa-terminal:before { + content: "\f120" !important; +} +.fa-code:before { + content: "\f121" !important; +} +.fa-mail-reply-all:before, +.fa-reply-all:before { + content: "\f122" !important; +} +.fa-star-half-empty:before, +.fa-star-half-full:before, +.fa-star-half-o:before { + content: "\f123" !important; +} +.fa-location-arrow:before { + content: "\f124" !important; +} +.fa-crop:before { + content: "\f125" !important; +} +.fa-code-fork:before { + content: "\f126" !important; +} +.fa-unlink:before, +.fa-chain-broken:before { + content: "\f127" !important; +} +.fa-question:before { + content: "\f128" !important; +} +.fa-info:before { + content: "\f129" !important; +} +.fa-exclamation:before { + content: "\f12a" !important; +} +.fa-superscript:before { + content: "\f12b" !important; +} +.fa-subscript:before { + content: "\f12c" !important; +} +.fa-eraser:before { + content: "\f12d" !important; +} +.fa-puzzle-piece:before { + content: "\f12e" !important; +} +.fa-microphone:before { + content: "\f130" !important; +} +.fa-microphone-slash:before { + content: "\f131" !important; +} +.fa-shield:before { + content: "\f132" !important; +} +.fa-calendar-o:before { + content: "\f133" !important; +} +.fa-fire-extinguisher:before { + content: "\f134" !important; +} +.fa-rocket:before { + content: "\f135" !important; +} +.fa-maxcdn:before { + content: "\f136" !important; +} +.fa-chevron-circle-left:before { + content: "\f137" !important; +} +.fa-chevron-circle-right:before { + content: "\f138" !important; +} +.fa-chevron-circle-up:before { + content: "\f139" !important; +} +.fa-chevron-circle-down:before { + content: "\f13a" !important; +} +.fa-html5:before { + content: "\f13b" !important; +} +.fa-css3:before { + content: "\f13c" !important; +} +.fa-anchor:before { + content: "\f13d" !important; +} +.fa-unlock-alt:before { + content: "\f13e" !important; +} +.fa-bullseye:before { + content: "\f140" !important; +} +.fa-ellipsis-h:before { + content: "\f141" !important; +} +.fa-ellipsis-v:before { + content: "\f142" !important; +} +.fa-rss-square:before { + content: "\f143" !important; +} +.fa-play-circle:before { + content: "\f144" !important; +} +.fa-ticket:before { + content: "\f145" !important; + color: #a0877d !important; +} +.fa-minus-square:before { + content: "\f146" !important; +} +.fa-minus-square-o:before { + content: "\f147" !important; +} +.fa-level-up:before { + content: "\f148" !important; +} +.fa-level-down:before { + content: "\f149" !important; +} +.fa-check-square:before { + content: "\f14a" !important; +} +.fa-pencil-square:before { + content: "\f14b" !important; +} +.fa-external-link-square:before { + content: "\f14c" !important; +} +.fa-share-square:before { + content: "\f14d" !important; +} +.fa-compass:before { + content: "\f14e" !important; +} +.fa-toggle-down:before, +.fa-caret-square-o-down:before { + content: "\f150" !important; +} +.fa-toggle-up:before, +.fa-caret-square-o-up:before { + content: "\f151" !important; +} +.fa-toggle-right:before, +.fa-caret-square-o-right:before { + content: "\f152" !important; +} +.fa-euro:before, +.fa-eur:before { + content: "\f153" !important; +} +.fa-gbp:before { + content: "\f154" !important; +} +.fa-dollar:before, +.fa-usd:before { + content: "\f155" !important; +} +.fa-rupee:before, +.fa-inr:before { + content: "\f156" !important; +} +.fa-cny:before, +.fa-rmb:before, +.fa-yen:before, +.fa-jpy:before { + content: "\f157" !important; +} +.fa-ruble:before, +.fa-rouble:before, +.fa-rub:before { + content: "\f158" !important; +} +.fa-won:before, +.fa-krw:before { + content: "\f159" !important; +} +.fa-bitcoin:before, +.fa-btc:before { + content: "\f15a" !important; +} +.fa-file:before { + content: "\f15b" !important; +} +.fa-file-text:before { + content: "\f15c" !important; + color: #a55ec7 !important; +} +.fa-file-text-workshop:before { + content: "\f15c" !important; + color: #4caf50 !important; +} +.fa-sort-alpha-asc:before { + content: "\f15d" !important; +} +.fa-sort-alpha-desc:before { + content: "\f15e" !important; +} +.fa-sort-amount-asc:before { + content: "\f160" !important; +} +.fa-sort-amount-desc:before { + content: "\f161" !important; +} +.fa-sort-numeric-asc:before { + content: "\f162" !important; +} +.fa-sort-numeric-desc:before { + content: "\f163" !important; +} +.fa-thumbs-up:before { + content: "\f164" !important; +} +.fa-thumbs-down:before { + content: "\f165" !important; +} +.fa-youtube-square:before { + content: "\f166" !important; +} +.fa-youtube:before { + content: "\f167" !important; +} +.fa-xing:before { + content: "\f168" !important; +} +.fa-xing-square:before { + content: "\f169" !important; +} +.fa-youtube-play:before { + content: "\f16a" !important; +} +.fa-dropbox:before { + content: "\f16b" !important; +} +.fa-stack-overflow:before { + content: "\f16c" !important; +} +.fa-instagram:before { + content: "\f16d" !important; +} +.fa-flickr:before { + content: "\f16e" !important; +} +.fa-adn:before { + content: "\f170" !important; +} +.fa-bitbucket:before { + content: "\f171" !important; +} +.fa-bitbucket-square:before { + content: "\f172" !important; +} +.fa-tumblr:before { + content: "\f173" !important; +} +.fa-tumblr-square:before { + content: "\f174" !important; +} +.fa-long-arrow-down:before { + content: "\f175" !important; +} +.fa-long-arrow-up:before { + content: "\f176" !important; +} +.fa-long-arrow-left:before { + content: "\f177" !important; +} +.fa-long-arrow-right:before { + content: "\f178" !important; +} +.fa-apple:before { + content: "\f179" !important; +} +.fa-windows:before { + content: "\f17a" !important; +} +.fa-android:before { + content: "\f17b" !important; +} +.fa-linux:before { + content: "\f17c" !important; +} +.fa-dribbble:before { + content: "\f17d" !important; +} +.fa-skype:before { + content: "\f17e" !important; +} +.fa-foursquare:before { + content: "\f180" !important; +} +.fa-trello:before { + content: "\f181" !important; +} +.fa-female:before { + content: "\f182" !important; +} +.fa-male:before { + content: "\f183" !important; +} +.fa-gittip:before, +.fa-gratipay:before { + content: "\f184" !important; +} +.fa-sun-o:before { + content: "\f185" !important; +} +.fa-moon-o:before { + content: "\f186" !important; +} +.fa-archive:before { + content: "\f187" !important; + color: #f6594e !important; +} +.fa-bug:before { + content: "\f188" !important; +} +.fa-vk:before { + content: "\f189" !important; +} +.fa-weibo:before { + content: "\f18a" !important; +} +.fa-renren:before { + content: "\f18b" !important; +} +.fa-pagelines:before { + content: "\f18c" !important; +} +.fa-stack-exchange:before { + content: "\f18d" !important; +} +.fa-arrow-circle-o-right:before { + content: "\f18e" !important; +} +.fa-arrow-circle-o-left:before { + content: "\f190" !important; +} +.fa-toggle-left:before, +.fa-caret-square-o-left:before { + content: "\f191" !important; +} +.fa-dot-circle-o:before { + content: "\f192" !important; +} +.fa-wheelchair:before { + content: "\f193" !important; +} +.fa-vimeo-square:before { + content: "\f194" !important; +} +.fa-turkish-lira:before, +.fa-try:before { + content: "\f195" !important; +} +.fa-plus-square-o:before { + content: "\f196" !important; +} +.fa-space-shuttle:before { + content: "\f197" !important; +} +.fa-slack:before { + content: "\f198" !important; +} +.fa-envelope-square:before { + content: "\f199" !important; +} +.fa-wordpress:before { + content: "\f19a" !important; +} +.fa-openid:before { + content: "\f19b" !important; +} +.fa-institution:before, +.fa-bank:before, +.fa-university:before { + content: "\f19c" !important; +} +.fa-mortar-board:before, +.fa-graduation-cap:before { + content: "\f19d" !important; +} +.fa-yahoo:before { + content: "\f19e" !important; +} +.fa-google:before { + content: "\f1a0" !important; +} +.fa-reddit:before { + content: "\f1a1" !important; +} +.fa-reddit-square:before { + content: "\f1a2" !important; +} +.fa-stumbleupon-circle:before { + content: "\f1a3" !important; +} +.fa-stumbleupon:before { + content: "\f1a4" !important; +} +.fa-delicious:before { + content: "\f1a5" !important; +} +.fa-digg:before { + content: "\f1a6" !important; +} +.fa-pied-piper-pp:before { + content: "\f1a7" !important; +} +.fa-pied-piper-alt:before { + content: "\f1a8" !important; +} +.fa-drupal:before { + content: "\f1a9" !important; +} +.fa-joomla:before { + content: "\f1aa" !important; +} +.fa-language:before { + content: "\f1ab" !important; +} +.fa-fax:before { + content: "\f1ac" !important; +} +.fa-building:before { + content: "\f1ad" !important; +} +.fa-child:before { + content: "\f1ae" !important; +} +.fa-paw:before { + content: "\f1b0" !important; +} +.fa-spoon:before { + content: "\f1b1" !important; +} +.fa-cube:before { + content: "\f1b2" !important; +} +.fa-cubes:before { + content: "\f1b3" !important; +} +.fa-cubes2:before { + content: "\f1b3" !important; + color: #a55ec7 !important; +} +.fa-behance:before { + content: "\f1b4" !important; +} +.fa-behance-square:before { + content: "\f1b5" !important; +} +.fa-steam:before { + content: "\f1b6" !important; +} +.fa-steam-square:before { + content: "\f1b7" !important; +} +.fa-recycle:before { + content: "\f1b8" !important; +} +.fa-automobile:before, +.fa-car:before { + content: "\f1b9" !important; +} +.fa-cab:before, +.fa-taxi:before { + content: "\f1ba" !important; +} +.fa-tree:before { + content: "\f1bb" !important; +} +.fa-spotify:before { + content: "\f1bc" !important; +} +.fa-deviantart:before { + content: "\f1bd" !important; +} +.fa-soundcloud:before { + content: "\f1be" !important; +} +.fa-database:before { + content: "\f1c0" !important; +} +.fa-file-pdf-o:before { + content: "\f1c1" !important; +} +.fa-file-word-o:before { + content: "\f1c2" !important; +} +.fa-file-excel-o:before { + content: "\f1c3" !important; + color: #4caf50 !important; +} +.fa-file-powerpoint-o:before { + content: "\f1c4" !important; +} +.fa-file-photo-o:before, +.fa-file-picture-o:before, +.fa-file-image-o:before { + content: "\f1c5" !important; +} +.fa-file-zip-o:before, +.fa-file-archive-o:before { + content: "\f1c6" !important; +} +.fa-file-sound-o:before, +.fa-file-audio-o:before { + content: "\f1c7" !important; +} +.fa-file-movie-o:before, +.fa-file-video-o:before { + content: "\f1c8" !important; +} +.fa-file-code-o:before { + content: "\f1c9" !important; +} +.fa-vine:before { + content: "\f1ca" !important; +} +.fa-codepen:before { + content: "\f1cb" !important; +} +.fa-jsfiddle:before { + content: "\f1cc" !important; +} +.fa-life-bouy:before, +.fa-life-buoy:before, +.fa-life-saver:before, +.fa-support:before, +.fa-life-ring:before { + content: "\f1cd" !important; +} +.fa-circle-o-notch:before { + content: "\f1ce" !important; +} +.fa-ra:before, +.fa-resistance:before, +.fa-rebel:before { + content: "\f1d0" !important; +} +.fa-ge:before, +.fa-empire:before { + content: "\f1d1" !important; +} +.fa-git-square:before { + content: "\f1d2" !important; +} +.fa-git:before { + content: "\f1d3" !important; +} +.fa-y-combinator-square:before, +.fa-yc-square:before, +.fa-hacker-news:before { + content: "\f1d4" !important; +} +.fa-tencent-weibo:before { + content: "\f1d5" !important; +} +.fa-qq:before { + content: "\f1d6" !important; +} +.fa-wechat:before, +.fa-weixin:before { + content: "\f1d7" !important; +} +.fa-send:before, +.fa-paper-plane:before { + content: "\f1d8" !important; + color: #fff; +} +.fa-send-o:before, +.fa-paper-plane-o:before { + content: "\f1d9" !important; +} +.fa-history:before { + content: "\f1da" !important; +} +.fa-circle-thin:before { + content: "\f1db" !important; +} +.fa-header:before { + content: "\f1dc" !important; +} +.fa-paragraph:before { + content: "\f1dd" !important; +} +.fa-sliders:before { + content: "\f1de" !important; +} +.fa-share-alt:before { + content: "\f1e0" !important; +} +.fa-share-alt-square:before { + content: "\f1e1" !important; +} +.fa-bomb:before { + content: "\f1e2" !important; +} +.fa-soccer-ball-o:before, +.fa-futbol-o:before { + content: "\f1e3" !important; +} +.fa-tty:before { + content: "\f1e4" !important; +} +.fa-binoculars:before { + content: "\f1e5" !important; +} +.fa-plug:before { + content: "\f1e6" !important; +} +.fa-slideshare:before { + content: "\f1e7" !important; +} +.fa-twitch:before { + content: "\f1e8" !important; +} +.fa-yelp:before { + content: "\f1e9" !important; +} +.fa-newspaper-o:before { + content: "\f1ea" !important; +} +.fa-wifi:before { + content: "\f1eb" !important; +} +.fa-calculator:before { + content: "\f1ec" !important; +} +.fa-paypal:before { + content: "\f1ed" !important; +} +.fa-google-wallet:before { + content: "\f1ee" !important; +} +.fa-cc-visa:before { + content: "\f1f0" !important; +} +.fa-cc-mastercard:before { + content: "\f1f1" !important; +} +.fa-cc-discover:before { + content: "\f1f2" !important; +} +.fa-cc-amex:before { + content: "\f1f3" !important; +} +.fa-cc-paypal:before { + content: "\f1f4" !important; +} +.fa-cc-stripe:before { + content: "\f1f5" !important; +} +.fa-bell-slash:before { + content: "\f1f6" !important; +} +.fa-bell-slash-o:before { + content: "\f1f7" !important; +} +.fa-trash:before { + content: "\f1f8" !important; +} +.fa-copyright:before { + content: "\f1f9" !important; +} +.fa-at:before { + content: "\f1fa" !important; +} +.fa-eyedropper:before { + content: "\f1fb" !important; +} +.fa-paint-brush:before { + content: "\f1fc" !important; +} +.fa-birthday-cake:before { + content: "\f1fd" !important; +} +.fa-area-chart:before { + content: "\f1fe" !important; +} +.fa-pie-chart:before { + content: "\f200" !important; +} +.fa-line-chart:before { + content: "\f201" !important; +} +.fa-lastfm:before { + content: "\f202" !important; +} +.fa-lastfm-square:before { + content: "\f203" !important; +} +.fa-toggle-off:before { + content: "\f204" !important; +} +.fa-toggle-on:before { + content: "\f205" !important; +} +.fa-bicycle:before { + content: "\f206" !important; +} +.fa-bus:before { + content: "\f207" !important; +} +.fa-ioxhost:before { + content: "\f208" !important; +} +.fa-angellist:before { + content: "\f209" !important; +} +.fa-cc:before { + content: "\f20a" !important; +} +.fa-shekel:before, +.fa-sheqel:before, +.fa-ils:before { + content: "\f20b" !important; +} +.fa-meanpath:before { + content: "\f20c" !important; +} +.fa-buysellads:before { + content: "\f20d" !important; +} +.fa-connectdevelop:before { + content: "\f20e" !important; +} +.fa-dashcube:before { + content: "\f210" !important; +} +.fa-forumbee:before { + content: "\f211" !important; +} +.fa-leanpub:before { + content: "\f212" !important; +} +.fa-sellsy:before { + content: "\f213" !important; +} +.fa-shirtsinbulk:before { + content: "\f214" !important; +} +.fa-simplybuilt:before { + content: "\f215" !important; +} +.fa-skyatlas:before { + content: "\f216" !important; +} +.fa-cart-plus:before { + content: "\f217" !important; +} +.fa-cart-arrow-down:before { + content: "\f218" !important; +} +.fa-diamond:before { + content: "\f219" !important; +} +.fa-ship:before { + content: "\f21a" !important; +} +.fa-user-secret:before { + content: "\f21b" !important; +} +.fa-motorcycle:before { + content: "\f21c" !important; +} +.fa-street-view:before { + content: "\f21d" !important; +} +.fa-heartbeat:before { + content: "\f21e" !important; +} +.fa-venus:before { + content: "\f221" !important; +} +.fa-mars:before { + content: "\f222" !important; +} +.fa-mercury:before { + content: "\f223" !important; +} +.fa-intersex:before, +.fa-transgender:before { + content: "\f224" !important; +} +.fa-transgender-alt:before { + content: "\f225" !important; +} +.fa-venus-double:before { + content: "\f226" !important; +} +.fa-mars-double:before { + content: "\f227" !important; +} +.fa-venus-mars:before { + content: "\f228" !important; +} +.fa-mars-stroke:before { + content: "\f229" !important; +} +.fa-mars-stroke-v:before { + content: "\f22a" !important; +} +.fa-mars-stroke-h:before { + content: "\f22b" !important; +} +.fa-neuter:before { + content: "\f22c" !important; +} +.fa-genderless:before { + content: "\f22d" !important; +} +.fa-facebook-official:before { + content: "\f230" !important; +} +.fa-pinterest-p:before { + content: "\f231" !important; +} +.fa-whatsapp:before { + content: "\f232" !important; +} +.fa-server:before { + content: "\f233" !important; +} +.fa-user-plus:before { + content: "\f234" !important; +} +.fa-user-times:before { + content: "\f235" !important; +} +.fa-hotel:before, +.fa-bed:before { + content: "\f236" !important; +} +.fa-viacoin:before { + content: "\f237" !important; +} +.fa-train:before { + content: "\f238" !important; +} +.fa-subway:before { + content: "\f239" !important; +} +.fa-medium:before { + content: "\f23a" !important; +} +.fa-yc:before, +.fa-y-combinator:before { + content: "\f23b" !important; +} +.fa-optin-monster:before { + content: "\f23c" !important; +} +.fa-opencart:before { + content: "\f23d" !important; +} +.fa-expeditedssl:before { + content: "\f23e" !important; +} +.fa-battery-4:before, +.fa-battery:before, +.fa-battery-full:before { + content: "\f240" !important; +} +.fa-battery-3:before, +.fa-battery-three-quarters:before { + content: "\f241" !important; +} +.fa-battery-2:before, +.fa-battery-half:before { + content: "\f242" !important; +} +.fa-battery-1:before, +.fa-battery-quarter:before { + content: "\f243" !important; +} +.fa-battery-0:before, +.fa-battery-empty:before { + content: "\f244" !important; +} +.fa-mouse-pointer:before { + content: "\f245" !important; +} +.fa-i-cursor:before { + content: "\f246" !important; +} +.fa-object-group:before { + content: "\f247" !important; +} +.fa-object-ungroup:before { + content: "\f248" !important; +} +.fa-sticky-note:before { + content: "\f249" !important; + color: #4caf50 !important; +} +.fa-sticky-note-o:before { + content: "\f24a" !important; + color: #a0877d !important; +} +.fa-cc-jcb:before { + content: "\f24b" !important; +} +.fa-cc-diners-club:before { + content: "\f24c" !important; +} +.fa-clone:before { + content: "\f24d" !important; +} +.fa-balance-scale:before { + content: "\f24e" !important; +} +.fa-hourglass-o:before { + content: "\f250" !important; +} +.fa-hourglass-1:before, +.fa-hourglass-start:before { + content: "\f251" !important; +} +.fa-hourglass-2:before, +.fa-hourglass-half:before { + content: "\f252" !important; +} +.fa-hourglass-3:before, +.fa-hourglass-end:before { + content: "\f253" !important; +} +.fa-hourglass:before { + content: "\f254" !important; +} +.fa-hand-grab-o:before, +.fa-hand-rock-o:before { + content: "\f255" !important; +} +.fa-hand-stop-o:before, +.fa-hand-paper-o:before { + content: "\f256" !important; +} +.fa-hand-scissors-o:before { + content: "\f257" !important; +} +.fa-hand-lizard-o:before { + content: "\f258" !important; +} +.fa-hand-spock-o:before { + content: "\f259" !important; +} +.fa-hand-pointer-o:before { + content: "\f25a" !important; +} +.fa-hand-peace-o:before { + content: "\f25b" !important; +} +.fa-trademark:before { + content: "\f25c" !important; +} +.fa-registered:before { + content: "\f25d" !important; +} +.fa-creative-commons:before { + content: "\f25e" !important; +} +.fa-gg:before { + content: "\f260" !important; +} +.fa-gg-circle:before { + content: "\f261" !important; +} +.fa-tripadvisor:before { + content: "\f262" !important; +} +.fa-odnoklassniki:before { + content: "\f263" !important; +} +.fa-odnoklassniki-square:before { + content: "\f264" !important; +} +.fa-get-pocket:before { + content: "\f265" !important; +} +.fa-wikipedia-w:before { + content: "\f266" !important; +} +.fa-safari:before { + content: "\f267" !important; +} +.fa-chrome:before { + content: "\f268" !important; +} +.fa-firefox:before { + content: "\f269" !important; +} +.fa-opera:before { + content: "\f26a" !important; +} +.fa-internet-explorer:before { + content: "\f26b" !important; +} +.fa-tv:before, +.fa-television:before { + content: "\f26c" !important; +} +.fa-contao:before { + content: "\f26d" !important; +} +.fa-500px:before { + content: "\f26e" !important; +} +.fa-amazon:before { + content: "\f270" !important; +} +.fa-calendar-plus-o:before { + content: "\f271" !important; +} +.fa-calendar-minus-o:before { + content: "\f272" !important; +} +.fa-calendar-times-o:before { + content: "\f273" !important; +} +.fa-calendar-check-o:before { + content: "\f274" !important; +} +.fa-industry:before { + content: "\f275" !important; +} +.fa-map-pin:before { + content: "\f276" !important; +} +.fa-map-signs:before { + content: "\f277" !important; +} +.fa-map-o:before { + content: "\f278" !important; +} +.fa-map:before { + content: "\f279" !important; +} +.fa-commenting:before { + content: "\f27a" !important; +} +.fa-commenting-o:before { + content: "\f27b" !important; +} +.fa-houzz:before { + content: "\f27c" !important; +} +.fa-vimeo:before { + content: "\f27d" !important; +} +.fa-black-tie:before { + content: "\f27e" !important; +} +.fa-fonticons:before { + content: "\f280" !important; +} +.fa-reddit-alien:before { + content: "\f281" !important; +} +.fa-edge:before { + content: "\f282" !important; +} +.fa-credit-card-alt:before { + content: "\f283" !important; +} +.fa-codiepie:before { + content: "\f284" !important; +} +.fa-modx:before { + content: "\f285" !important; +} +.fa-fort-awesome:before { + content: "\f286" !important; +} +.fa-usb:before { + content: "\f287" !important; +} +.fa-product-hunt:before { + content: "\f288" !important; +} +.fa-mixcloud:before { + content: "\f289" !important; +} +.fa-scribd:before { + content: "\f28a" !important; +} +.fa-pause-circle:before { + content: "\f28b" !important; +} +.fa-pause-circle-o:before { + content: "\f28c" !important; +} +.fa-stop-circle:before { + content: "\f28d" !important; +} +.fa-stop-circle-o:before { + content: "\f28e" !important; +} +.fa-shopping-bag:before { + content: "\f290" !important; +} +.fa-shopping-basket:before { + content: "\f291" !important; +} +.fa-hashtag:before { + content: "\f292" !important; +} +.fa-bluetooth:before { + content: "\f293" !important; +} +.fa-bluetooth-b:before { + content: "\f294" !important; +} +.fa-percent:before { + content: "\f295" !important; +} +.fa-gitlab:before { + content: "\f296" !important; +} +.fa-wpbeginner:before { + content: "\f297" !important; +} +.fa-wpforms:before { + content: "\f298" !important; +} +.fa-envira:before { + content: "\f299" !important; +} +.fa-universal-access:before { + content: "\f29a" !important; +} +.fa-wheelchair-alt:before { + content: "\f29b" !important; +} +.fa-question-circle-o:before { + content: "\f29c" !important; +} +.fa-blind:before { + content: "\f29d" !important; +} +.fa-audio-description:before { + content: "\f29e" !important; +} +.fa-volume-control-phone:before { + content: "\f2a0" !important; +} +.fa-braille:before { + content: "\f2a1" !important; +} +.fa-assistive-listening-systems:before { + content: "\f2a2" !important; +} +.fa-asl-interpreting:before, +.fa-american-sign-language-interpreting:before { + content: "\f2a3" !important; +} +.fa-deafness:before, +.fa-hard-of-hearing:before, +.fa-deaf:before { + content: "\f2a4" !important; +} +.fa-glide:before { + content: "\f2a5" !important; +} +.fa-glide-g:before { + content: "\f2a6" !important; +} +.fa-signing:before, +.fa-sign-language:before { + content: "\f2a7" !important; +} +.fa-low-vision:before { + content: "\f2a8" !important; +} +.fa-viadeo:before { + content: "\f2a9" !important; +} +.fa-viadeo-square:before { + content: "\f2aa" !important; +} +.fa-snapchat:before { + content: "\f2ab" !important; +} +.fa-snapchat-ghost:before { + content: "\f2ac" !important; +} +.fa-snapchat-square:before { + content: "\f2ad" !important; +} +.fa-pied-piper:before { + content: "\f2ae" !important; +} +.fa-first-order:before { + content: "\f2b0" !important; +} +.fa-yoast:before { + content: "\f2b1" !important; +} +.fa-themeisle:before { + content: "\f2b2" !important; +} +.fa-google-plus-circle:before, +.fa-google-plus-official:before { + content: "\f2b3" !important; +} +.fa-fa:before, +.fa-font-awesome:before { + content: "\f2b4" !important; +} +.fa-handshake-o:before { + content: "\f2b5" !important; +} +.fa-envelope-open:before { + content: "\f2b6" !important; +} +.fa-envelope-open-o:before { + content: "\f2b7" !important; +} +.fa-linode:before { + content: "\f2b8" !important; +} +.fa-address-book:before { + content: "\f2b9" !important; +} +.fa-address-book-o:before { + content: "\f2ba" !important; +} +.fa-vcard:before, +.fa-address-card:before { + content: "\f2bb" !important; +} +.fa-vcard-o:before, +.fa-address-card-o:before { + content: "\f2bc" !important; +} +.fa-user-circle:before { + content: "\f2bd" !important; +} +.fa-user-circle-o:before { + content: "\f2be" !important; + color: #a55ec7 !important; +} +.fa-user-o:before { + content: "\f2c0" !important; +} +.fa-id-badge:before { + content: "\f2c1" !important; +} +.fa-drivers-license:before, +.fa-id-card:before { + content: "\f2c2" !important; +} +.fa-drivers-license-o:before, +.fa-id-card-o:before { + content: "\f2c3" !important; +} +.fa-quora:before { + content: "\f2c4" !important; +} +.fa-free-code-camp:before { + content: "\f2c5" !important; +} +.fa-telegram:before { + content: "\f2c6" !important; +} +.fa-thermometer-4:before, +.fa-thermometer:before, +.fa-thermometer-full:before { + content: "\f2c7" !important; +} +.fa-thermometer-3:before, +.fa-thermometer-three-quarters:before { + content: "\f2c8" !important; +} +.fa-thermometer-2:before, +.fa-thermometer-half:before { + content: "\f2c9" !important; +} +.fa-thermometer-1:before, +.fa-thermometer-quarter:before { + content: "\f2ca" !important; +} +.fa-thermometer-0:before, +.fa-thermometer-empty:before { + content: "\f2cb" !important; +} +.fa-shower:before { + content: "\f2cc" !important; +} +.fa-bathtub:before, +.fa-s15:before, +.fa-bath:before { + content: "\f2cd" !important; +} +.fa-podcast:before { + content: "\f2ce" !important; +} +.fa-window-maximize:before { + content: "\f2d0" !important; +} +.fa-window-minimize:before { + content: "\f2d1" !important; +} +.fa-window-restore:before { + content: "\f2d2" !important; +} +.fa-times-rectangle:before, +.fa-window-close:before { + content: "\f2d3" !important; +} +.fa-times-rectangle-o:before, +.fa-window-close-o:before { + content: "\f2d4" !important; +} +.fa-bandcamp:before { + content: "\f2d5" !important; +} +.fa-grav:before { + content: "\f2d6" !important; +} +.fa-etsy:before { + content: "\f2d7" !important; +} +.fa-imdb:before { + content: "\f2d8" !important; +} +.fa-ravelry:before { + content: "\f2d9" !important; +} +.fa-eercast:before { + content: "\f2da" !important; +} +.fa-microchip:before { + content: "\f2db" !important; +} +.fa-snowflake-o:before { + content: "\f2dc" !important; +} +.fa-superpowers:before { + content: "\f2dd" !important; +} +.fa-wpexplorer:before { + content: "\f2de" !important; +} +.fa-meetup:before { + content: "\f2e0" !important; +} +.x-fa:before { + font-family: FontAwesome !important; +} +@font-face { + font-family: "ExtJS"; + src: url("../resources/font-ext/fonts/ExtJS.eot?-tqegh9"); + src: url("../resources/font-ext/fonts/ExtJS.eot?#iefix-tqegh9") + format("embedded-opentype"), + url("../../ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.ttf?-tqegh9") format("truetype"), + url("../../ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.woff?-tqegh9") format("woff"), + url("../../ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.svg?-tqegh9#ExtJS") format("svg"); + font-weight: normal; + font-style: normal; +} +.ext { + font-family: ExtJS; +} +.ext-sencha:before { + content: "\e61e"; +} +.ext-checkbox-checked:before { + content: "\e613"; +} +.ext-checkbox-unchecked:before { + content: "\e614"; +} +.ext-chevron-left:before { + content: "\e615"; +} +.ext-chevron-right:before { + content: "\e616"; +} +.ext-double-chevron-left:before { + content: "\e617"; +} +.ext-double-chevron-right:before { + content: "\e618"; +} +.ext-sort-down:before { + content: "\e619"; +} +.ext-sort-up:before { + content: "\e61a"; +} +.ext-spinner-down:before { + content: "\e61b"; +} +.ext-spinner-up:before { + content: "\e61c"; +} +.ext-square-edit:before { + content: "\e61d"; +} +.ext-equals-vertical:before { + content: "\e612"; +} +.ext-expand:before { + content: "\e600"; +} +.ext-columns:before { + content: "\e601"; +} +.ext-dirty:before { + content: "\e602"; +} +.ext-dirty-rtl:before { + content: "\e603"; +} +.ext-edit-html:before { + content: "\e604"; +} +.ext-equals:before { + content: "\e605"; +} +.ext-collapse:before { + content: "\e606"; +} +.ext-group-by:before { + content: "\e607"; +} +.ext-minimize:before { + content: "\e608"; +} +.ext-nw-handle:before { + content: "\e609"; +} +.ext-ne-handle:before { + content: "\e60a"; +} +.ext-sw-handle:before { + content: "\e60b"; +} +.ext-se-handle:before { + content: "\e60c"; +} +.ext-text-background-color:before { + content: "\e60d"; +} +.ext-text-color:before { + content: "\e60e"; +} +.ext-text-decrease:before { + content: "\e60f"; +} +.ext-text-increase:before { + content: "\e610"; +} +.ext-unpin:before { + content: "\e611"; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-Light"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Light.ttf"); + font-weight: 300; + font-style: normal; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-LightItalic"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-LightItalic.ttf"); + font-weight: 300; + font-style: italic; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-Regular"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Regular.ttf"); + font-weight: 400; + font-style: normal; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-Italic"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Italic.ttf"); + font-weight: 400; + font-style: italic; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-Semibold"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Semibold.ttf"); + font-weight: 600; + font-style: normal; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-SemiboldItalic"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-SemiboldItalic.ttf"); + font-weight: 600; + font-style: italic; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-Bold"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Bold.ttf"); + font-weight: 700; + font-style: normal; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-BoldItalic"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-BoldItalic.ttf"); + font-weight: 700; + font-style: italic; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-ExtraBold"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/OpenSans-ExtraBold.ttf"); + font-weight: 800; + font-style: normal; +} +@font-face { + font-family: "Open Sans"; + src: local("OpenSans-ExtraBoldItalic"); + src: url("../../ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/OpenSans-ExtraBoldItalic.ttf"); + font-weight: 800; + font-style: italic; +} +.x-menu-item-active .x-menu-item-text { + font-weight: 500; +} +.x-tab-close-btn:before { + display: block; + width: 16px; + line-height: 16px; + text-align: center; +} +.x-surface, +.x-surface-canvas { + position: absolute; +} +.x-draw-container { + position: relative; + cursor: default; +} +.x-legend { + background: #fff; + outline: none; +} +.x-legend-horizontal { + overflow-x: auto; + overflow-y: hidden; +} +.x-legend-horizontal .x-legend-item { + display: inline-block; + border-right: 1px solid #ccc; + border-top: 1px solid #ccc; + border-bottom: 1px solid #ccc; +} +.x-legend-horizontal .x-legend-item:first-child { + border-left: 1px solid #ccc; + border-bottom-left-radius: 0; + border-top-left-radius: 0; +} +.x-legend-horizontal .x-legend-item:last-child { + border-bottom-right-radius: 0; + border-top-right-radius: 0; +} +.x-legend-horizontal.x-rtl .x-legend-item:first-child { + border-right: 1px solid #ccc; + border-bottom-right-radius: 0; + border-top-right-radius: 0; +} +.x-legend-horizontal.x-rtl .x-legend-item:last-child { + border-right: none; + border-bottom-left-radius: 0; + border-top-left-radius: 0; +} +.x-legend-vertical { + overflow-x: hidden; + overflow-y: auto; +} +.x-legend-vertical .x-legend-item { + border-left: 1px solid #ccc; + border-right: 1px solid #ccc; + border-bottom: 1px solid #ccc; +} +.x-legend-vertical .x-legend-item:first-child { + border-top: 1px solid #ccc; + border-top-left-radius: 0; + border-top-right-radius: 0; +} +.x-legend-vertical .x-legend-item:last-child { + border-bottom-left-radius: 0; + border-bottom-right-radius: 0; +} +.x-legend-item-inactive { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +.x-legend-item { + padding: 0.8em 0.6em 0.8em 1.8em; + color: #333; + background: rgba(255, 255, 255, 0); + max-width: 16em; + min-width: 0; + font-size: 13px; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 13px; + font-weight: 400; + white-space: nowrap; + overflow: hidden; + text-overflow: ellipsis; + position: relative; +} +.x-rtl > * > .x-legend-item { + padding: 0.8em 1.8em 0.8em 1em; +} +.x-legend-item-marker { + position: absolute; + width: 0.8em; + height: 0.8em; + -webkit-box-shadow: rgba(255, 255, 255, 0.3) 0 1px 0, + rgba(0, 0, 0, 0.4) 0 1px 0 inset; + -moz-box-shadow: rgba(255, 255, 255, 0.3) 0 1px 0, + rgba(0, 0, 0, 0.4) 0 1px 0 inset; + box-shadow: rgba(255, 255, 255, 0.3) 0 1px 0, rgba(0, 0, 0, 0.4) 0 1px 0 inset; + left: 0.7em; + top: 0.85em; +} +.x-rtl > * > * > .x-legend-item-marker { + right: 0.7em; +} +.x-legend-inner { + display: table; + text-align: center; + padding: 10px; +} +.x-legend-horizontal .x-legend-inner { + min-width: 100%; +} +.x-legend-vertical .x-legend-inner { + min-height: 100%; +} +.x-legend-container { + display: table-cell; + vertical-align: middle; + white-space: nowrap; + line-height: 0; + background: #fff; + -webkit-box-shadow: rgba(255, 255, 255, 0.6) 0 1px 1px; + -moz-box-shadow: rgba(255, 255, 255, 0.6) 0 1px 1px; + box-shadow: rgba(255, 255, 255, 0.6) 0 1px 1px; +} +.x-chart-image { + width: 100%; + height: auto; +} +.x-responsivecolumn { + padding: 20px 10px 0 20px; +} +.x-responsivecolumn > * { + margin: 0 10px 10px 0; + float: left; +} +.weather-panel { + background: #fff; +} +.weather-image-container { + height: 80px; + width: 100px; + float: left; + background: #82d9ea; + text-align: center; + padding-top: 20px; +} +.weather-details-container { + color: #458fd2; + line-height: 20px; + float: left; + padding: 20px; +} +.weather-details-container :first-child { + margin-bottom: 4px; + font-size: 30px; +} +.forms-specialoffer { + background-color: #579ddb; + color: #fff; + text-align: center; + position: relative; +} +.forms-specialoffer h3 { + font-size: 24px; + font-weight: 300; + margin-bottom: 10px; +} +.specialoffer-outer { + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; + padding: 0 1.4em; +} +.specialoffer-outer:before { + content: ""; + display: inline-block; + vertical-align: middle; + height: 100%; +} +.specialoffer-inner { + display: inline-block; + vertical-align: middle; +} +.specialoffer-icon-wrap { + background-color: rgba(255, 255, 255, 0.1); + padding: 1.2em; + height: 100px; + width: 100px; + display: inline-block; +} +.specialoffer-text { + font-weight: 400; + margin: 1em 0; +} +.specialoffer-discount { + font-weight: 700; + font-size: 1.2em; +} +.specialoffer-link { + padding: 1em 1.2em 0.3em; + font-size: 1.2em; + color: #fff; + text-decoration: none; +} +.specialoffer-link:before { + padding-right: 0.5em; +} +.userProfile-container .userProfilePic { + border: 4px solid #ddd; + -webkit-border-radius: 50%; + -moz-border-radius: 50%; + -ms-border-radius: 50%; + -o-border-radius: 50%; + border-radius: 50%; +} +.userProfile-container .userProfileName { + font-size: 16px; + font-weight: bold; + line-height: 30px; + color: #404040; +} +.userProfile-container .userProfileDesc { + color: #404040; + line-height: 16px; +} +.userProfile-container .user-profile-desc .x-box-item:before, +.userProfile-container .user-profile-desc .x-layout-box-item:before { + color: #5aaed4; + margin-right: 12px; + font-size: 18px; + position: relative; + top: 2px; +} +.userProfile-container .user-profile-desc a { + color: #404040; + text-decoration: none; +} +.userProfile-container .user-profile-desc .box { + margin-left: 40px; + line-height: 14px; + font-size: 14px; + line-height: 18px; +} +.userProfile-container .user-profile-desc .box:before { + margin-left: -20px; + color: #5aaed4; +} +.userProfile-container .user-profile-desc .x-toolbar { + border: none; +} +.userProfile-container .about-me-wrap { + border-top: 1px solid #ddd; +} +.userProfile-container .about-me-wrap h3 { + margin: 0; + font-size: 16px; + font-weight: 600; + padding: 14px 0 10px 0; + display: block; + margin-left: 20px; +} +.userProfile-container .about-me-wrap h3:before { + font-size: 18px; + font-weight: normal; + color: #5aaed4; + margin-right: 12px; +} +.userProfile-container .about-me-wrap p { + margin: 0; + padding: 0 20px 20px 26px; +} +.userProfile-container .likes-friends-wrap { + text-align: center; + border-top: 1px solid #ddd; +} +.userProfile-container .likes-friends-wrap .x-panel { + margin-top: 12px; +} +.userProfile-container .likes-friends-wrap .friends-count-wrap { + border-left: 1px solid #ddd; +} +.userProfile-container .large-icon:before { + color: #5aaed4; + font-size: 35px !important; +} +.userProfile-container .icon-padding:before { + padding: 16px; + color: #5aaed4; +} +.userProfile-container .tall-separator { + height: 48px; +} +.userProfile-container .fa-ellipsis-v { + font-size: 20px; +} +.userProfile-container .likes-value, +.userProfile-container .friends-value { + font-size: 16px; + line-height: 24px; + font-weight: normal; +} +.userProfile-container .comments { + margin-bottom: 10px; +} +.userProfile-container .comments img.profile-icon { + height: 50px; + width: 50px; + border: 2px solid #ddd; + -webkit-border-radius: 50%; + -moz-border-radius: 50%; + -ms-border-radius: 50%; + -o-border-radius: 50%; + border-radius: 50%; + float: left; +} +.userProfile-container .comments h4 { + font-size: 14px; + margin: 0 10px 12px 0; + float: left; +} +.userProfile-container .comments h4 span { + margin-left: 8px; + font-size: 18px; + position: relative; + top: 2px; +} +.userProfile-container .comments .from-now { + float: right; +} +.userProfile-container .comments .from-now span { + margin-right: 5px; + font-size: 16px; + position: relative; + top: 1px; +} +.userProfile-container .comments .content-wrap { + margin-left: 65px; +} +.userProfile-container .comments .content-wrap .content { + margin-bottom: 15px; + white-space: normal; + clear: both; +} +.userProfile-container .comments.sub-comments { + margin: 0 0 10px 60px; + border-bottom: 1px solid #ddd; +} +.userProfile-container .comments.sub-comments .like-comment-btn-wrap { + border-bottom: none; +} +.userProfile-container .like-comment-btn-wrap { + text-align: right; + padding-bottom: 15px; + border-bottom: 1px solid #ddd; +} +.userProfile-container .like-comment-btn-wrap button { + margin-left: 15px; + padding: 0; + height: 30px; + width: 30px; + background-color: #f4f4f4; + font-size: 14px; + color: #404040; + border: none; + cursor: pointer; +} +.userProfile-container .x-grid-item, +.userProfile-container .x-grid-item-over { + background: #fff; + border: 0; +} +.userProfile-container .x-grid-item:last-child { + border-bottom: none; +} +.userProfile-container .x-grid-item:last-child .like-comment-btn-wrap { + border-bottom: none; + padding-bottom: 0; +} +.userProfile-container .x-grid-item:last-child .comments { + margin-bottom: 0; +} +.userProfile-container .x-grid-cell-inner { + padding: 0; +} +.userProfile-container .timeline-item .line-wrap { + position: relative; +} +.userProfile-container .timeline-item .line-wrap:before { + content: ""; + position: absolute; + width: 50px; + height: 100%; + border-right: solid 2px #5aaed4; + left: 0; + top: 70px; +} +.userProfile-container .timeline-item .profile-pic-wrap { + width: 100px; + float: left; + font-size: 10px; + text-align: center; + position: relative; + background: #fff; + padding: 5px 0; +} +.userProfile-container .timeline-item .profile-pic-wrap img { + height: 46px; + width: 46px; + -webkit-border-radius: 50%; + -moz-border-radius: 50%; + -ms-border-radius: 50%; + -o-border-radius: 50%; + border-radius: 50%; +} +.userProfile-container .timeline-item .contents-wrap { + margin: 0 0px 15px 110px; + border: 1px solid #ddd; + position: relative; + padding: 15px; + white-space: normal; +} +.userProfile-container .timeline-item .contents-wrap:before, +.userProfile-container .timeline-item .contents-wrap:after { + content: ""; + display: block; + position: absolute; + width: 0; + height: 0; + left: 0; + top: 0; +} +.userProfile-container .timeline-item .contents-wrap:before { + border-top: 9px solid transparent; + border-bottom: 9px solid transparent; + border-right: 9px solid #ddd; + margin: 15px 0 0 -9px; +} +.userProfile-container .timeline-item .contents-wrap:after { + border-top: 9px solid transparent; + border-bottom: 9px solid transparent; + border-right: 9px solid #fff; + margin: 15px 0 0 -8px; +} +.userProfile-container .timeline-item .contents-wrap .shared-by, +.userProfile-container .timeline-item .contents-wrap .followed-by { + font-size: 12px; + line-height: 18px; + margin-bottom: 10px; +} +.userProfile-container .timeline-item .contents-wrap .shared-by a, +.userProfile-container .timeline-item .contents-wrap .followed-by a { + color: #5aaed4; + text-decoration: none; + font-weight: bold; +} +.userProfile-container .timeline-item .contents-wrap .shared-img { + width: 100%; + display: block; +} +.userProfile-container .timeline-item .contents-wrap .job-meeting a { + color: #5aaed4; + text-decoration: none; + font-weight: bold; + margin-bottom: 10px; + display: block; +} +.userProfile-container .timeline-item .article-comment { + border-left: 5px solid #ddd; + padding: 10px 20px; +} +.userProfile-container .timeline-item .article-comment span { + margin-right: 10px; + color: #eee; +} +.userProfile-container .timeline-item .followed-by img { + height: 32px; + width: 32px; + -webkit-border-radius: 50%; + -moz-border-radius: 50%; + -ms-border-radius: 50%; + -o-border-radius: 50%; + border-radius: 50%; + margin-right: 5px; + float: left; +} +.userProfile-container .timeline-item .followed-by .followed-by-inner { + margin-left: 40px; + padding: 5px 0; +} +.profiledescription-social-toolbar { + border-top: 1px solid #ddd !important; +} +@media (max-width: 450px) { + .userProfile-container .comments h4, + .userProfile-container .comments .from-now { + float: none; + } + .userProfile-container .comments .from-now { + margin-bottom: 10px; + } + .userProfile-container .comments h4 { + margin: 0; + } +} +@media (max-width: 350px) { + .timeline-items-wrap { + display: none; + } +} +@media (max-width: 420px) { + .profiledescription-social-toolbar { + display: none !important; + } +} +.user-notifications, +.timeline-items-wrap { + padding: 15px; + background: #fff; +} +.timeline-epoch { + width: 100px; + background: #fff; + text-align: center; + padding: 7px 5px; + position: relative; + margin-bottom: 15px; + color: #5aaed4; + font-size: 14px; + border: solid 3px #5aaed4; + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + font-weight: bold; +} +.timeline-item-last .line-wrap:before { + display: none; +} +@media (max-width: 320px) { + .phone .user-profile-desc { + height: 380px !important; + } + .phone .userProfile-container .icon-padding:before { + padding: 16px 8px; + } + .phone + .userProfile-container + .timeline-items-wrap + .x-dataview-item + .timeline-item:before { + height: 540px; + } +} +.big-100 { + width: calc(100% - 20px); + background-position: 100% 20px !important; +} +.big-60 { + width: calc(60% - 20px); + background-position: 60% 20px !important; +} +.big-50 { + width: calc(50% - 20px); + background-position: 50% 20px !important; +} +.big-40 { + width: calc(40% - 20px); + background-position: 40% 20px !important; +} +.big-33 { + width: calc(33.33% - 20px); + background-position: 33.33% 20px !important; +} +.big-20 { + width: calc(20% - 20px); + background-position: 20% 20px !important; +} +.big-25 { + width: calc(25% - 20px); + background-position: 25% 20px !important; +} +.x-responsivecolumn-small > .small-100 { + width: calc(100% - 20px); + background-position: 100% 20px !important; +} +.x-responsivecolumn-small > .small-50 { + width: calc(50% - 20px); + background-position: 50% 20px !important; +} +.sencha-logo { + background-color: #f6f6f6; + height: 65px; + font-size: 16px; + color: #404040; + font-weight: bold; + margin-left: 17px; + +} +.sencha-logo .main-logo { + line-height: 65px; +} +.sencha-logo .main-logo img { + margin-left: 22px; + margin-right: 22px; + top: 8px; + position: relative; +} +.sencha-dash-dash-headerbar { + padding: 0 30px 0 0; + position: fixed; + width: 100%; + z-index: 10; + border: none; +} +.sencha-dash-dash-headerbar .header-right-profile-image { + border-radius: 20px; +} +.top-english-button .x-btn-icon-el { + width: 21px; + height: 14px; +} +.collapsed .hot-icon:after, +.collapsed .new-icon:after { + display: none; +} +.collapsed .x-tree-elbow-img { + display: none; +} +.collapsed .x-tree-node-text { + display: none; +} +.x-grid-cell { + position: relative; +} +.hot-icon.hot-icon:after, +.new-icon.hot-icon:after { + content: "HOT"; + background: #e3495a; +} +.hot-icon.new-icon:after, +.new-icon.new-icon:after { + content: "NEW"; + background: #5aaed4; +} +.hot-icon:after, +.new-icon:after { + height: 18px; + width: 34px; + display: inline-block; + position: absolute; + top: 22px; + right: -180px; + text-align: center; + color: #fff; + font-weight: bold; + font-size: 10px; + line-height: 18px; +} +.x-treelist-item-tool { + height: 64px; +} +.x-treelist-item-tool.hot-icon:after, +.x-treelist-item-tool.new-icon:after { + background: #5aaed4; + content: ""; +} +.x-html-editor-input { + border: 1px solid #ccc; +} +.x-btn-soft-blue-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #2eadf5; +} +.x-btn-soft-blue-small-mc { + background-color: #2eadf5; +} +.x-nbr .x-btn-soft-blue-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-blue-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-blue-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-blue-small-tr { + background-position: right -3px; +} +.x-btn-soft-blue-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-blue-small-br { + background-position: right -5px; +} +.x-btn-soft-blue-small-ml { + background-position: 0 top; +} +.x-btn-soft-blue-small-mr { + background-position: right top; +} +.x-btn-soft-blue-small-tc { + background-position: 0 0; +} +.x-btn-soft-blue-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-blue-small-tr, +.x-btn-soft-blue-small-br, +.x-btn-soft-blue-small-mr { + padding-right: 1px; +} +.x-btn-soft-blue-small-tl, +.x-btn-soft-blue-small-bl, +.x-btn-soft-blue-small-ml { + padding-left: 1px; +} +.x-btn-soft-blue-small-tc { + height: 1px; +} +.x-btn-soft-blue-small-bc { + height: 1px; +} +.x-btn-soft-blue-small-tl, +.x-btn-soft-blue-small-bl, +.x-btn-soft-blue-small-tr, +.x-btn-soft-blue-small-br, +.x-btn-soft-blue-small-tc, +.x-btn-soft-blue-small-bc, +.x-btn-soft-blue-small-ml, +.x-btn-soft-blue-small-mr { + background-image: url(images/btn/btn-soft-blue-small-corners.gif); +} +.x-btn-soft-blue-small-ml, +.x-btn-soft-blue-small-mr { + background-image: url(images/btn/btn-soft-blue-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-blue-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-blue-small { + border-color: #16a3f4; +} +.x-btn-button-soft-blue-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-blue-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-blue-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-blue-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-blue-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-blue-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-blue-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-blue-small { + max-width: none; +} +.x-btn-icon-el-soft-blue-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-blue-small, +.x-btn-icon-right > .x-btn-icon-el-soft-blue-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-blue-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-blue-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-blue-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-blue-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-blue-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-blue-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-blue-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-blue-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-blue-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-blue-small, +.x-btn-split-bottom > .x-btn-button-soft-blue-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-blue-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-blue-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-blue-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-blue-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-blue-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-soft-blue-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-blue-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-blue-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-blue-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-blue-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-blue-small { + background-image: none; + background-color: #2eadf5; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-soft-blue-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-blue-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-soft-blue-small { + border-color: #1496e0; + background-image: none; + background-color: #2a9fe1; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-blue-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-blue-small, +.x-btn.x-btn-pressed.x-btn-soft-blue-small { + border-color: #107bb7; + background-image: none; + background-color: #2382b8; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-blue-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-blue-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-blue-small { + background-image: none; + background-color: #2eadf5; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-small-bc { + background-image: url(images/btn/btn-soft-blue-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-small-mr { + background-image: url(images/btn/btn-soft-blue-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-small-mc { + background-color: #2eadf5; +} +.x-btn-over .x-btn-soft-blue-small-tl, +.x-btn-over .x-btn-soft-blue-small-bl, +.x-btn-over .x-btn-soft-blue-small-tr, +.x-btn-over .x-btn-soft-blue-small-br, +.x-btn-over .x-btn-soft-blue-small-tc, +.x-btn-over .x-btn-soft-blue-small-bc { + background-image: url(images/btn/btn-soft-blue-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-blue-small-ml, +.x-btn-over .x-btn-soft-blue-small-mr { + background-image: url(images/btn/btn-soft-blue-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-blue-small-mc { + background-color: #2a9fe1; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-small-bc { + background-image: url(images/btn/btn-soft-blue-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-small-mr { + background-image: url(images/btn/btn-soft-blue-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-small-mc { + background-color: #2a9fe1; +} +.x-btn.x-btn-menu-active .x-btn-soft-blue-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-blue-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-blue-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-blue-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-blue-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-blue-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-blue-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-blue-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-blue-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-blue-small-br, +.x-btn.x-btn-pressed .x-btn-soft-blue-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-blue-small-bc { + background-image: url(images/btn/btn-soft-blue-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-blue-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-blue-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-blue-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-blue-small-mr { + background-image: url(images/btn/btn-soft-blue-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-blue-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-blue-small-mc { + background-color: #2382b8; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-small-bc { + background-image: url(images/btn/btn-soft-blue-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-small-mr { + background-image: url(images/btn/btn-soft-blue-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-small-mc { + background-color: #2382b8; +} +.x-btn.x-btn-disabled .x-btn-soft-blue-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-blue-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-blue-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-blue-small-br, +.x-btn.x-btn-disabled .x-btn-soft-blue-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-blue-small-bc { + background-image: url(images/btn/btn-soft-blue-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-blue-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-blue-small-mr { + background-image: url(images/btn/btn-soft-blue-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-blue-small-mc { + background-color: #2eadf5; +} +.x-nbr .x-btn-soft-blue-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-blue-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-small.x-segmented-button-first + .x-btn-soft-blue-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-small.x-segmented-button-middle + .x-btn-soft-blue-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-small.x-segmented-button-last + .x-btn-soft-blue-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-small.x-segmented-button-first + .x-btn-soft-blue-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-small.x-segmented-button-middle + .x-btn-soft-blue-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-small.x-segmented-button-last + .x-btn-soft-blue-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-blue-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-blue-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-blue-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-blue-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-blue-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-blue-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-blue-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-soft-blue-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #2eadf5; +} +.x-btn-soft-blue-large-mc { + background-color: #2eadf5; +} +.x-nbr .x-btn-soft-blue-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-blue-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +.x-btn-soft-blue-large-tl { + background-position: 0 -2px; +} +.x-btn-soft-blue-large-tr { + background-position: right -3px; +} +.x-btn-soft-blue-large-bl { + background-position: 0 -4px; +} +.x-btn-soft-blue-large-br { + background-position: right -5px; +} +.x-btn-soft-blue-large-ml { + background-position: 0 top; +} +.x-btn-soft-blue-large-mr { + background-position: right top; +} +.x-btn-soft-blue-large-tc { + background-position: 0 0; +} +.x-btn-soft-blue-large-bc { + background-position: 0 -1px; +} +.x-btn-soft-blue-large-tr, +.x-btn-soft-blue-large-br, +.x-btn-soft-blue-large-mr { + padding-right: 1px; +} +.x-btn-soft-blue-large-tl, +.x-btn-soft-blue-large-bl, +.x-btn-soft-blue-large-ml { + padding-left: 1px; +} +.x-btn-soft-blue-large-tc { + height: 1px; +} +.x-btn-soft-blue-large-bc { + height: 1px; +} +.x-btn-soft-blue-large-tl, +.x-btn-soft-blue-large-bl, +.x-btn-soft-blue-large-tr, +.x-btn-soft-blue-large-br, +.x-btn-soft-blue-large-tc, +.x-btn-soft-blue-large-bc, +.x-btn-soft-blue-large-ml, +.x-btn-soft-blue-large-mr { + background-image: url(images/btn/btn-soft-blue-large-corners.gif); +} +.x-btn-soft-blue-large-ml, +.x-btn-soft-blue-large-mr { + background-image: url(images/btn/btn-soft-blue-large-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-blue-large-mc { + padding: 9px 9px 9px 9px; +} +.x-btn-soft-blue-large { + border-color: #16a3f4; +} +.x-btn-button-soft-blue-large { + min-height: 34px; +} +.x-ie9m .x-btn-button-soft-blue-large { + min-height: auto; + height: 34px; +} +.x-btn-inner-soft-blue-large { + font: 500 16px/34px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 10px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-blue-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-blue-large { + max-width: calc(100% - 24px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-blue-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-blue-large { + max-width: calc(100% - 23px); +} +.x-ie10p .x-btn-inner-soft-blue-large { + max-width: none; +} +.x-btn-icon-el-soft-blue-large { + font-size: 24px; + height: 24px; + color: #f0f0f0; + line-height: 24px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-blue-large, +.x-btn-icon-right > .x-btn-icon-el-soft-blue-large { + width: 24px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-blue-large, +.x-btn-icon-bottom > .x-btn-icon-el-soft-blue-large { + min-width: 24px; +} +.x-ie8 .x-btn-icon-el-soft-blue-large.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-blue-large { + margin-right: 0; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-blue-large { + margin-left: 0; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-blue-large { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-blue-large { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-blue-large { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-blue-large { + margin-right: 10px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-blue-large, +.x-btn-split-bottom > .x-btn-button-soft-blue-large { + padding-bottom: 9px; +} +.x-btn-wrap-soft-blue-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-blue-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-blue-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +.x-btn-wrap-soft-blue-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-blue-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; + padding-left: 9px; +} +.x-btn-wrap-soft-blue-large.x-btn-split-bottom { + margin-bottom: -9px; +} +.x-btn-wrap-soft-blue-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-blue-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-blue-large { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-blue-large { + margin-right: 10px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-blue-large { + background-image: none; + background-color: #2eadf5; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-soft-blue-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-blue-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-soft-blue-large { + border-color: #1496e0; + background-image: none; + background-color: #2a9fe1; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-blue-large { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-blue-large, +.x-btn.x-btn-pressed.x-btn-soft-blue-large { + border-color: #107bb7; + background-image: none; + background-color: #2382b8; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-blue-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-blue-large { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-blue-large { + background-image: none; + background-color: #2eadf5; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-large-bc { + background-image: url(images/btn/btn-soft-blue-large-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-large-mr { + background-image: url(images/btn/btn-soft-blue-large-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-large-mc { + background-color: #2eadf5; +} +.x-btn-over .x-btn-soft-blue-large-tl, +.x-btn-over .x-btn-soft-blue-large-bl, +.x-btn-over .x-btn-soft-blue-large-tr, +.x-btn-over .x-btn-soft-blue-large-br, +.x-btn-over .x-btn-soft-blue-large-tc, +.x-btn-over .x-btn-soft-blue-large-bc { + background-image: url(images/btn/btn-soft-blue-large-over-corners.gif); +} +.x-btn-over .x-btn-soft-blue-large-ml, +.x-btn-over .x-btn-soft-blue-large-mr { + background-image: url(images/btn/btn-soft-blue-large-over-sides.gif); +} +.x-btn-over .x-btn-soft-blue-large-mc { + background-color: #2a9fe1; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-large-bc { + background-image: url(images/btn/btn-soft-blue-large-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-large-mr { + background-image: url(images/btn/btn-soft-blue-large-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-large-mc { + background-color: #2a9fe1; +} +.x-btn.x-btn-menu-active .x-btn-soft-blue-large-tl, +.x-btn.x-btn-menu-active .x-btn-soft-blue-large-bl, +.x-btn.x-btn-menu-active .x-btn-soft-blue-large-tr, +.x-btn.x-btn-menu-active .x-btn-soft-blue-large-br, +.x-btn.x-btn-menu-active .x-btn-soft-blue-large-tc, +.x-btn.x-btn-menu-active .x-btn-soft-blue-large-bc, +.x-btn.x-btn-pressed .x-btn-soft-blue-large-tl, +.x-btn.x-btn-pressed .x-btn-soft-blue-large-bl, +.x-btn.x-btn-pressed .x-btn-soft-blue-large-tr, +.x-btn.x-btn-pressed .x-btn-soft-blue-large-br, +.x-btn.x-btn-pressed .x-btn-soft-blue-large-tc, +.x-btn.x-btn-pressed .x-btn-soft-blue-large-bc { + background-image: url(images/btn/btn-soft-blue-large-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-blue-large-ml, +.x-btn.x-btn-menu-active .x-btn-soft-blue-large-mr, +.x-btn.x-btn-pressed .x-btn-soft-blue-large-ml, +.x-btn.x-btn-pressed .x-btn-soft-blue-large-mr { + background-image: url(images/btn/btn-soft-blue-large-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-blue-large-mc, +.x-btn.x-btn-pressed .x-btn-soft-blue-large-mc { + background-color: #2382b8; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-large-bc { + background-image: url(images/btn/btn-soft-blue-large-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-large-mr { + background-image: url(images/btn/btn-soft-blue-large-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-blue-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-large-mc { + background-color: #2382b8; +} +.x-btn.x-btn-disabled .x-btn-soft-blue-large-tl, +.x-btn.x-btn-disabled .x-btn-soft-blue-large-bl, +.x-btn.x-btn-disabled .x-btn-soft-blue-large-tr, +.x-btn.x-btn-disabled .x-btn-soft-blue-large-br, +.x-btn.x-btn-disabled .x-btn-soft-blue-large-tc, +.x-btn.x-btn-disabled .x-btn-soft-blue-large-bc { + background-image: url(images/btn/btn-soft-blue-large-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-blue-large-ml, +.x-btn.x-btn-disabled .x-btn-soft-blue-large-mr { + background-image: url(images/btn/btn-soft-blue-large-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-blue-large-mc { + background-color: #2eadf5; +} +.x-nbr .x-btn-soft-blue-large { + background-image: none; +} +.x-btn-disabled.x-btn-soft-blue-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-large.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-large.x-segmented-button-first + .x-btn-soft-blue-large-mc { + padding-right: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-large.x-segmented-button-middle + .x-btn-soft-blue-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-large.x-segmented-button-last + .x-btn-soft-blue-large-mc { + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-large.x-segmented-button-first + .x-btn-soft-blue-large-mc { + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-large.x-segmented-button-middle + .x-btn-soft-blue-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-large.x-segmented-button-last + .x-btn-soft-blue-large-mc { + padding-top: 9px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-blue-large:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-blue-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-large.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-large.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-blue-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-large.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-large.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-blue-large:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-blue-large:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-blue-large:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-blue-large:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-soft-blue-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #2eadf5; +} +.x-btn-soft-blue-toolbar-small-mc { + background-color: #2eadf5; +} +.x-nbr .x-btn-soft-blue-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-blue-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-blue-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-blue-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-soft-blue-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-blue-toolbar-small-br { + background-position: right -5px; +} +.x-btn-soft-blue-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-soft-blue-toolbar-small-mr { + background-position: right top; +} +.x-btn-soft-blue-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-soft-blue-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-blue-toolbar-small-tr, +.x-btn-soft-blue-toolbar-small-br, +.x-btn-soft-blue-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-soft-blue-toolbar-small-tl, +.x-btn-soft-blue-toolbar-small-bl, +.x-btn-soft-blue-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-soft-blue-toolbar-small-tc { + height: 1px; +} +.x-btn-soft-blue-toolbar-small-bc { + height: 1px; +} +.x-btn-soft-blue-toolbar-small-tl, +.x-btn-soft-blue-toolbar-small-bl, +.x-btn-soft-blue-toolbar-small-tr, +.x-btn-soft-blue-toolbar-small-br, +.x-btn-soft-blue-toolbar-small-tc, +.x-btn-soft-blue-toolbar-small-bc, +.x-btn-soft-blue-toolbar-small-ml, +.x-btn-soft-blue-toolbar-small-mr { + background-image: url(images/btn/btn-soft-blue-toolbar-small-corners.gif); +} +.x-btn-soft-blue-toolbar-small-ml, +.x-btn-soft-blue-toolbar-small-mr { + background-image: url(images/btn/btn-soft-blue-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-blue-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-blue-toolbar-small { + border-color: #16a3f4; +} +.x-btn-button-soft-blue-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-blue-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-blue-toolbar-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-blue-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-blue-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-blue-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-blue-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-blue-toolbar-small { + max-width: none; +} +.x-btn-icon-el-soft-blue-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-blue-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-soft-blue-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-blue-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-blue-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-blue-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-blue-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-blue-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-blue-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-blue-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-blue-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-blue-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-blue-toolbar-small, +.x-btn-split-bottom > .x-btn-button-soft-blue-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-blue-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-blue-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-blue-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-blue-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-blue-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-soft-blue-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-blue-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-blue-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-blue-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-blue-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-blue-toolbar-small { + background-image: none; + background-color: #2eadf5; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-soft-blue-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-blue-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-soft-blue-toolbar-small { + border-color: #159dea; + background-image: none; + background-color: #2ca6eb; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-blue-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-blue-toolbar-small, +.x-btn.x-btn-pressed.x-btn-soft-blue-toolbar-small { + border-color: #1496e0; + background-image: none; + background-color: #2a9fe1; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-blue-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-blue-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-blue-toolbar-small { + background-image: none; + background-color: #2eadf5; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-toolbar-small-bc { + background-image: url(images/btn/btn-soft-blue-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-toolbar-small-mr { + background-image: url(images/btn/btn-soft-blue-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-blue-toolbar-small-mc { + background-color: #2eadf5; +} +.x-btn-over .x-btn-soft-blue-toolbar-small-tl, +.x-btn-over .x-btn-soft-blue-toolbar-small-bl, +.x-btn-over .x-btn-soft-blue-toolbar-small-tr, +.x-btn-over .x-btn-soft-blue-toolbar-small-br, +.x-btn-over .x-btn-soft-blue-toolbar-small-tc, +.x-btn-over .x-btn-soft-blue-toolbar-small-bc { + background-image: url(images/btn/btn-soft-blue-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-blue-toolbar-small-ml, +.x-btn-over .x-btn-soft-blue-toolbar-small-mr { + background-image: url(images/btn/btn-soft-blue-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-blue-toolbar-small-mc { + background-color: #2ca6eb; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-toolbar-small-bc { + background-image: url(images/btn/btn-soft-blue-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-toolbar-small-mr { + background-image: url(images/btn/btn-soft-blue-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-blue-toolbar-small-mc { + background-color: #2ca6eb; +} +.x-btn.x-btn-menu-active .x-btn-soft-blue-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-blue-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-blue-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-blue-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-blue-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-blue-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-blue-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-blue-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-blue-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-blue-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-soft-blue-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-blue-toolbar-small-bc { + background-image: url(images/btn/btn-soft-blue-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-blue-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-blue-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-blue-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-blue-toolbar-small-mr { + background-image: url(images/btn/btn-soft-blue-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-blue-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-blue-toolbar-small-mc { + background-color: #2a9fe1; +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-blue-toolbar-small-tl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-blue-toolbar-small-bl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-blue-toolbar-small-tr, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-blue-toolbar-small-br, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-blue-toolbar-small-tc, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-blue-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-toolbar-small-bc { + background-image: url(images/btn/btn-soft-blue-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-blue-toolbar-small-ml, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-blue-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-toolbar-small-mr { + background-image: url(images/btn/btn-soft-blue-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-blue-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-blue-toolbar-small-mc { + background-color: #2a9fe1; +} +.x-btn.x-btn-disabled .x-btn-soft-blue-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-blue-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-blue-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-blue-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-soft-blue-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-blue-toolbar-small-bc { + background-image: url(images/btn/btn-soft-blue-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-blue-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-blue-toolbar-small-mr { + background-image: url(images/btn/btn-soft-blue-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-blue-toolbar-small-mc { + background-color: #2eadf5; +} +.x-nbr .x-btn-soft-blue-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-blue-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-toolbar-small.x-segmented-button-first + .x-btn-soft-blue-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-toolbar-small.x-segmented-button-middle + .x-btn-soft-blue-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-toolbar-small.x-segmented-button-last + .x-btn-soft-blue-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-toolbar-small.x-segmented-button-first + .x-btn-soft-blue-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-toolbar-small.x-segmented-button-middle + .x-btn-soft-blue-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-toolbar-small.x-segmented-button-last + .x-btn-soft-blue-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-blue-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-blue-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-blue-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-blue-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-blue-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-blue-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-blue-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-blue-toolbar-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-blue-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-facebook-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #167abc; +} +.x-btn-facebook-small-mc { + background-color: #167abc; +} +.x-nbr .x-btn-facebook-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-facebook-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-facebook-small-tl { + background-position: 0 -2px; +} +.x-btn-facebook-small-tr { + background-position: right -3px; +} +.x-btn-facebook-small-bl { + background-position: 0 -4px; +} +.x-btn-facebook-small-br { + background-position: right -5px; +} +.x-btn-facebook-small-ml { + background-position: 0 top; +} +.x-btn-facebook-small-mr { + background-position: right top; +} +.x-btn-facebook-small-tc { + background-position: 0 0; +} +.x-btn-facebook-small-bc { + background-position: 0 -1px; +} +.x-btn-facebook-small-tr, +.x-btn-facebook-small-br, +.x-btn-facebook-small-mr { + padding-right: 1px; +} +.x-btn-facebook-small-tl, +.x-btn-facebook-small-bl, +.x-btn-facebook-small-ml { + padding-left: 1px; +} +.x-btn-facebook-small-tc { + height: 1px; +} +.x-btn-facebook-small-bc { + height: 1px; +} +.x-btn-facebook-small-tl, +.x-btn-facebook-small-bl, +.x-btn-facebook-small-tr, +.x-btn-facebook-small-br, +.x-btn-facebook-small-tc, +.x-btn-facebook-small-bc, +.x-btn-facebook-small-ml, +.x-btn-facebook-small-mr { + background-image: url(images/btn/btn-facebook-small-corners.gif); +} +.x-btn-facebook-small-ml, +.x-btn-facebook-small-mr { + background-image: url(images/btn/btn-facebook-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-facebook-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-facebook-small { + border-color: #136ba5; +} +.x-btn-button-facebook-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-facebook-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-facebook-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-facebook-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-facebook-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-facebook-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-facebook-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-facebook-small { + max-width: none; +} +.x-btn-icon-el-facebook-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-facebook-small, +.x-btn-icon-right > .x-btn-icon-el-facebook-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-facebook-small, +.x-btn-icon-bottom > .x-btn-icon-el-facebook-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-facebook-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-facebook-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-facebook-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-facebook-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-facebook-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-facebook-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-facebook-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-facebook-small, +.x-btn-split-bottom > .x-btn-button-facebook-small { + padding-bottom: 7px; +} +.x-btn-wrap-facebook-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-facebook-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-facebook-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-facebook-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-facebook-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-facebook-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-facebook-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-facebook-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-facebook-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-facebook-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-facebook-small { + background-image: none; + background-color: #167abc; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-facebook-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-facebook-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-facebook-small { + border-color: #126398; + background-image: none; + background-color: #1470ad; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-facebook-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-facebook-small, +.x-btn.x-btn-pressed.x-btn-facebook-small { + border-color: #0e507c; + background-image: none; + background-color: #115c8d; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-facebook-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-facebook-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-facebook-small { + background-image: none; + background-color: #167abc; +} +.x-keyboard-mode .x-btn-focus .x-btn-facebook-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-small-bc { + background-image: url(images/btn/btn-facebook-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-facebook-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-small-mr { + background-image: url(images/btn/btn-facebook-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-facebook-small-mc { + background-color: #167abc; +} +.x-btn-over .x-btn-facebook-small-tl, +.x-btn-over .x-btn-facebook-small-bl, +.x-btn-over .x-btn-facebook-small-tr, +.x-btn-over .x-btn-facebook-small-br, +.x-btn-over .x-btn-facebook-small-tc, +.x-btn-over .x-btn-facebook-small-bc { + background-image: url(images/btn/btn-facebook-small-over-corners.gif); +} +.x-btn-over .x-btn-facebook-small-ml, +.x-btn-over .x-btn-facebook-small-mr { + background-image: url(images/btn/btn-facebook-small-over-sides.gif); +} +.x-btn-over .x-btn-facebook-small-mc { + background-color: #1470ad; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-small-bc { + background-image: url(images/btn/btn-facebook-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-small-mr { + background-image: url(images/btn/btn-facebook-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-small-mc { + background-color: #1470ad; +} +.x-btn.x-btn-menu-active .x-btn-facebook-small-tl, +.x-btn.x-btn-menu-active .x-btn-facebook-small-bl, +.x-btn.x-btn-menu-active .x-btn-facebook-small-tr, +.x-btn.x-btn-menu-active .x-btn-facebook-small-br, +.x-btn.x-btn-menu-active .x-btn-facebook-small-tc, +.x-btn.x-btn-menu-active .x-btn-facebook-small-bc, +.x-btn.x-btn-pressed .x-btn-facebook-small-tl, +.x-btn.x-btn-pressed .x-btn-facebook-small-bl, +.x-btn.x-btn-pressed .x-btn-facebook-small-tr, +.x-btn.x-btn-pressed .x-btn-facebook-small-br, +.x-btn.x-btn-pressed .x-btn-facebook-small-tc, +.x-btn.x-btn-pressed .x-btn-facebook-small-bc { + background-image: url(images/btn/btn-facebook-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-facebook-small-ml, +.x-btn.x-btn-menu-active .x-btn-facebook-small-mr, +.x-btn.x-btn-pressed .x-btn-facebook-small-ml, +.x-btn.x-btn-pressed .x-btn-facebook-small-mr { + background-image: url(images/btn/btn-facebook-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-facebook-small-mc, +.x-btn.x-btn-pressed .x-btn-facebook-small-mc { + background-color: #115c8d; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-small-bc { + background-image: url(images/btn/btn-facebook-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-small-mr { + background-image: url(images/btn/btn-facebook-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-small-mc { + background-color: #115c8d; +} +.x-btn.x-btn-disabled .x-btn-facebook-small-tl, +.x-btn.x-btn-disabled .x-btn-facebook-small-bl, +.x-btn.x-btn-disabled .x-btn-facebook-small-tr, +.x-btn.x-btn-disabled .x-btn-facebook-small-br, +.x-btn.x-btn-disabled .x-btn-facebook-small-tc, +.x-btn.x-btn-disabled .x-btn-facebook-small-bc { + background-image: url(images/btn/btn-facebook-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-facebook-small-ml, +.x-btn.x-btn-disabled .x-btn-facebook-small-mr { + background-image: url(images/btn/btn-facebook-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-facebook-small-mc { + background-color: #167abc; +} +.x-nbr .x-btn-facebook-small { + background-image: none; +} +.x-btn-disabled.x-btn-facebook-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-small.x-segmented-button-first + .x-btn-facebook-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-small.x-segmented-button-middle + .x-btn-facebook-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-small.x-segmented-button-last + .x-btn-facebook-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-small.x-segmented-button-first + .x-btn-facebook-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-small.x-segmented-button-middle + .x-btn-facebook-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-small.x-segmented-button-last + .x-btn-facebook-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-facebook-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-facebook-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-facebook-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-facebook-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-facebook-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-facebook-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-facebook-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-facebook-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #167abc; +} +.x-btn-facebook-large-mc { + background-color: #167abc; +} +.x-nbr .x-btn-facebook-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-facebook-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +.x-btn-facebook-large-tl { + background-position: 0 -2px; +} +.x-btn-facebook-large-tr { + background-position: right -3px; +} +.x-btn-facebook-large-bl { + background-position: 0 -4px; +} +.x-btn-facebook-large-br { + background-position: right -5px; +} +.x-btn-facebook-large-ml { + background-position: 0 top; +} +.x-btn-facebook-large-mr { + background-position: right top; +} +.x-btn-facebook-large-tc { + background-position: 0 0; +} +.x-btn-facebook-large-bc { + background-position: 0 -1px; +} +.x-btn-facebook-large-tr, +.x-btn-facebook-large-br, +.x-btn-facebook-large-mr { + padding-right: 1px; +} +.x-btn-facebook-large-tl, +.x-btn-facebook-large-bl, +.x-btn-facebook-large-ml { + padding-left: 1px; +} +.x-btn-facebook-large-tc { + height: 1px; +} +.x-btn-facebook-large-bc { + height: 1px; +} +.x-btn-facebook-large-tl, +.x-btn-facebook-large-bl, +.x-btn-facebook-large-tr, +.x-btn-facebook-large-br, +.x-btn-facebook-large-tc, +.x-btn-facebook-large-bc, +.x-btn-facebook-large-ml, +.x-btn-facebook-large-mr { + background-image: url(images/btn/btn-facebook-large-corners.gif); +} +.x-btn-facebook-large-ml, +.x-btn-facebook-large-mr { + background-image: url(images/btn/btn-facebook-large-sides.gif); + background-repeat: repeat-y; +} +.x-btn-facebook-large-mc { + padding: 9px 9px 9px 9px; +} +.x-btn-facebook-large { + border-color: #136ba5; +} +.x-btn-button-facebook-large { + min-height: 34px; +} +.x-ie9m .x-btn-button-facebook-large { + min-height: auto; + height: 34px; +} +.x-btn-inner-facebook-large { + font: 500 16px/34px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 10px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-facebook-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-facebook-large { + max-width: calc(100% - 24px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-facebook-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-facebook-large { + max-width: calc(100% - 23px); +} +.x-ie10p .x-btn-inner-facebook-large { + max-width: none; +} +.x-btn-icon-el-facebook-large { + font-size: 24px; + height: 24px; + color: #f0f0f0; + line-height: 24px; +} +.x-btn-icon-left > .x-btn-icon-el-facebook-large, +.x-btn-icon-right > .x-btn-icon-el-facebook-large { + width: 24px; +} +.x-btn-icon-top > .x-btn-icon-el-facebook-large, +.x-btn-icon-bottom > .x-btn-icon-el-facebook-large { + min-width: 24px; +} +.x-ie8 .x-btn-icon-el-facebook-large.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-facebook-large { + margin-right: 0; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-facebook-large { + margin-left: 0; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-facebook-large { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-facebook-large { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-facebook-large { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-facebook-large { + margin-right: 10px; +} +.x-btn-arrow-bottom > .x-btn-button-facebook-large, +.x-btn-split-bottom > .x-btn-button-facebook-large { + padding-bottom: 9px; +} +.x-btn-wrap-facebook-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-facebook-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-facebook-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +.x-btn-wrap-facebook-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-facebook-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; + padding-left: 9px; +} +.x-btn-wrap-facebook-large.x-btn-split-bottom { + margin-bottom: -9px; +} +.x-btn-wrap-facebook-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-facebook-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-facebook-large { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-facebook-large { + margin-right: 10px; +} +.x-keyboard-mode .x-btn-focus.x-btn-facebook-large { + background-image: none; + background-color: #167abc; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-facebook-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-facebook-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-facebook-large { + border-color: #126398; + background-image: none; + background-color: #1470ad; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-facebook-large { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-facebook-large, +.x-btn.x-btn-pressed.x-btn-facebook-large { + border-color: #0e507c; + background-image: none; + background-color: #115c8d; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-facebook-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-facebook-large { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-facebook-large { + background-image: none; + background-color: #167abc; +} +.x-keyboard-mode .x-btn-focus .x-btn-facebook-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-large-bc { + background-image: url(images/btn/btn-facebook-large-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-facebook-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-facebook-large-mr { + background-image: url(images/btn/btn-facebook-large-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-facebook-large-mc { + background-color: #167abc; +} +.x-btn-over .x-btn-facebook-large-tl, +.x-btn-over .x-btn-facebook-large-bl, +.x-btn-over .x-btn-facebook-large-tr, +.x-btn-over .x-btn-facebook-large-br, +.x-btn-over .x-btn-facebook-large-tc, +.x-btn-over .x-btn-facebook-large-bc { + background-image: url(images/btn/btn-facebook-large-over-corners.gif); +} +.x-btn-over .x-btn-facebook-large-ml, +.x-btn-over .x-btn-facebook-large-mr { + background-image: url(images/btn/btn-facebook-large-over-sides.gif); +} +.x-btn-over .x-btn-facebook-large-mc { + background-color: #1470ad; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-large-bc { + background-image: url(images/btn/btn-facebook-large-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-large-mr { + background-image: url(images/btn/btn-facebook-large-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-facebook-large-mc { + background-color: #1470ad; +} +.x-btn.x-btn-menu-active .x-btn-facebook-large-tl, +.x-btn.x-btn-menu-active .x-btn-facebook-large-bl, +.x-btn.x-btn-menu-active .x-btn-facebook-large-tr, +.x-btn.x-btn-menu-active .x-btn-facebook-large-br, +.x-btn.x-btn-menu-active .x-btn-facebook-large-tc, +.x-btn.x-btn-menu-active .x-btn-facebook-large-bc, +.x-btn.x-btn-pressed .x-btn-facebook-large-tl, +.x-btn.x-btn-pressed .x-btn-facebook-large-bl, +.x-btn.x-btn-pressed .x-btn-facebook-large-tr, +.x-btn.x-btn-pressed .x-btn-facebook-large-br, +.x-btn.x-btn-pressed .x-btn-facebook-large-tc, +.x-btn.x-btn-pressed .x-btn-facebook-large-bc { + background-image: url(images/btn/btn-facebook-large-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-facebook-large-ml, +.x-btn.x-btn-menu-active .x-btn-facebook-large-mr, +.x-btn.x-btn-pressed .x-btn-facebook-large-ml, +.x-btn.x-btn-pressed .x-btn-facebook-large-mr { + background-image: url(images/btn/btn-facebook-large-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-facebook-large-mc, +.x-btn.x-btn-pressed .x-btn-facebook-large-mc { + background-color: #115c8d; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-large-bc { + background-image: url(images/btn/btn-facebook-large-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-large-mr { + background-image: url(images/btn/btn-facebook-large-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-facebook-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-facebook-large-mc { + background-color: #115c8d; +} +.x-btn.x-btn-disabled .x-btn-facebook-large-tl, +.x-btn.x-btn-disabled .x-btn-facebook-large-bl, +.x-btn.x-btn-disabled .x-btn-facebook-large-tr, +.x-btn.x-btn-disabled .x-btn-facebook-large-br, +.x-btn.x-btn-disabled .x-btn-facebook-large-tc, +.x-btn.x-btn-disabled .x-btn-facebook-large-bc { + background-image: url(images/btn/btn-facebook-large-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-facebook-large-ml, +.x-btn.x-btn-disabled .x-btn-facebook-large-mr { + background-image: url(images/btn/btn-facebook-large-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-facebook-large-mc { + background-color: #167abc; +} +.x-nbr .x-btn-facebook-large { + background-image: none; +} +.x-btn-disabled.x-btn-facebook-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-large.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-large.x-segmented-button-first + .x-btn-facebook-large-mc { + padding-right: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-large.x-segmented-button-middle + .x-btn-facebook-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-large.x-segmented-button-last + .x-btn-facebook-large-mc { + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-large.x-segmented-button-first + .x-btn-facebook-large-mc { + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-large.x-segmented-button-middle + .x-btn-facebook-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-large.x-segmented-button-last + .x-btn-facebook-large-mc { + padding-top: 9px !important; +} +.x-nbr .x-segmented-button-item.x-btn-facebook-large:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-facebook-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-large.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-facebook-large.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-facebook-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-large.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-facebook-large.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-facebook-large:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-facebook-large:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-facebook-large:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-facebook-large:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-soft-cyan-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #03b4d5; +} +.x-btn-soft-cyan-small-mc { + background-color: #03b4d5; +} +.x-nbr .x-btn-soft-cyan-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-cyan-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-cyan-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-cyan-small-tr { + background-position: right -3px; +} +.x-btn-soft-cyan-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-cyan-small-br { + background-position: right -5px; +} +.x-btn-soft-cyan-small-ml { + background-position: 0 top; +} +.x-btn-soft-cyan-small-mr { + background-position: right top; +} +.x-btn-soft-cyan-small-tc { + background-position: 0 0; +} +.x-btn-soft-cyan-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-cyan-small-tr, +.x-btn-soft-cyan-small-br, +.x-btn-soft-cyan-small-mr { + padding-right: 1px; +} +.x-btn-soft-cyan-small-tl, +.x-btn-soft-cyan-small-bl, +.x-btn-soft-cyan-small-ml { + padding-left: 1px; +} +.x-btn-soft-cyan-small-tc { + height: 1px; +} +.x-btn-soft-cyan-small-bc { + height: 1px; +} +.x-btn-soft-cyan-small-tl, +.x-btn-soft-cyan-small-bl, +.x-btn-soft-cyan-small-tr, +.x-btn-soft-cyan-small-br, +.x-btn-soft-cyan-small-tc, +.x-btn-soft-cyan-small-bc, +.x-btn-soft-cyan-small-ml, +.x-btn-soft-cyan-small-mr { + background-image: url(images/btn/btn-soft-cyan-small-corners.gif); +} +.x-btn-soft-cyan-small-ml, +.x-btn-soft-cyan-small-mr { + background-image: url(images/btn/btn-soft-cyan-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-cyan-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-cyan-small { + border-color: #039fbc; +} +.x-btn-button-soft-cyan-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-cyan-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-cyan-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-cyan-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-cyan-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-cyan-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-cyan-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-cyan-small { + max-width: none; +} +.x-btn-icon-el-soft-cyan-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-cyan-small, +.x-btn-icon-right > .x-btn-icon-el-soft-cyan-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-cyan-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-cyan-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-cyan-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-cyan-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-cyan-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-cyan-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-cyan-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-cyan-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-cyan-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-cyan-small, +.x-btn-split-bottom > .x-btn-button-soft-cyan-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-cyan-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-cyan-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-cyan-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-cyan-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-cyan-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-soft-cyan-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-cyan-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-cyan-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-cyan-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-cyan-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-cyan-small { + background-image: none; + background-color: #03b4d5; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-soft-cyan-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-cyan-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-soft-cyan-small { + border-color: #0292ad; + background-image: none; + background-color: #03a6c4; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-cyan-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-cyan-small, +.x-btn.x-btn-pressed.x-btn-soft-cyan-small { + border-color: #02778d; + background-image: none; + background-color: #0287a0; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-cyan-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-cyan-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-cyan-small { + background-image: none; + background-color: #03b4d5; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-small-bc { + background-image: url(images/btn/btn-soft-cyan-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-small-mr { + background-image: url(images/btn/btn-soft-cyan-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-small-mc { + background-color: #03b4d5; +} +.x-btn-over .x-btn-soft-cyan-small-tl, +.x-btn-over .x-btn-soft-cyan-small-bl, +.x-btn-over .x-btn-soft-cyan-small-tr, +.x-btn-over .x-btn-soft-cyan-small-br, +.x-btn-over .x-btn-soft-cyan-small-tc, +.x-btn-over .x-btn-soft-cyan-small-bc { + background-image: url(images/btn/btn-soft-cyan-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-cyan-small-ml, +.x-btn-over .x-btn-soft-cyan-small-mr { + background-image: url(images/btn/btn-soft-cyan-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-cyan-small-mc { + background-color: #03a6c4; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-small-bc { + background-image: url(images/btn/btn-soft-cyan-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-small-mr { + background-image: url(images/btn/btn-soft-cyan-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-small-mc { + background-color: #03a6c4; +} +.x-btn.x-btn-menu-active .x-btn-soft-cyan-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-cyan-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-cyan-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-cyan-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-cyan-small-br, +.x-btn.x-btn-pressed .x-btn-soft-cyan-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-cyan-small-bc { + background-image: url(images/btn/btn-soft-cyan-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-cyan-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-cyan-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-cyan-small-mr { + background-image: url(images/btn/btn-soft-cyan-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-cyan-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-cyan-small-mc { + background-color: #0287a0; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-cyan-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-cyan-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-cyan-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-cyan-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-cyan-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-cyan-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-small-bc { + background-image: url(images/btn/btn-soft-cyan-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-cyan-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-cyan-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-small-mr { + background-image: url(images/btn/btn-soft-cyan-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-cyan-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-small-mc { + background-color: #0287a0; +} +.x-btn.x-btn-disabled .x-btn-soft-cyan-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-cyan-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-cyan-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-cyan-small-br, +.x-btn.x-btn-disabled .x-btn-soft-cyan-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-cyan-small-bc { + background-image: url(images/btn/btn-soft-cyan-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-cyan-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-cyan-small-mr { + background-image: url(images/btn/btn-soft-cyan-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-cyan-small-mc { + background-color: #03b4d5; +} +.x-nbr .x-btn-soft-cyan-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-cyan-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-small.x-segmented-button-first + .x-btn-soft-cyan-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-small.x-segmented-button-middle + .x-btn-soft-cyan-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-small.x-segmented-button-last + .x-btn-soft-cyan-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-small.x-segmented-button-first + .x-btn-soft-cyan-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-small.x-segmented-button-middle + .x-btn-soft-cyan-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-small.x-segmented-button-last + .x-btn-soft-cyan-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-cyan-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-cyan-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-cyan-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-cyan-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-cyan-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-cyan-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-cyan-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-soft-cyan-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #03b4d5; +} +.x-btn-soft-cyan-toolbar-small-mc { + background-color: #03b4d5; +} +.x-nbr .x-btn-soft-cyan-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-cyan-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-cyan-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-cyan-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-soft-cyan-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-cyan-toolbar-small-br { + background-position: right -5px; +} +.x-btn-soft-cyan-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-soft-cyan-toolbar-small-mr { + background-position: right top; +} +.x-btn-soft-cyan-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-soft-cyan-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-cyan-toolbar-small-tr, +.x-btn-soft-cyan-toolbar-small-br, +.x-btn-soft-cyan-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-soft-cyan-toolbar-small-tl, +.x-btn-soft-cyan-toolbar-small-bl, +.x-btn-soft-cyan-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-soft-cyan-toolbar-small-tc { + height: 1px; +} +.x-btn-soft-cyan-toolbar-small-bc { + height: 1px; +} +.x-btn-soft-cyan-toolbar-small-tl, +.x-btn-soft-cyan-toolbar-small-bl, +.x-btn-soft-cyan-toolbar-small-tr, +.x-btn-soft-cyan-toolbar-small-br, +.x-btn-soft-cyan-toolbar-small-tc, +.x-btn-soft-cyan-toolbar-small-bc, +.x-btn-soft-cyan-toolbar-small-ml, +.x-btn-soft-cyan-toolbar-small-mr { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-corners.gif); +} +.x-btn-soft-cyan-toolbar-small-ml, +.x-btn-soft-cyan-toolbar-small-mr { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-cyan-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-cyan-toolbar-small { + border-color: #039fbc; +} +.x-btn-button-soft-cyan-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-cyan-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-cyan-toolbar-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-cyan-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-cyan-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-cyan-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-cyan-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-cyan-toolbar-small { + max-width: none; +} +.x-btn-icon-el-soft-cyan-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-cyan-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-soft-cyan-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-cyan-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-cyan-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-cyan-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-cyan-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-cyan-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-cyan-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-cyan-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-cyan-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-cyan-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-cyan-toolbar-small, +.x-btn-split-bottom > .x-btn-button-soft-cyan-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-cyan-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-cyan-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-cyan-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-cyan-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-cyan-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-soft-cyan-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-cyan-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-cyan-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-cyan-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-cyan-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-cyan-toolbar-small { + background-image: none; + background-color: #03b4d5; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-soft-cyan-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-cyan-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-soft-cyan-toolbar-small { + border-color: #0398b4; + background-image: none; + background-color: #03adcc; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-cyan-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-cyan-toolbar-small, +.x-btn.x-btn-pressed.x-btn-soft-cyan-toolbar-small { + border-color: #0292ad; + background-image: none; + background-color: #03a6c4; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-cyan-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-cyan-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-cyan-toolbar-small { + background-image: none; + background-color: #03b4d5; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-toolbar-small-bc { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-toolbar-small-mr { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-cyan-toolbar-small-mc { + background-color: #03b4d5; +} +.x-btn-over .x-btn-soft-cyan-toolbar-small-tl, +.x-btn-over .x-btn-soft-cyan-toolbar-small-bl, +.x-btn-over .x-btn-soft-cyan-toolbar-small-tr, +.x-btn-over .x-btn-soft-cyan-toolbar-small-br, +.x-btn-over .x-btn-soft-cyan-toolbar-small-tc, +.x-btn-over .x-btn-soft-cyan-toolbar-small-bc { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-cyan-toolbar-small-ml, +.x-btn-over .x-btn-soft-cyan-toolbar-small-mr { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-cyan-toolbar-small-mc { + background-color: #03adcc; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-toolbar-small-bc { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-toolbar-small-mr { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-cyan-toolbar-small-mc { + background-color: #03adcc; +} +.x-btn.x-btn-menu-active .x-btn-soft-cyan-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-cyan-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-cyan-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-cyan-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-cyan-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-soft-cyan-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-cyan-toolbar-small-bc { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-cyan-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-cyan-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-cyan-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-cyan-toolbar-small-mr { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-cyan-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-cyan-toolbar-small-mc { + background-color: #03a6c4; +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-cyan-toolbar-small-tl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-cyan-toolbar-small-bl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-cyan-toolbar-small-tr, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-cyan-toolbar-small-br, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-cyan-toolbar-small-tc, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-cyan-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-toolbar-small-bc { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-cyan-toolbar-small-ml, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-cyan-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-toolbar-small-mr { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-cyan-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-cyan-toolbar-small-mc { + background-color: #03a6c4; +} +.x-btn.x-btn-disabled .x-btn-soft-cyan-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-cyan-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-cyan-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-cyan-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-soft-cyan-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-cyan-toolbar-small-bc { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-cyan-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-cyan-toolbar-small-mr { + background-image: url(images/btn/btn-soft-cyan-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-cyan-toolbar-small-mc { + background-color: #03b4d5; +} +.x-nbr .x-btn-soft-cyan-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-cyan-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-toolbar-small.x-segmented-button-first + .x-btn-soft-cyan-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-toolbar-small.x-segmented-button-middle + .x-btn-soft-cyan-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-toolbar-small.x-segmented-button-last + .x-btn-soft-cyan-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-toolbar-small.x-segmented-button-first + .x-btn-soft-cyan-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-toolbar-small.x-segmented-button-middle + .x-btn-soft-cyan-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-toolbar-small.x-segmented-button-last + .x-btn-soft-cyan-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-cyan-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-cyan-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-cyan-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-cyan-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-cyan-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-cyan-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-cyan-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-cyan-toolbar-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-cyan-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-soft-green-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #9cc96b; +} +.x-btn-soft-green-small-mc { + background-color: #9cc96b; +} +.x-nbr .x-btn-soft-green-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-green-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-green-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-green-small-tr { + background-position: right -3px; +} +.x-btn-soft-green-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-green-small-br { + background-position: right -5px; +} +.x-btn-soft-green-small-ml { + background-position: 0 top; +} +.x-btn-soft-green-small-mr { + background-position: right top; +} +.x-btn-soft-green-small-tc { + background-position: 0 0; +} +.x-btn-soft-green-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-green-small-tr, +.x-btn-soft-green-small-br, +.x-btn-soft-green-small-mr { + padding-right: 1px; +} +.x-btn-soft-green-small-tl, +.x-btn-soft-green-small-bl, +.x-btn-soft-green-small-ml { + padding-left: 1px; +} +.x-btn-soft-green-small-tc { + height: 1px; +} +.x-btn-soft-green-small-bc { + height: 1px; +} +.x-btn-soft-green-small-tl, +.x-btn-soft-green-small-bl, +.x-btn-soft-green-small-tr, +.x-btn-soft-green-small-br, +.x-btn-soft-green-small-tc, +.x-btn-soft-green-small-bc, +.x-btn-soft-green-small-ml, +.x-btn-soft-green-small-mr { + background-image: url(images/btn/btn-soft-green-small-corners.gif); +} +.x-btn-soft-green-small-ml, +.x-btn-soft-green-small-mr { + background-image: url(images/btn/btn-soft-green-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-green-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-green-small { + border-color: #90c258; +} +.x-btn-button-soft-green-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-green-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-green-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-green-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-green-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-green-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-green-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-green-small { + max-width: none; +} +.x-btn-icon-el-soft-green-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-green-small, +.x-btn-icon-right > .x-btn-icon-el-soft-green-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-green-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-green-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-green-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-green-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-green-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-green-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-green-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-green-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-green-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-green-small, +.x-btn-split-bottom > .x-btn-button-soft-green-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-green-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-green-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-green-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-green-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-green-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-soft-green-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-green-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-green-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-green-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-green-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-green-small { + background-image: none; + background-color: #9cc96b; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-soft-green-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-green-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-soft-green-small { + border-color: #84b351; + background-image: none; + background-color: #90b962; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-green-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-green-small, +.x-btn.x-btn-pressed.x-btn-soft-green-small { + border-color: #6c9242; + background-image: none; + background-color: #759750; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-green-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-green-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-green-small { + background-image: none; + background-color: #9cc96b; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-small-bc { + background-image: url(images/btn/btn-soft-green-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-small-mr { + background-image: url(images/btn/btn-soft-green-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-small-mc { + background-color: #9cc96b; +} +.x-btn-over .x-btn-soft-green-small-tl, +.x-btn-over .x-btn-soft-green-small-bl, +.x-btn-over .x-btn-soft-green-small-tr, +.x-btn-over .x-btn-soft-green-small-br, +.x-btn-over .x-btn-soft-green-small-tc, +.x-btn-over .x-btn-soft-green-small-bc { + background-image: url(images/btn/btn-soft-green-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-green-small-ml, +.x-btn-over .x-btn-soft-green-small-mr { + background-image: url(images/btn/btn-soft-green-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-green-small-mc { + background-color: #90b962; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-small-bc { + background-image: url(images/btn/btn-soft-green-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-small-mr { + background-image: url(images/btn/btn-soft-green-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-small-mc { + background-color: #90b962; +} +.x-btn.x-btn-menu-active .x-btn-soft-green-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-green-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-green-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-green-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-green-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-green-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-green-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-green-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-green-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-green-small-br, +.x-btn.x-btn-pressed .x-btn-soft-green-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-green-small-bc { + background-image: url(images/btn/btn-soft-green-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-green-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-green-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-green-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-green-small-mr { + background-image: url(images/btn/btn-soft-green-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-green-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-green-small-mc { + background-color: #759750; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-small-bc { + background-image: url(images/btn/btn-soft-green-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-small-mr { + background-image: url(images/btn/btn-soft-green-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-small-mc { + background-color: #759750; +} +.x-btn.x-btn-disabled .x-btn-soft-green-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-green-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-green-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-green-small-br, +.x-btn.x-btn-disabled .x-btn-soft-green-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-green-small-bc { + background-image: url(images/btn/btn-soft-green-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-green-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-green-small-mr { + background-image: url(images/btn/btn-soft-green-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-green-small-mc { + background-color: #9cc96b; +} +.x-nbr .x-btn-soft-green-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-green-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-small.x-segmented-button-first + .x-btn-soft-green-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-small.x-segmented-button-middle + .x-btn-soft-green-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-small.x-segmented-button-last + .x-btn-soft-green-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-small.x-segmented-button-first + .x-btn-soft-green-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-small.x-segmented-button-middle + .x-btn-soft-green-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-small.x-segmented-button-last + .x-btn-soft-green-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-green-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-green-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-green-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-green-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-green-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-green-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-green-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-soft-green-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #9cc96b; +} +.x-btn-soft-green-large-mc { + background-color: #9cc96b; +} +.x-nbr .x-btn-soft-green-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-green-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +.x-btn-soft-green-large-tl { + background-position: 0 -2px; +} +.x-btn-soft-green-large-tr { + background-position: right -3px; +} +.x-btn-soft-green-large-bl { + background-position: 0 -4px; +} +.x-btn-soft-green-large-br { + background-position: right -5px; +} +.x-btn-soft-green-large-ml { + background-position: 0 top; +} +.x-btn-soft-green-large-mr { + background-position: right top; +} +.x-btn-soft-green-large-tc { + background-position: 0 0; +} +.x-btn-soft-green-large-bc { + background-position: 0 -1px; +} +.x-btn-soft-green-large-tr, +.x-btn-soft-green-large-br, +.x-btn-soft-green-large-mr { + padding-right: 1px; +} +.x-btn-soft-green-large-tl, +.x-btn-soft-green-large-bl, +.x-btn-soft-green-large-ml { + padding-left: 1px; +} +.x-btn-soft-green-large-tc { + height: 1px; +} +.x-btn-soft-green-large-bc { + height: 1px; +} +.x-btn-soft-green-large-tl, +.x-btn-soft-green-large-bl, +.x-btn-soft-green-large-tr, +.x-btn-soft-green-large-br, +.x-btn-soft-green-large-tc, +.x-btn-soft-green-large-bc, +.x-btn-soft-green-large-ml, +.x-btn-soft-green-large-mr { + background-image: url(images/btn/btn-soft-green-large-corners.gif); +} +.x-btn-soft-green-large-ml, +.x-btn-soft-green-large-mr { + background-image: url(images/btn/btn-soft-green-large-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-green-large-mc { + padding: 9px 9px 9px 9px; +} +.x-btn-soft-green-large { + border-color: #90c258; +} +.x-btn-button-soft-green-large { + min-height: 34px; +} +.x-ie9m .x-btn-button-soft-green-large { + min-height: auto; + height: 34px; +} +.x-btn-inner-soft-green-large { + font: 500 16px/34px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 10px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-green-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-green-large { + max-width: calc(100% - 24px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-green-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-green-large { + max-width: calc(100% - 23px); +} +.x-ie10p .x-btn-inner-soft-green-large { + max-width: none; +} +.x-btn-icon-el-soft-green-large { + font-size: 24px; + height: 24px; + color: #f0f0f0; + line-height: 24px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-green-large, +.x-btn-icon-right > .x-btn-icon-el-soft-green-large { + width: 24px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-green-large, +.x-btn-icon-bottom > .x-btn-icon-el-soft-green-large { + min-width: 24px; +} +.x-ie8 .x-btn-icon-el-soft-green-large.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-green-large { + margin-right: 0; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-green-large { + margin-left: 0; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-green-large { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-green-large { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-green-large { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-green-large { + margin-right: 10px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-green-large, +.x-btn-split-bottom > .x-btn-button-soft-green-large { + padding-bottom: 9px; +} +.x-btn-wrap-soft-green-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-green-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-green-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +.x-btn-wrap-soft-green-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-green-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; + padding-left: 9px; +} +.x-btn-wrap-soft-green-large.x-btn-split-bottom { + margin-bottom: -9px; +} +.x-btn-wrap-soft-green-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-green-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-green-large { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-green-large { + margin-right: 10px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-green-large { + background-image: none; + background-color: #9cc96b; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-soft-green-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-green-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-soft-green-large { + border-color: #84b351; + background-image: none; + background-color: #90b962; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-green-large { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-green-large, +.x-btn.x-btn-pressed.x-btn-soft-green-large { + border-color: #6c9242; + background-image: none; + background-color: #759750; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-green-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-green-large { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-green-large { + background-image: none; + background-color: #9cc96b; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-large-bc { + background-image: url(images/btn/btn-soft-green-large-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-large-mr { + background-image: url(images/btn/btn-soft-green-large-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-large-mc { + background-color: #9cc96b; +} +.x-btn-over .x-btn-soft-green-large-tl, +.x-btn-over .x-btn-soft-green-large-bl, +.x-btn-over .x-btn-soft-green-large-tr, +.x-btn-over .x-btn-soft-green-large-br, +.x-btn-over .x-btn-soft-green-large-tc, +.x-btn-over .x-btn-soft-green-large-bc { + background-image: url(images/btn/btn-soft-green-large-over-corners.gif); +} +.x-btn-over .x-btn-soft-green-large-ml, +.x-btn-over .x-btn-soft-green-large-mr { + background-image: url(images/btn/btn-soft-green-large-over-sides.gif); +} +.x-btn-over .x-btn-soft-green-large-mc { + background-color: #90b962; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-large-bc { + background-image: url(images/btn/btn-soft-green-large-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-large-mr { + background-image: url(images/btn/btn-soft-green-large-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-large-mc { + background-color: #90b962; +} +.x-btn.x-btn-menu-active .x-btn-soft-green-large-tl, +.x-btn.x-btn-menu-active .x-btn-soft-green-large-bl, +.x-btn.x-btn-menu-active .x-btn-soft-green-large-tr, +.x-btn.x-btn-menu-active .x-btn-soft-green-large-br, +.x-btn.x-btn-menu-active .x-btn-soft-green-large-tc, +.x-btn.x-btn-menu-active .x-btn-soft-green-large-bc, +.x-btn.x-btn-pressed .x-btn-soft-green-large-tl, +.x-btn.x-btn-pressed .x-btn-soft-green-large-bl, +.x-btn.x-btn-pressed .x-btn-soft-green-large-tr, +.x-btn.x-btn-pressed .x-btn-soft-green-large-br, +.x-btn.x-btn-pressed .x-btn-soft-green-large-tc, +.x-btn.x-btn-pressed .x-btn-soft-green-large-bc { + background-image: url(images/btn/btn-soft-green-large-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-green-large-ml, +.x-btn.x-btn-menu-active .x-btn-soft-green-large-mr, +.x-btn.x-btn-pressed .x-btn-soft-green-large-ml, +.x-btn.x-btn-pressed .x-btn-soft-green-large-mr { + background-image: url(images/btn/btn-soft-green-large-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-green-large-mc, +.x-btn.x-btn-pressed .x-btn-soft-green-large-mc { + background-color: #759750; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-large-bc { + background-image: url(images/btn/btn-soft-green-large-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-large-mr { + background-image: url(images/btn/btn-soft-green-large-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-green-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-large-mc { + background-color: #759750; +} +.x-btn.x-btn-disabled .x-btn-soft-green-large-tl, +.x-btn.x-btn-disabled .x-btn-soft-green-large-bl, +.x-btn.x-btn-disabled .x-btn-soft-green-large-tr, +.x-btn.x-btn-disabled .x-btn-soft-green-large-br, +.x-btn.x-btn-disabled .x-btn-soft-green-large-tc, +.x-btn.x-btn-disabled .x-btn-soft-green-large-bc { + background-image: url(images/btn/btn-soft-green-large-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-green-large-ml, +.x-btn.x-btn-disabled .x-btn-soft-green-large-mr { + background-image: url(images/btn/btn-soft-green-large-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-green-large-mc { + background-color: #9cc96b; +} +.x-nbr .x-btn-soft-green-large { + background-image: none; +} +.x-btn-disabled.x-btn-soft-green-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-large.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-large.x-segmented-button-first + .x-btn-soft-green-large-mc { + padding-right: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-large.x-segmented-button-middle + .x-btn-soft-green-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-large.x-segmented-button-last + .x-btn-soft-green-large-mc { + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-large.x-segmented-button-first + .x-btn-soft-green-large-mc { + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-large.x-segmented-button-middle + .x-btn-soft-green-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-large.x-segmented-button-last + .x-btn-soft-green-large-mc { + padding-top: 9px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-green-large:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-green-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-large.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-large.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-green-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-large.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-large.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-green-large:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-green-large:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-green-large:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-green-large:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-soft-green-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #9cc96b; +} +.x-btn-soft-green-toolbar-small-mc { + background-color: #9cc96b; +} +.x-nbr .x-btn-soft-green-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-green-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-green-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-green-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-soft-green-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-green-toolbar-small-br { + background-position: right -5px; +} +.x-btn-soft-green-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-soft-green-toolbar-small-mr { + background-position: right top; +} +.x-btn-soft-green-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-soft-green-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-green-toolbar-small-tr, +.x-btn-soft-green-toolbar-small-br, +.x-btn-soft-green-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-soft-green-toolbar-small-tl, +.x-btn-soft-green-toolbar-small-bl, +.x-btn-soft-green-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-soft-green-toolbar-small-tc { + height: 1px; +} +.x-btn-soft-green-toolbar-small-bc { + height: 1px; +} +.x-btn-soft-green-toolbar-small-tl, +.x-btn-soft-green-toolbar-small-bl, +.x-btn-soft-green-toolbar-small-tr, +.x-btn-soft-green-toolbar-small-br, +.x-btn-soft-green-toolbar-small-tc, +.x-btn-soft-green-toolbar-small-bc, +.x-btn-soft-green-toolbar-small-ml, +.x-btn-soft-green-toolbar-small-mr { + background-image: url(images/btn/btn-soft-green-toolbar-small-corners.gif); +} +.x-btn-soft-green-toolbar-small-ml, +.x-btn-soft-green-toolbar-small-mr { + background-image: url(images/btn/btn-soft-green-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-green-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-green-toolbar-small { + border-color: #90c258; +} +.x-btn-button-soft-green-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-green-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-green-toolbar-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-green-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-green-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-green-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-green-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-green-toolbar-small { + max-width: none; +} +.x-btn-icon-el-soft-green-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-green-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-soft-green-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-green-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-green-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-green-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-green-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-green-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-green-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-green-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-green-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-green-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-green-toolbar-small, +.x-btn-split-bottom > .x-btn-button-soft-green-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-green-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-green-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-green-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-green-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-green-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-soft-green-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-green-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-green-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-green-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-green-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-green-toolbar-small { + background-image: none; + background-color: #9cc96b; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-soft-green-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-green-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-soft-green-toolbar-small { + border-color: #8aba55; + background-image: none; + background-color: #96c167; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-green-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-green-toolbar-small, +.x-btn.x-btn-pressed.x-btn-soft-green-toolbar-small { + border-color: #84b351; + background-image: none; + background-color: #90b962; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-green-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-green-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-green-toolbar-small { + background-image: none; + background-color: #9cc96b; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-toolbar-small-bc { + background-image: url(images/btn/btn-soft-green-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-toolbar-small-mr { + background-image: url(images/btn/btn-soft-green-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-green-toolbar-small-mc { + background-color: #9cc96b; +} +.x-btn-over .x-btn-soft-green-toolbar-small-tl, +.x-btn-over .x-btn-soft-green-toolbar-small-bl, +.x-btn-over .x-btn-soft-green-toolbar-small-tr, +.x-btn-over .x-btn-soft-green-toolbar-small-br, +.x-btn-over .x-btn-soft-green-toolbar-small-tc, +.x-btn-over .x-btn-soft-green-toolbar-small-bc { + background-image: url(images/btn/btn-soft-green-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-green-toolbar-small-ml, +.x-btn-over .x-btn-soft-green-toolbar-small-mr { + background-image: url(images/btn/btn-soft-green-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-green-toolbar-small-mc { + background-color: #96c167; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-toolbar-small-bc { + background-image: url(images/btn/btn-soft-green-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-toolbar-small-mr { + background-image: url(images/btn/btn-soft-green-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-green-toolbar-small-mc { + background-color: #96c167; +} +.x-btn.x-btn-menu-active .x-btn-soft-green-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-green-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-green-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-green-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-green-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-green-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-green-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-green-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-green-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-green-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-soft-green-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-green-toolbar-small-bc { + background-image: url(images/btn/btn-soft-green-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-green-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-green-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-green-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-green-toolbar-small-mr { + background-image: url(images/btn/btn-soft-green-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-green-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-green-toolbar-small-mc { + background-color: #90b962; +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-green-toolbar-small-tl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-green-toolbar-small-bl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-green-toolbar-small-tr, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-green-toolbar-small-br, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-green-toolbar-small-tc, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-green-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-toolbar-small-bc { + background-image: url(images/btn/btn-soft-green-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-green-toolbar-small-ml, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-green-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-toolbar-small-mr { + background-image: url(images/btn/btn-soft-green-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-green-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-green-toolbar-small-mc { + background-color: #90b962; +} +.x-btn.x-btn-disabled .x-btn-soft-green-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-green-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-green-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-green-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-soft-green-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-green-toolbar-small-bc { + background-image: url(images/btn/btn-soft-green-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-green-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-green-toolbar-small-mr { + background-image: url(images/btn/btn-soft-green-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-green-toolbar-small-mc { + background-color: #9cc96b; +} +.x-nbr .x-btn-soft-green-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-green-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-toolbar-small.x-segmented-button-first + .x-btn-soft-green-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-toolbar-small.x-segmented-button-middle + .x-btn-soft-green-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-toolbar-small.x-segmented-button-last + .x-btn-soft-green-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-toolbar-small.x-segmented-button-first + .x-btn-soft-green-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-toolbar-small.x-segmented-button-middle + .x-btn-soft-green-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-toolbar-small.x-segmented-button-last + .x-btn-soft-green-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-green-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-green-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-green-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-green-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-green-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-green-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-green-toolbar-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-green-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-soft-red-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #e44959; +} +.x-btn-soft-red-small-mc { + background-color: #e44959; +} +.x-nbr .x-btn-soft-red-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-red-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-red-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-red-small-tr { + background-position: right -3px; +} +.x-btn-soft-red-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-red-small-br { + background-position: right -5px; +} +.x-btn-soft-red-small-ml { + background-position: 0 top; +} +.x-btn-soft-red-small-mr { + background-position: right top; +} +.x-btn-soft-red-small-tc { + background-position: 0 0; +} +.x-btn-soft-red-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-red-small-tr, +.x-btn-soft-red-small-br, +.x-btn-soft-red-small-mr { + padding-right: 1px; +} +.x-btn-soft-red-small-tl, +.x-btn-soft-red-small-bl, +.x-btn-soft-red-small-ml { + padding-left: 1px; +} +.x-btn-soft-red-small-tc { + height: 1px; +} +.x-btn-soft-red-small-bc { + height: 1px; +} +.x-btn-soft-red-small-tl, +.x-btn-soft-red-small-bl, +.x-btn-soft-red-small-tr, +.x-btn-soft-red-small-br, +.x-btn-soft-red-small-tc, +.x-btn-soft-red-small-bc, +.x-btn-soft-red-small-ml, +.x-btn-soft-red-small-mr { + background-image: url(images/btn/btn-soft-red-small-corners.gif); +} +.x-btn-soft-red-small-ml, +.x-btn-soft-red-small-mr { + background-image: url(images/btn/btn-soft-red-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-red-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-red-small { + border-color: #e13345; +} +.x-btn-button-soft-red-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-red-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-red-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-red-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-red-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-red-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-red-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-red-small { + max-width: none; +} +.x-btn-icon-el-soft-red-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-red-small, +.x-btn-icon-right > .x-btn-icon-el-soft-red-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-red-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-red-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-red-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-red-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-red-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-red-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-red-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-red-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-red-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-red-small, +.x-btn-split-bottom > .x-btn-button-soft-red-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-red-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-red-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-red-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-red-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-red-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-soft-red-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-red-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-red-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-red-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-red-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-red-small { + background-image: none; + background-color: #e44959; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-soft-red-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-red-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-soft-red-small { + border-color: #cf2f3f; + background-image: none; + background-color: #d24352; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-red-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-red-small, +.x-btn.x-btn-pressed.x-btn-soft-red-small { + border-color: #a92634; + background-image: none; + background-color: #ab3743; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-red-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-red-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-red-small { + background-image: none; + background-color: #e44959; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-small-bc { + background-image: url(images/btn/btn-soft-red-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-small-mr { + background-image: url(images/btn/btn-soft-red-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-small-mc { + background-color: #e44959; +} +.x-btn-over .x-btn-soft-red-small-tl, +.x-btn-over .x-btn-soft-red-small-bl, +.x-btn-over .x-btn-soft-red-small-tr, +.x-btn-over .x-btn-soft-red-small-br, +.x-btn-over .x-btn-soft-red-small-tc, +.x-btn-over .x-btn-soft-red-small-bc { + background-image: url(images/btn/btn-soft-red-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-red-small-ml, +.x-btn-over .x-btn-soft-red-small-mr { + background-image: url(images/btn/btn-soft-red-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-red-small-mc { + background-color: #d24352; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-small-bc { + background-image: url(images/btn/btn-soft-red-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-small-mr { + background-image: url(images/btn/btn-soft-red-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-small-mc { + background-color: #d24352; +} +.x-btn.x-btn-menu-active .x-btn-soft-red-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-red-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-red-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-red-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-red-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-red-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-red-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-red-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-red-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-red-small-br, +.x-btn.x-btn-pressed .x-btn-soft-red-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-red-small-bc { + background-image: url(images/btn/btn-soft-red-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-red-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-red-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-red-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-red-small-mr { + background-image: url(images/btn/btn-soft-red-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-red-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-red-small-mc { + background-color: #ab3743; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-red-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-red-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-red-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-red-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-red-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-red-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-small-bc { + background-image: url(images/btn/btn-soft-red-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-red-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-red-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-small-mr { + background-image: url(images/btn/btn-soft-red-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-red-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-small-mc { + background-color: #ab3743; +} +.x-btn.x-btn-disabled .x-btn-soft-red-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-red-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-red-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-red-small-br, +.x-btn.x-btn-disabled .x-btn-soft-red-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-red-small-bc { + background-image: url(images/btn/btn-soft-red-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-red-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-red-small-mr { + background-image: url(images/btn/btn-soft-red-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-red-small-mc { + background-color: #e44959; +} +.x-nbr .x-btn-soft-red-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-red-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-small.x-segmented-button-first + .x-btn-soft-red-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-small.x-segmented-button-middle + .x-btn-soft-red-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-small.x-segmented-button-last + .x-btn-soft-red-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-small.x-segmented-button-first + .x-btn-soft-red-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-small.x-segmented-button-middle + .x-btn-soft-red-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-small.x-segmented-button-last + .x-btn-soft-red-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-red-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-red-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-red-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-red-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-red-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-red-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-red-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-soft-red-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #e44959; +} +.x-btn-soft-red-toolbar-small-mc { + background-color: #e44959; +} +.x-nbr .x-btn-soft-red-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-red-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-red-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-red-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-soft-red-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-red-toolbar-small-br { + background-position: right -5px; +} +.x-btn-soft-red-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-soft-red-toolbar-small-mr { + background-position: right top; +} +.x-btn-soft-red-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-soft-red-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-red-toolbar-small-tr, +.x-btn-soft-red-toolbar-small-br, +.x-btn-soft-red-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-soft-red-toolbar-small-tl, +.x-btn-soft-red-toolbar-small-bl, +.x-btn-soft-red-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-soft-red-toolbar-small-tc { + height: 1px; +} +.x-btn-soft-red-toolbar-small-bc { + height: 1px; +} +.x-btn-soft-red-toolbar-small-tl, +.x-btn-soft-red-toolbar-small-bl, +.x-btn-soft-red-toolbar-small-tr, +.x-btn-soft-red-toolbar-small-br, +.x-btn-soft-red-toolbar-small-tc, +.x-btn-soft-red-toolbar-small-bc, +.x-btn-soft-red-toolbar-small-ml, +.x-btn-soft-red-toolbar-small-mr { + background-image: url(images/btn/btn-soft-red-toolbar-small-corners.gif); +} +.x-btn-soft-red-toolbar-small-ml, +.x-btn-soft-red-toolbar-small-mr { + background-image: url(images/btn/btn-soft-red-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-red-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-red-toolbar-small { + border-color: #e13345; +} +.x-btn-button-soft-red-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-red-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-red-toolbar-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-red-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-red-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-red-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-red-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-red-toolbar-small { + max-width: none; +} +.x-btn-icon-el-soft-red-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-red-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-soft-red-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-red-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-red-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-red-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-red-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-red-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-red-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-red-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-red-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-red-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-red-toolbar-small, +.x-btn-split-bottom > .x-btn-button-soft-red-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-red-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-red-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-red-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-red-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-red-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-soft-red-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-red-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-red-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-red-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-red-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-red-toolbar-small { + background-image: none; + background-color: #e44959; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-soft-red-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-red-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-soft-red-toolbar-small { + border-color: #d83142; + background-image: none; + background-color: #db4655; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-red-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-red-toolbar-small, +.x-btn.x-btn-pressed.x-btn-soft-red-toolbar-small { + border-color: #cf2f3f; + background-image: none; + background-color: #d24352; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-red-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-red-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-red-toolbar-small { + background-image: none; + background-color: #e44959; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-toolbar-small-bc { + background-image: url(images/btn/btn-soft-red-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-toolbar-small-mr { + background-image: url(images/btn/btn-soft-red-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-red-toolbar-small-mc { + background-color: #e44959; +} +.x-btn-over .x-btn-soft-red-toolbar-small-tl, +.x-btn-over .x-btn-soft-red-toolbar-small-bl, +.x-btn-over .x-btn-soft-red-toolbar-small-tr, +.x-btn-over .x-btn-soft-red-toolbar-small-br, +.x-btn-over .x-btn-soft-red-toolbar-small-tc, +.x-btn-over .x-btn-soft-red-toolbar-small-bc { + background-image: url(images/btn/btn-soft-red-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-red-toolbar-small-ml, +.x-btn-over .x-btn-soft-red-toolbar-small-mr { + background-image: url(images/btn/btn-soft-red-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-red-toolbar-small-mc { + background-color: #db4655; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-toolbar-small-bc { + background-image: url(images/btn/btn-soft-red-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-toolbar-small-mr { + background-image: url(images/btn/btn-soft-red-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-red-toolbar-small-mc { + background-color: #db4655; +} +.x-btn.x-btn-menu-active .x-btn-soft-red-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-red-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-red-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-red-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-red-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-red-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-red-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-red-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-red-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-red-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-soft-red-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-red-toolbar-small-bc { + background-image: url(images/btn/btn-soft-red-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-red-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-red-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-red-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-red-toolbar-small-mr { + background-image: url(images/btn/btn-soft-red-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-red-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-red-toolbar-small-mc { + background-color: #d24352; +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-red-toolbar-small-tl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-red-toolbar-small-bl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-red-toolbar-small-tr, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-red-toolbar-small-br, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-red-toolbar-small-tc, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-red-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-toolbar-small-bc { + background-image: url(images/btn/btn-soft-red-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-red-toolbar-small-ml, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-red-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-toolbar-small-mr { + background-image: url(images/btn/btn-soft-red-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-red-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-red-toolbar-small-mc { + background-color: #d24352; +} +.x-btn.x-btn-disabled .x-btn-soft-red-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-red-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-red-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-red-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-soft-red-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-red-toolbar-small-bc { + background-image: url(images/btn/btn-soft-red-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-red-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-red-toolbar-small-mr { + background-image: url(images/btn/btn-soft-red-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-red-toolbar-small-mc { + background-color: #e44959; +} +.x-nbr .x-btn-soft-red-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-red-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-toolbar-small.x-segmented-button-first + .x-btn-soft-red-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-toolbar-small.x-segmented-button-middle + .x-btn-soft-red-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-toolbar-small.x-segmented-button-last + .x-btn-soft-red-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-toolbar-small.x-segmented-button-first + .x-btn-soft-red-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-toolbar-small.x-segmented-button-middle + .x-btn-soft-red-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-toolbar-small.x-segmented-button-last + .x-btn-soft-red-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-red-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-red-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-red-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-red-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-red-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-red-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-red-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-red-toolbar-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-red-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-soft-purple-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #925e8b; +} +.x-btn-soft-purple-small-mc { + background-color: #925e8b; +} +.x-nbr .x-btn-soft-purple-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-purple-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-purple-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-purple-small-tr { + background-position: right -3px; +} +.x-btn-soft-purple-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-purple-small-br { + background-position: right -5px; +} +.x-btn-soft-purple-small-ml { + background-position: 0 top; +} +.x-btn-soft-purple-small-mr { + background-position: right top; +} +.x-btn-soft-purple-small-tc { + background-position: 0 0; +} +.x-btn-soft-purple-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-purple-small-tr, +.x-btn-soft-purple-small-br, +.x-btn-soft-purple-small-mr { + padding-right: 1px; +} +.x-btn-soft-purple-small-tl, +.x-btn-soft-purple-small-bl, +.x-btn-soft-purple-small-ml { + padding-left: 1px; +} +.x-btn-soft-purple-small-tc { + height: 1px; +} +.x-btn-soft-purple-small-bc { + height: 1px; +} +.x-btn-soft-purple-small-tl, +.x-btn-soft-purple-small-bl, +.x-btn-soft-purple-small-tr, +.x-btn-soft-purple-small-br, +.x-btn-soft-purple-small-tc, +.x-btn-soft-purple-small-bc, +.x-btn-soft-purple-small-ml, +.x-btn-soft-purple-small-mr { + background-image: url(images/btn/btn-soft-purple-small-corners.gif); +} +.x-btn-soft-purple-small-ml, +.x-btn-soft-purple-small-mr { + background-image: url(images/btn/btn-soft-purple-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-purple-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-purple-small { + border-color: #82547c; +} +.x-btn-button-soft-purple-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-purple-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-purple-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-purple-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-purple-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-purple-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-purple-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-purple-small { + max-width: none; +} +.x-btn-icon-el-soft-purple-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-purple-small, +.x-btn-icon-right > .x-btn-icon-el-soft-purple-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-purple-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-purple-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-purple-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-purple-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-purple-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-purple-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-purple-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-purple-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-purple-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-purple-small, +.x-btn-split-bottom > .x-btn-button-soft-purple-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-purple-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-purple-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-soft-purple-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-purple-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-purple-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-soft-purple-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-purple-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-soft-purple-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-soft-purple-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-purple-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-purple-small { + background-image: none; + background-color: #925e8b; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-soft-purple-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-soft-purple-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-soft-purple-small { + border-color: #784d72; + background-image: none; + background-color: #865680; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-purple-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-purple-small, +.x-btn.x-btn-pressed.x-btn-soft-purple-small { + border-color: #623f5d; + background-image: none; + background-color: #6e4768; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-purple-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-purple-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-purple-small { + background-image: none; + background-color: #925e8b; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-small-bc { + background-image: url(images/btn/btn-soft-purple-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-small-mr { + background-image: url(images/btn/btn-soft-purple-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-small-mc { + background-color: #925e8b; +} +.x-btn-over .x-btn-soft-purple-small-tl, +.x-btn-over .x-btn-soft-purple-small-bl, +.x-btn-over .x-btn-soft-purple-small-tr, +.x-btn-over .x-btn-soft-purple-small-br, +.x-btn-over .x-btn-soft-purple-small-tc, +.x-btn-over .x-btn-soft-purple-small-bc { + background-image: url(images/btn/btn-soft-purple-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-purple-small-ml, +.x-btn-over .x-btn-soft-purple-small-mr { + background-image: url(images/btn/btn-soft-purple-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-purple-small-mc { + background-color: #865680; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-small-bc { + background-image: url(images/btn/btn-soft-purple-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-small-mr { + background-image: url(images/btn/btn-soft-purple-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-small-mc { + background-color: #865680; +} +.x-btn.x-btn-menu-active .x-btn-soft-purple-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-purple-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-purple-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-purple-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-purple-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-purple-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-purple-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-purple-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-purple-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-purple-small-br, +.x-btn.x-btn-pressed .x-btn-soft-purple-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-purple-small-bc { + background-image: url(images/btn/btn-soft-purple-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-purple-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-purple-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-purple-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-purple-small-mr { + background-image: url(images/btn/btn-soft-purple-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-purple-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-purple-small-mc { + background-color: #6e4768; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-purple-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-purple-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-purple-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-purple-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-purple-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-purple-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-small-bc { + background-image: url(images/btn/btn-soft-purple-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-purple-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-purple-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-small-mr { + background-image: url(images/btn/btn-soft-purple-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-soft-purple-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-small-mc { + background-color: #6e4768; +} +.x-btn.x-btn-disabled .x-btn-soft-purple-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-purple-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-purple-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-purple-small-br, +.x-btn.x-btn-disabled .x-btn-soft-purple-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-purple-small-bc { + background-image: url(images/btn/btn-soft-purple-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-purple-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-purple-small-mr { + background-image: url(images/btn/btn-soft-purple-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-purple-small-mc { + background-color: #925e8b; +} +.x-nbr .x-btn-soft-purple-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-purple-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-small.x-segmented-button-first + .x-btn-soft-purple-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-small.x-segmented-button-middle + .x-btn-soft-purple-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-small.x-segmented-button-last + .x-btn-soft-purple-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-small.x-segmented-button-first + .x-btn-soft-purple-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-small.x-segmented-button-middle + .x-btn-soft-purple-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-small.x-segmented-button-last + .x-btn-soft-purple-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-purple-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-soft-purple-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-purple-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-purple-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-purple-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-purple-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-purple-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-soft-purple-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #925e8b; +} +.x-btn-soft-purple-toolbar-small-mc { + background-color: #925e8b; +} +.x-nbr .x-btn-soft-purple-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-soft-purple-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-soft-purple-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-soft-purple-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-soft-purple-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-soft-purple-toolbar-small-br { + background-position: right -5px; +} +.x-btn-soft-purple-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-soft-purple-toolbar-small-mr { + background-position: right top; +} +.x-btn-soft-purple-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-soft-purple-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-soft-purple-toolbar-small-tr, +.x-btn-soft-purple-toolbar-small-br, +.x-btn-soft-purple-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-soft-purple-toolbar-small-tl, +.x-btn-soft-purple-toolbar-small-bl, +.x-btn-soft-purple-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-soft-purple-toolbar-small-tc { + height: 1px; +} +.x-btn-soft-purple-toolbar-small-bc { + height: 1px; +} +.x-btn-soft-purple-toolbar-small-tl, +.x-btn-soft-purple-toolbar-small-bl, +.x-btn-soft-purple-toolbar-small-tr, +.x-btn-soft-purple-toolbar-small-br, +.x-btn-soft-purple-toolbar-small-tc, +.x-btn-soft-purple-toolbar-small-bc, +.x-btn-soft-purple-toolbar-small-ml, +.x-btn-soft-purple-toolbar-small-mr { + background-image: url(images/btn/btn-soft-purple-toolbar-small-corners.gif); +} +.x-btn-soft-purple-toolbar-small-ml, +.x-btn-soft-purple-toolbar-small-mr { + background-image: url(images/btn/btn-soft-purple-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-soft-purple-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-soft-purple-toolbar-small { + border-color: #82547c; +} +.x-btn-button-soft-purple-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-soft-purple-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-soft-purple-toolbar-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-soft-purple-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-soft-purple-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-soft-purple-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-soft-purple-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-soft-purple-toolbar-small { + max-width: none; +} +.x-btn-icon-el-soft-purple-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-soft-purple-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-soft-purple-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-soft-purple-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-soft-purple-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-soft-purple-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-soft-purple-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-soft-purple-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-soft-purple-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-soft-purple-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-purple-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-purple-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-soft-purple-toolbar-small, +.x-btn-split-bottom > .x-btn-button-soft-purple-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-soft-purple-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-purple-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-soft-purple-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-soft-purple-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-purple-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-soft-purple-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-soft-purple-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-soft-purple-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-soft-purple-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-soft-purple-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-soft-purple-toolbar-small { + background-image: none; + background-color: #925e8b; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn-soft-purple-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode + .x-btn-soft-purple-toolbar-small.x-arrow-focus + .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-soft-purple-toolbar-small { + border-color: #7d5177; + background-image: none; + background-color: #8c5a85; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-soft-purple-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-soft-purple-toolbar-small, +.x-btn.x-btn-pressed.x-btn-soft-purple-toolbar-small { + border-color: #784d72; + background-image: none; + background-color: #865680; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-soft-purple-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-soft-purple-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, + #5aaed4 -1px 0 0px 0 inset, #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-soft-purple-toolbar-small { + background-image: none; + background-color: #925e8b; +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-toolbar-small-bc { + background-image: url(images/btn/btn-soft-purple-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-toolbar-small-mr { + background-image: url(images/btn/btn-soft-purple-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-soft-purple-toolbar-small-mc { + background-color: #925e8b; +} +.x-btn-over .x-btn-soft-purple-toolbar-small-tl, +.x-btn-over .x-btn-soft-purple-toolbar-small-bl, +.x-btn-over .x-btn-soft-purple-toolbar-small-tr, +.x-btn-over .x-btn-soft-purple-toolbar-small-br, +.x-btn-over .x-btn-soft-purple-toolbar-small-tc, +.x-btn-over .x-btn-soft-purple-toolbar-small-bc { + background-image: url(images/btn/btn-soft-purple-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-soft-purple-toolbar-small-ml, +.x-btn-over .x-btn-soft-purple-toolbar-small-mr { + background-image: url(images/btn/btn-soft-purple-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-soft-purple-toolbar-small-mc { + background-color: #8c5a85; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-toolbar-small-bc { + background-image: url(images/btn/btn-soft-purple-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-toolbar-small-mr { + background-image: url(images/btn/btn-soft-purple-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-soft-purple-toolbar-small-mc { + background-color: #8c5a85; +} +.x-btn.x-btn-menu-active .x-btn-soft-purple-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-soft-purple-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-soft-purple-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-soft-purple-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-soft-purple-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-soft-purple-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-soft-purple-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-soft-purple-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-soft-purple-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-soft-purple-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-soft-purple-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-soft-purple-toolbar-small-bc { + background-image: url(images/btn/btn-soft-purple-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-purple-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-soft-purple-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-soft-purple-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-soft-purple-toolbar-small-mr { + background-image: url(images/btn/btn-soft-purple-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-soft-purple-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-soft-purple-toolbar-small-mc { + background-color: #865680; +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-purple-toolbar-small-tl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-purple-toolbar-small-bl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-purple-toolbar-small-tr, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-purple-toolbar-small-br, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-purple-toolbar-small-tc, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-purple-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-toolbar-small-tc, +.x-keyboard-mode + .x-btn-focus.x-btn-pressed + .x-btn-soft-purple-toolbar-small-bc { + background-image: url(images/btn/btn-soft-purple-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-purple-toolbar-small-ml, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-purple-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-soft-purple-toolbar-small-ml, +.x-keyboard-mode + .x-btn-focus.x-btn-pressed + .x-btn-soft-purple-toolbar-small-mr { + background-image: url(images/btn/btn-soft-purple-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-soft-purple-toolbar-small-mc, +.x-keyboard-mode + .x-btn-focus.x-btn-pressed + .x-btn-soft-purple-toolbar-small-mc { + background-color: #865680; +} +.x-btn.x-btn-disabled .x-btn-soft-purple-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-soft-purple-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-soft-purple-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-soft-purple-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-soft-purple-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-soft-purple-toolbar-small-bc { + background-image: url(images/btn/btn-soft-purple-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-purple-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-soft-purple-toolbar-small-mr { + background-image: url(images/btn/btn-soft-purple-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-soft-purple-toolbar-small-mc { + background-color: #925e8b; +} +.x-nbr .x-btn-soft-purple-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-soft-purple-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-toolbar-small.x-segmented-button-first + .x-btn-soft-purple-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-toolbar-small.x-segmented-button-middle + .x-btn-soft-purple-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-toolbar-small.x-segmented-button-last + .x-btn-soft-purple-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-toolbar-small.x-segmented-button-first + .x-btn-soft-purple-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-toolbar-small.x-segmented-button-middle + .x-btn-soft-purple-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-toolbar-small.x-segmented-button-last + .x-btn-soft-purple-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-soft-purple-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-soft-purple-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-soft-purple-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-soft-purple-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-soft-purple-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-soft-purple-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-soft-purple-toolbar-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-soft-purple-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-gray-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #949495; +} +.x-btn-gray-small-mc { + background-color: #949495; +} +.x-nbr .x-btn-gray-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-gray-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-gray-small-tl { + background-position: 0 -2px; +} +.x-btn-gray-small-tr { + background-position: right -3px; +} +.x-btn-gray-small-bl { + background-position: 0 -4px; +} +.x-btn-gray-small-br { + background-position: right -5px; +} +.x-btn-gray-small-ml { + background-position: 0 top; +} +.x-btn-gray-small-mr { + background-position: right top; +} +.x-btn-gray-small-tc { + background-position: 0 0; +} +.x-btn-gray-small-bc { + background-position: 0 -1px; +} +.x-btn-gray-small-tr, +.x-btn-gray-small-br, +.x-btn-gray-small-mr { + padding-right: 1px; +} +.x-btn-gray-small-tl, +.x-btn-gray-small-bl, +.x-btn-gray-small-ml { + padding-left: 1px; +} +.x-btn-gray-small-tc { + height: 1px; +} +.x-btn-gray-small-bc { + height: 1px; +} +.x-btn-gray-small-tl, +.x-btn-gray-small-bl, +.x-btn-gray-small-tr, +.x-btn-gray-small-br, +.x-btn-gray-small-tc, +.x-btn-gray-small-bc, +.x-btn-gray-small-ml, +.x-btn-gray-small-mr { + background-image: url(images/btn/btn-gray-small-corners.gif); +} +.x-btn-gray-small-ml, +.x-btn-gray-small-mr { + background-image: url(images/btn/btn-gray-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-gray-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-gray-small { + border-color: #878788; +} +.x-btn-button-gray-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-gray-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-gray-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-gray-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-gray-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-gray-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-gray-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-gray-small { + max-width: none; +} +.x-btn-icon-el-gray-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-gray-small, +.x-btn-icon-right > .x-btn-icon-el-gray-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-gray-small, +.x-btn-icon-bottom > .x-btn-icon-el-gray-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-gray-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-gray-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-gray-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-gray-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-gray-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-gray-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-gray-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-gray-small, +.x-btn-split-bottom > .x-btn-button-gray-small { + padding-bottom: 7px; +} +.x-btn-wrap-gray-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-gray-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-gray-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-gray-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-gray-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-gray-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-gray-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-gray-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-gray-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-gray-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-gray-small { + background-image: none; + background-color: #949495; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-gray-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-gray-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-gray-small { + border-color: #7c7c7d; + background-image: none; + background-color: #888889; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-gray-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-gray-small, +.x-btn.x-btn-pressed.x-btn-gray-small { + border-color: #656566; + background-image: none; + background-color: #6f6f70; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-gray-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-gray-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, + #c8dce5 -1px 0 0px 0 inset, #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-gray-small { + background-image: none; + background-color: #949495; +} +.x-keyboard-mode .x-btn-focus .x-btn-gray-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-gray-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-gray-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-gray-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-gray-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-gray-small-bc { + background-image: url(images/btn/btn-gray-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-gray-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-gray-small-mr { + background-image: url(images/btn/btn-gray-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-gray-small-mc { + background-color: #949495; +} +.x-btn-over .x-btn-gray-small-tl, +.x-btn-over .x-btn-gray-small-bl, +.x-btn-over .x-btn-gray-small-tr, +.x-btn-over .x-btn-gray-small-br, +.x-btn-over .x-btn-gray-small-tc, +.x-btn-over .x-btn-gray-small-bc { + background-image: url(images/btn/btn-gray-small-over-corners.gif); +} +.x-btn-over .x-btn-gray-small-ml, +.x-btn-over .x-btn-gray-small-mr { + background-image: url(images/btn/btn-gray-small-over-sides.gif); +} +.x-btn-over .x-btn-gray-small-mc { + background-color: #888889; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-small-bc { + background-image: url(images/btn/btn-gray-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-small-mr { + background-image: url(images/btn/btn-gray-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-small-mc { + background-color: #888889; +} +.x-btn.x-btn-menu-active .x-btn-gray-small-tl, +.x-btn.x-btn-menu-active .x-btn-gray-small-bl, +.x-btn.x-btn-menu-active .x-btn-gray-small-tr, +.x-btn.x-btn-menu-active .x-btn-gray-small-br, +.x-btn.x-btn-menu-active .x-btn-gray-small-tc, +.x-btn.x-btn-menu-active .x-btn-gray-small-bc, +.x-btn.x-btn-pressed .x-btn-gray-small-tl, +.x-btn.x-btn-pressed .x-btn-gray-small-bl, +.x-btn.x-btn-pressed .x-btn-gray-small-tr, +.x-btn.x-btn-pressed .x-btn-gray-small-br, +.x-btn.x-btn-pressed .x-btn-gray-small-tc, +.x-btn.x-btn-pressed .x-btn-gray-small-bc { + background-image: url(images/btn/btn-gray-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-gray-small-ml, +.x-btn.x-btn-menu-active .x-btn-gray-small-mr, +.x-btn.x-btn-pressed .x-btn-gray-small-ml, +.x-btn.x-btn-pressed .x-btn-gray-small-mr { + background-image: url(images/btn/btn-gray-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-gray-small-mc, +.x-btn.x-btn-pressed .x-btn-gray-small-mc { + background-color: #6f6f70; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-small-bc { + background-image: url(images/btn/btn-gray-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-small-mr { + background-image: url(images/btn/btn-gray-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-small-mc { + background-color: #6f6f70; +} +.x-btn.x-btn-disabled .x-btn-gray-small-tl, +.x-btn.x-btn-disabled .x-btn-gray-small-bl, +.x-btn.x-btn-disabled .x-btn-gray-small-tr, +.x-btn.x-btn-disabled .x-btn-gray-small-br, +.x-btn.x-btn-disabled .x-btn-gray-small-tc, +.x-btn.x-btn-disabled .x-btn-gray-small-bc { + background-image: url(images/btn/btn-gray-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-gray-small-ml, +.x-btn.x-btn-disabled .x-btn-gray-small-mr { + background-image: url(images/btn/btn-gray-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-gray-small-mc { + background-color: #949495; +} +.x-nbr .x-btn-gray-small { + background-image: none; +} +.x-btn-disabled.x-btn-gray-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-small.x-segmented-button-first + .x-btn-gray-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-small.x-segmented-button-middle + .x-btn-gray-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-small.x-segmented-button-last + .x-btn-gray-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-gray-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-gray-small.x-segmented-button-first + .x-btn-gray-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-gray-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-gray-small.x-segmented-button-middle + .x-btn-gray-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-gray-small.x-segmented-button-last + .x-btn-gray-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-gray-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-gray-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-gray-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-gray-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-gray-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-gray-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-gray-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-gray-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #949495; +} +.x-btn-gray-large-mc { + background-color: #949495; +} +.x-nbr .x-btn-gray-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-gray-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +.x-btn-gray-large-tl { + background-position: 0 -2px; +} +.x-btn-gray-large-tr { + background-position: right -3px; +} +.x-btn-gray-large-bl { + background-position: 0 -4px; +} +.x-btn-gray-large-br { + background-position: right -5px; +} +.x-btn-gray-large-ml { + background-position: 0 top; +} +.x-btn-gray-large-mr { + background-position: right top; +} +.x-btn-gray-large-tc { + background-position: 0 0; +} +.x-btn-gray-large-bc { + background-position: 0 -1px; +} +.x-btn-gray-large-tr, +.x-btn-gray-large-br, +.x-btn-gray-large-mr { + padding-right: 1px; +} +.x-btn-gray-large-tl, +.x-btn-gray-large-bl, +.x-btn-gray-large-ml { + padding-left: 1px; +} +.x-btn-gray-large-tc { + height: 1px; +} +.x-btn-gray-large-bc { + height: 1px; +} +.x-btn-gray-large-tl, +.x-btn-gray-large-bl, +.x-btn-gray-large-tr, +.x-btn-gray-large-br, +.x-btn-gray-large-tc, +.x-btn-gray-large-bc, +.x-btn-gray-large-ml, +.x-btn-gray-large-mr { + background-image: url(images/btn/btn-gray-large-corners.gif); +} +.x-btn-gray-large-ml, +.x-btn-gray-large-mr { + background-image: url(images/btn/btn-gray-large-sides.gif); + background-repeat: repeat-y; +} +.x-btn-gray-large-mc { + padding: 9px 9px 9px 9px; +} +.x-btn-gray-large { + border-color: #878788; +} +.x-btn-button-gray-large { + min-height: 34px; +} +.x-ie9m .x-btn-button-gray-large { + min-height: auto; + height: 34px; +} +.x-btn-inner-gray-large { + font: 500 16px/34px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 10px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-gray-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-gray-large { + max-width: calc(100% - 24px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-gray-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-gray-large { + max-width: calc(100% - 23px); +} +.x-ie10p .x-btn-inner-gray-large { + max-width: none; +} +.x-btn-icon-el-gray-large { + font-size: 24px; + height: 24px; + color: #f0f0f0; + line-height: 24px; +} +.x-btn-icon-left > .x-btn-icon-el-gray-large, +.x-btn-icon-right > .x-btn-icon-el-gray-large { + width: 24px; +} +.x-btn-icon-top > .x-btn-icon-el-gray-large, +.x-btn-icon-bottom > .x-btn-icon-el-gray-large { + min-width: 24px; +} +.x-ie8 .x-btn-icon-el-gray-large.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-gray-large { + margin-right: 0; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-gray-large { + margin-left: 0; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-gray-large { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-gray-large { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-gray-large { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-gray-large { + margin-right: 10px; +} +.x-btn-arrow-bottom > .x-btn-button-gray-large, +.x-btn-split-bottom > .x-btn-button-gray-large { + padding-bottom: 9px; +} +.x-btn-wrap-gray-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-gray-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-gray-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +.x-btn-wrap-gray-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-gray-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; + padding-left: 9px; +} +.x-btn-wrap-gray-large.x-btn-split-bottom { + margin-bottom: -9px; +} +.x-btn-wrap-gray-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-gray-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-gray-large { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-gray-large { + margin-right: 10px; +} +.x-keyboard-mode .x-btn-focus.x-btn-gray-large { + background-image: none; + background-color: #949495; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, + #cbe5f1 -1px 0 0px 0 inset, #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-gray-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-gray-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-gray-large { + border-color: #7c7c7d; + background-image: none; + background-color: #888889; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-gray-large { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, + #cae2ed -1px 0 0px 0 inset, #cae2ed 1px 0 0px 0 inset; +} diff --git a/src/main/webapp/resources/css/adminDashboardCSS/Admin-all_3.css b/src/main/webapp/resources/css/adminDashboardCSS/Admin-all_3.css new file mode 100644 index 0000000..74e806b --- /dev/null +++ b/src/main/webapp/resources/css/adminDashboardCSS/Admin-all_3.css @@ -0,0 +1,5065 @@ +.x-btn.x-btn-menu-active.x-btn-gray-large, +.x-btn.x-btn-pressed.x-btn-gray-large { + border-color: #656566; + background-image: none; + background-color: #6f6f70; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-gray-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-gray-large { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-gray-large { + background-image: none; + background-color: #949495; +} +.x-keyboard-mode .x-btn-focus .x-btn-gray-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-gray-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-gray-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-gray-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-gray-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-gray-large-bc { + background-image: url(images/btn/btn-gray-large-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-gray-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-gray-large-mr { + background-image: url(images/btn/btn-gray-large-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-gray-large-mc { + background-color: #949495; +} +.x-btn-over .x-btn-gray-large-tl, +.x-btn-over .x-btn-gray-large-bl, +.x-btn-over .x-btn-gray-large-tr, +.x-btn-over .x-btn-gray-large-br, +.x-btn-over .x-btn-gray-large-tc, +.x-btn-over .x-btn-gray-large-bc { + background-image: url(images/btn/btn-gray-large-over-corners.gif); +} +.x-btn-over .x-btn-gray-large-ml, +.x-btn-over .x-btn-gray-large-mr { + background-image: url(images/btn/btn-gray-large-over-sides.gif); +} +.x-btn-over .x-btn-gray-large-mc { + background-color: #888889; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-large-bc { + background-image: url(images/btn/btn-gray-large-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-large-mr { + background-image: url(images/btn/btn-gray-large-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-large-mc { + background-color: #888889; +} +.x-btn.x-btn-menu-active .x-btn-gray-large-tl, +.x-btn.x-btn-menu-active .x-btn-gray-large-bl, +.x-btn.x-btn-menu-active .x-btn-gray-large-tr, +.x-btn.x-btn-menu-active .x-btn-gray-large-br, +.x-btn.x-btn-menu-active .x-btn-gray-large-tc, +.x-btn.x-btn-menu-active .x-btn-gray-large-bc, +.x-btn.x-btn-pressed .x-btn-gray-large-tl, +.x-btn.x-btn-pressed .x-btn-gray-large-bl, +.x-btn.x-btn-pressed .x-btn-gray-large-tr, +.x-btn.x-btn-pressed .x-btn-gray-large-br, +.x-btn.x-btn-pressed .x-btn-gray-large-tc, +.x-btn.x-btn-pressed .x-btn-gray-large-bc { + background-image: url(images/btn/btn-gray-large-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-gray-large-ml, +.x-btn.x-btn-menu-active .x-btn-gray-large-mr, +.x-btn.x-btn-pressed .x-btn-gray-large-ml, +.x-btn.x-btn-pressed .x-btn-gray-large-mr { + background-image: url(images/btn/btn-gray-large-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-gray-large-mc, +.x-btn.x-btn-pressed .x-btn-gray-large-mc { + background-color: #6f6f70; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-large-bc { + background-image: url(images/btn/btn-gray-large-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-large-mr { + background-image: url(images/btn/btn-gray-large-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-large-mc { + background-color: #6f6f70; +} +.x-btn.x-btn-disabled .x-btn-gray-large-tl, +.x-btn.x-btn-disabled .x-btn-gray-large-bl, +.x-btn.x-btn-disabled .x-btn-gray-large-tr, +.x-btn.x-btn-disabled .x-btn-gray-large-br, +.x-btn.x-btn-disabled .x-btn-gray-large-tc, +.x-btn.x-btn-disabled .x-btn-gray-large-bc { + background-image: url(images/btn/btn-gray-large-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-gray-large-ml, +.x-btn.x-btn-disabled .x-btn-gray-large-mr { + background-image: url(images/btn/btn-gray-large-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-gray-large-mc { + background-color: #949495; +} +.x-nbr .x-btn-gray-large { + background-image: none; +} +.x-btn-disabled.x-btn-gray-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-large.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-large.x-segmented-button-first .x-btn-gray-large-mc { + padding-right: 9px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-large.x-segmented-button-middle .x-btn-gray-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-large.x-segmented-button-last .x-btn-gray-large-mc { + padding-left: 9px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-large.x-segmented-button-first .x-btn-gray-large-mc { + padding-bottom: 9px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-large.x-segmented-button-middle .x-btn-gray-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-large.x-segmented-button-last .x-btn-gray-large-mc { + padding-top: 9px !important; +} +.x-nbr .x-segmented-button-item.x-btn-gray-large:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-large.x-segmented-button-first:after { + left: 1px; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-large.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-large.x-segmented-button-first:after { + top: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-large.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-gray-large:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-gray-large:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-gray-large:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-gray-large:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-gray-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #949495; +} +.x-btn-gray-toolbar-small-mc { + background-color: #949495; +} +.x-nbr .x-btn-gray-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-gray-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-gray-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-gray-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-gray-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-gray-toolbar-small-br { + background-position: right -5px; +} +.x-btn-gray-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-gray-toolbar-small-mr { + background-position: right top; +} +.x-btn-gray-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-gray-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-gray-toolbar-small-tr, +.x-btn-gray-toolbar-small-br, +.x-btn-gray-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-gray-toolbar-small-tl, +.x-btn-gray-toolbar-small-bl, +.x-btn-gray-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-gray-toolbar-small-tc { + height: 1px; +} +.x-btn-gray-toolbar-small-bc { + height: 1px; +} +.x-btn-gray-toolbar-small-tl, +.x-btn-gray-toolbar-small-bl, +.x-btn-gray-toolbar-small-tr, +.x-btn-gray-toolbar-small-br, +.x-btn-gray-toolbar-small-tc, +.x-btn-gray-toolbar-small-bc, +.x-btn-gray-toolbar-small-ml, +.x-btn-gray-toolbar-small-mr { + background-image: url(images/btn/btn-gray-toolbar-small-corners.gif); +} +.x-btn-gray-toolbar-small-ml, +.x-btn-gray-toolbar-small-mr { + background-image: url(images/btn/btn-gray-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-gray-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-gray-toolbar-small { + border-color: #878788; +} +.x-btn-button-gray-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-gray-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-gray-toolbar-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-gray-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-gray-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-gray-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-gray-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-gray-toolbar-small { + max-width: none; +} +.x-btn-icon-el-gray-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-gray-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-gray-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-gray-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-gray-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-gray-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-gray-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-gray-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-gray-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-gray-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-gray-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-gray-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-gray-toolbar-small, +.x-btn-split-bottom > .x-btn-button-gray-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-gray-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-gray-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-gray-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-gray-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-gray-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-gray-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-gray-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-gray-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-gray-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-gray-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-gray-toolbar-small { + background-image: none; + background-color: #949495; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; +} +.x-btn-gray-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-gray-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-gray-toolbar-small { + border-color: #828283; + background-image: none; + background-color: #8e8e8f; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-gray-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-gray-toolbar-small, +.x-btn.x-btn-pressed.x-btn-gray-toolbar-small { + border-color: #7c7c7d; + background-image: none; + background-color: #888889; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-gray-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-gray-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-gray-toolbar-small { + background-image: none; + background-color: #949495; +} +.x-keyboard-mode .x-btn-focus .x-btn-gray-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-gray-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-gray-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-gray-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-gray-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-gray-toolbar-small-bc { + background-image: url(images/btn/btn-gray-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-gray-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-gray-toolbar-small-mr { + background-image: url(images/btn/btn-gray-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-gray-toolbar-small-mc { + background-color: #949495; +} +.x-btn-over .x-btn-gray-toolbar-small-tl, +.x-btn-over .x-btn-gray-toolbar-small-bl, +.x-btn-over .x-btn-gray-toolbar-small-tr, +.x-btn-over .x-btn-gray-toolbar-small-br, +.x-btn-over .x-btn-gray-toolbar-small-tc, +.x-btn-over .x-btn-gray-toolbar-small-bc { + background-image: url(images/btn/btn-gray-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-gray-toolbar-small-ml, +.x-btn-over .x-btn-gray-toolbar-small-mr { + background-image: url(images/btn/btn-gray-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-gray-toolbar-small-mc { + background-color: #8e8e8f; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-toolbar-small-bc { + background-image: url(images/btn/btn-gray-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-toolbar-small-mr { + background-image: url(images/btn/btn-gray-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-gray-toolbar-small-mc { + background-color: #8e8e8f; +} +.x-btn.x-btn-menu-active .x-btn-gray-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-gray-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-gray-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-gray-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-gray-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-gray-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-gray-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-gray-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-gray-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-gray-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-gray-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-gray-toolbar-small-bc { + background-image: url(images/btn/btn-gray-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-gray-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-gray-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-gray-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-gray-toolbar-small-mr { + background-image: url(images/btn/btn-gray-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-gray-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-gray-toolbar-small-mc { + background-color: #888889; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-toolbar-small-bc { + background-image: url(images/btn/btn-gray-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-toolbar-small-mr { + background-image: url(images/btn/btn-gray-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-gray-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-gray-toolbar-small-mc { + background-color: #888889; +} +.x-btn.x-btn-disabled .x-btn-gray-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-gray-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-gray-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-gray-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-gray-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-gray-toolbar-small-bc { + background-image: url(images/btn/btn-gray-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-gray-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-gray-toolbar-small-mr { + background-image: url(images/btn/btn-gray-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-gray-toolbar-small-mc { + background-color: #949495; +} +.x-nbr .x-btn-gray-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-gray-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-toolbar-small.x-segmented-button-first + .x-btn-gray-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-toolbar-small.x-segmented-button-middle + .x-btn-gray-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-gray-toolbar-small.x-segmented-button-last + .x-btn-gray-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-gray-toolbar-small.x-segmented-button-first + .x-btn-gray-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-gray-toolbar-small.x-segmented-button-middle + .x-btn-gray-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-toolbar-small.x-segmented-button-last .x-btn-gray-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-gray-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-gray-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-gray-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-gray-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-gray-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-gray-toolbar-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-gray-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-green-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #16b603; +} +.x-btn-green-small-mc { + background-color: #16b603; +} +.x-nbr .x-btn-green-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-green-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-green-small-tl { + background-position: 0 -2px; +} +.x-btn-green-small-tr { + background-position: right -3px; +} +.x-btn-green-small-bl { + background-position: 0 -4px; +} +.x-btn-green-small-br { + background-position: right -5px; +} +.x-btn-green-small-ml { + background-position: 0 top; +} +.x-btn-green-small-mr { + background-position: right top; +} +.x-btn-green-small-tc { + background-position: 0 0; +} +.x-btn-green-small-bc { + background-position: 0 -1px; +} +.x-btn-green-small-tr, +.x-btn-green-small-br, +.x-btn-green-small-mr { + padding-right: 1px; +} +.x-btn-green-small-tl, +.x-btn-green-small-bl, +.x-btn-green-small-ml { + padding-left: 1px; +} +.x-btn-green-small-tc { + height: 1px; +} +.x-btn-green-small-bc { + height: 1px; +} +.x-btn-green-small-tl, +.x-btn-green-small-bl, +.x-btn-green-small-tr, +.x-btn-green-small-br, +.x-btn-green-small-tc, +.x-btn-green-small-bc, +.x-btn-green-small-ml, +.x-btn-green-small-mr { + background-image: url(images/btn/btn-green-small-corners.gif); +} +.x-btn-green-small-ml, +.x-btn-green-small-mr { + background-image: url(images/btn/btn-green-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-green-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-green-small { + border-color: #139d03; +} +.x-btn-button-green-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-green-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-green-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-green-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-green-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-green-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-green-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-green-small { + max-width: none; +} +.x-btn-icon-el-green-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-green-small, +.x-btn-icon-right > .x-btn-icon-el-green-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-green-small, +.x-btn-icon-bottom > .x-btn-icon-el-green-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-green-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-green-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-green-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-green-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-green-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-green-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-green-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-green-small, +.x-btn-split-bottom > .x-btn-button-green-small { + padding-bottom: 7px; +} +.x-btn-wrap-green-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-green-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-green-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-green-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-green-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-green-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-green-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-green-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-green-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-green-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-green-small { + background-image: none; + background-color: #16b603; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, #cbe5f1 -1px 0 0px 0 inset, + #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, #cbe5f1 -1px 0 0px 0 inset, + #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, #cbe5f1 -1px 0 0px 0 inset, + #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-green-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-green-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-green-small { + border-color: #119002; + background-image: none; + background-color: #14a703; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-green-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, #cae2ed -1px 0 0px 0 inset, + #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, #cae2ed -1px 0 0px 0 inset, + #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, #cae2ed -1px 0 0px 0 inset, + #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-green-small, +.x-btn.x-btn-pressed.x-btn-green-small { + border-color: #0e7602; + background-image: none; + background-color: #118902; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-green-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-green-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-green-small { + background-image: none; + background-color: #16b603; +} +.x-keyboard-mode .x-btn-focus .x-btn-green-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-green-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-green-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-green-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-green-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-green-small-bc { + background-image: url(images/btn/btn-green-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-green-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-green-small-mr { + background-image: url(images/btn/btn-green-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-green-small-mc { + background-color: #16b603; +} +.x-btn-over .x-btn-green-small-tl, +.x-btn-over .x-btn-green-small-bl, +.x-btn-over .x-btn-green-small-tr, +.x-btn-over .x-btn-green-small-br, +.x-btn-over .x-btn-green-small-tc, +.x-btn-over .x-btn-green-small-bc { + background-image: url(images/btn/btn-green-small-over-corners.gif); +} +.x-btn-over .x-btn-green-small-ml, +.x-btn-over .x-btn-green-small-mr { + background-image: url(images/btn/btn-green-small-over-sides.gif); +} +.x-btn-over .x-btn-green-small-mc { + background-color: #14a703; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-small-bc { + background-image: url(images/btn/btn-green-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-small-mr { + background-image: url(images/btn/btn-green-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-small-mc { + background-color: #14a703; +} +.x-btn.x-btn-menu-active .x-btn-green-small-tl, +.x-btn.x-btn-menu-active .x-btn-green-small-bl, +.x-btn.x-btn-menu-active .x-btn-green-small-tr, +.x-btn.x-btn-menu-active .x-btn-green-small-br, +.x-btn.x-btn-menu-active .x-btn-green-small-tc, +.x-btn.x-btn-menu-active .x-btn-green-small-bc, +.x-btn.x-btn-pressed .x-btn-green-small-tl, +.x-btn.x-btn-pressed .x-btn-green-small-bl, +.x-btn.x-btn-pressed .x-btn-green-small-tr, +.x-btn.x-btn-pressed .x-btn-green-small-br, +.x-btn.x-btn-pressed .x-btn-green-small-tc, +.x-btn.x-btn-pressed .x-btn-green-small-bc { + background-image: url(images/btn/btn-green-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-green-small-ml, +.x-btn.x-btn-menu-active .x-btn-green-small-mr, +.x-btn.x-btn-pressed .x-btn-green-small-ml, +.x-btn.x-btn-pressed .x-btn-green-small-mr { + background-image: url(images/btn/btn-green-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-green-small-mc, +.x-btn.x-btn-pressed .x-btn-green-small-mc { + background-color: #118902; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-small-bc { + background-image: url(images/btn/btn-green-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-small-mr { + background-image: url(images/btn/btn-green-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-small-mc { + background-color: #118902; +} +.x-btn.x-btn-disabled .x-btn-green-small-tl, +.x-btn.x-btn-disabled .x-btn-green-small-bl, +.x-btn.x-btn-disabled .x-btn-green-small-tr, +.x-btn.x-btn-disabled .x-btn-green-small-br, +.x-btn.x-btn-disabled .x-btn-green-small-tc, +.x-btn.x-btn-disabled .x-btn-green-small-bc { + background-image: url(images/btn/btn-green-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-green-small-ml, +.x-btn.x-btn-disabled .x-btn-green-small-mr { + background-image: url(images/btn/btn-green-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-green-small-mc { + background-color: #16b603; +} +.x-nbr .x-btn-green-small { + background-image: none; +} +.x-btn-disabled.x-btn-green-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-small.x-segmented-button-first .x-btn-green-small-mc { + padding-right: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-small.x-segmented-button-middle .x-btn-green-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-small.x-segmented-button-last .x-btn-green-small-mc { + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-small.x-segmented-button-first .x-btn-green-small-mc { + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-small.x-segmented-button-middle .x-btn-green-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-small.x-segmented-button-last .x-btn-green-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-green-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-green-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-green-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-green-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-green-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-green-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #16b603; +} +.x-btn-green-toolbar-small-mc { + background-color: #16b603; +} +.x-nbr .x-btn-green-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-green-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-green-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-green-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-green-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-green-toolbar-small-br { + background-position: right -5px; +} +.x-btn-green-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-green-toolbar-small-mr { + background-position: right top; +} +.x-btn-green-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-green-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-green-toolbar-small-tr, +.x-btn-green-toolbar-small-br, +.x-btn-green-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-green-toolbar-small-tl, +.x-btn-green-toolbar-small-bl, +.x-btn-green-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-green-toolbar-small-tc { + height: 1px; +} +.x-btn-green-toolbar-small-bc { + height: 1px; +} +.x-btn-green-toolbar-small-tl, +.x-btn-green-toolbar-small-bl, +.x-btn-green-toolbar-small-tr, +.x-btn-green-toolbar-small-br, +.x-btn-green-toolbar-small-tc, +.x-btn-green-toolbar-small-bc, +.x-btn-green-toolbar-small-ml, +.x-btn-green-toolbar-small-mr { + background-image: url(images/btn/btn-green-toolbar-small-corners.gif); +} +.x-btn-green-toolbar-small-ml, +.x-btn-green-toolbar-small-mr { + background-image: url(images/btn/btn-green-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-green-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-green-toolbar-small { + border-color: #139d03; +} +.x-btn-button-green-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-green-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-green-toolbar-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-green-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-green-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-green-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-green-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-green-toolbar-small { + max-width: none; +} +.x-btn-icon-el-green-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-green-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-green-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-green-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-green-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-green-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-green-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-green-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-green-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-green-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-green-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-green-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-green-toolbar-small, +.x-btn-split-bottom > .x-btn-button-green-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-green-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-green-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-green-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-green-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-green-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-green-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-green-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-green-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-green-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-green-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-green-toolbar-small { + background-image: none; + background-color: #16b603; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; +} +.x-btn-green-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-green-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-green-toolbar-small { + border-color: #129702; + background-image: none; + background-color: #15af03; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-green-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-green-toolbar-small, +.x-btn.x-btn-pressed.x-btn-green-toolbar-small { + border-color: #119002; + background-image: none; + background-color: #14a703; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-green-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-green-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-green-toolbar-small { + background-image: none; + background-color: #16b603; +} +.x-keyboard-mode .x-btn-focus .x-btn-green-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-green-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-green-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-green-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-green-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-green-toolbar-small-bc { + background-image: url(images/btn/btn-green-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-green-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-green-toolbar-small-mr { + background-image: url(images/btn/btn-green-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-green-toolbar-small-mc { + background-color: #16b603; +} +.x-btn-over .x-btn-green-toolbar-small-tl, +.x-btn-over .x-btn-green-toolbar-small-bl, +.x-btn-over .x-btn-green-toolbar-small-tr, +.x-btn-over .x-btn-green-toolbar-small-br, +.x-btn-over .x-btn-green-toolbar-small-tc, +.x-btn-over .x-btn-green-toolbar-small-bc { + background-image: url(images/btn/btn-green-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-green-toolbar-small-ml, +.x-btn-over .x-btn-green-toolbar-small-mr { + background-image: url(images/btn/btn-green-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-green-toolbar-small-mc { + background-color: #15af03; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-toolbar-small-bc { + background-image: url(images/btn/btn-green-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-toolbar-small-mr { + background-image: url(images/btn/btn-green-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-green-toolbar-small-mc { + background-color: #15af03; +} +.x-btn.x-btn-menu-active .x-btn-green-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-green-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-green-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-green-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-green-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-green-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-green-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-green-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-green-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-green-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-green-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-green-toolbar-small-bc { + background-image: url(images/btn/btn-green-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-green-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-green-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-green-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-green-toolbar-small-mr { + background-image: url(images/btn/btn-green-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-green-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-green-toolbar-small-mc { + background-color: #14a703; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-toolbar-small-bc { + background-image: url(images/btn/btn-green-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-toolbar-small-mr { + background-image: url(images/btn/btn-green-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-green-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-green-toolbar-small-mc { + background-color: #14a703; +} +.x-btn.x-btn-disabled .x-btn-green-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-green-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-green-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-green-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-green-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-green-toolbar-small-bc { + background-image: url(images/btn/btn-green-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-green-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-green-toolbar-small-mr { + background-image: url(images/btn/btn-green-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-green-toolbar-small-mc { + background-color: #16b603; +} +.x-nbr .x-btn-green-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-green-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-green-toolbar-small.x-segmented-button-first + .x-btn-green-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-green-toolbar-small.x-segmented-button-middle + .x-btn-green-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-green-toolbar-small.x-segmented-button-last + .x-btn-green-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-green-toolbar-small.x-segmented-button-first + .x-btn-green-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-green-toolbar-small.x-segmented-button-middle + .x-btn-green-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-green-toolbar-small.x-segmented-button-last + .x-btn-green-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-green-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-green-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-green-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-green-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-green-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-green-toolbar-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-green-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-blue-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #167abc; +} +.x-btn-blue-small-mc { + background-color: #167abc; +} +.x-nbr .x-btn-blue-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-blue-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-blue-small-tl { + background-position: 0 -2px; +} +.x-btn-blue-small-tr { + background-position: right -3px; +} +.x-btn-blue-small-bl { + background-position: 0 -4px; +} +.x-btn-blue-small-br { + background-position: right -5px; +} +.x-btn-blue-small-ml { + background-position: 0 top; +} +.x-btn-blue-small-mr { + background-position: right top; +} +.x-btn-blue-small-tc { + background-position: 0 0; +} +.x-btn-blue-small-bc { + background-position: 0 -1px; +} +.x-btn-blue-small-tr, +.x-btn-blue-small-br, +.x-btn-blue-small-mr { + padding-right: 1px; +} +.x-btn-blue-small-tl, +.x-btn-blue-small-bl, +.x-btn-blue-small-ml { + padding-left: 1px; +} +.x-btn-blue-small-tc { + height: 1px; +} +.x-btn-blue-small-bc { + height: 1px; +} +.x-btn-blue-small-tl, +.x-btn-blue-small-bl, +.x-btn-blue-small-tr, +.x-btn-blue-small-br, +.x-btn-blue-small-tc, +.x-btn-blue-small-bc, +.x-btn-blue-small-ml, +.x-btn-blue-small-mr { + background-image: url(images/btn/btn-blue-small-corners.gif); +} +.x-btn-blue-small-ml, +.x-btn-blue-small-mr { + background-image: url(images/btn/btn-blue-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-blue-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-blue-small { + border-color: #136ba5; +} +.x-btn-button-blue-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-blue-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-blue-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-blue-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-blue-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-blue-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-blue-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-blue-small { + max-width: none; +} +.x-btn-icon-el-blue-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-blue-small, +.x-btn-icon-right > .x-btn-icon-el-blue-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-blue-small, +.x-btn-icon-bottom > .x-btn-icon-el-blue-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-blue-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-blue-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-blue-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-blue-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-blue-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-blue-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-blue-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-blue-small, +.x-btn-split-bottom > .x-btn-button-blue-small { + padding-bottom: 7px; +} +.x-btn-wrap-blue-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-blue-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-blue-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-blue-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-blue-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-blue-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-blue-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-blue-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-blue-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-blue-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-blue-small { + background-image: none; + background-color: #167abc; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, #cbe5f1 -1px 0 0px 0 inset, + #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, #cbe5f1 -1px 0 0px 0 inset, + #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, #cbe5f1 -1px 0 0px 0 inset, + #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-blue-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-blue-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-blue-small { + border-color: #126398; + background-image: none; + background-color: #1470ad; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-blue-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, #cae2ed -1px 0 0px 0 inset, + #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, #cae2ed -1px 0 0px 0 inset, + #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, #cae2ed -1px 0 0px 0 inset, + #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-blue-small, +.x-btn.x-btn-pressed.x-btn-blue-small { + border-color: #0e507c; + background-image: none; + background-color: #115c8d; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-blue-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-blue-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-blue-small { + background-image: none; + background-color: #167abc; +} +.x-keyboard-mode .x-btn-focus .x-btn-blue-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-blue-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-blue-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-blue-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-blue-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-blue-small-bc { + background-image: url(images/btn/btn-blue-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-blue-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-blue-small-mr { + background-image: url(images/btn/btn-blue-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-blue-small-mc { + background-color: #167abc; +} +.x-btn-over .x-btn-blue-small-tl, +.x-btn-over .x-btn-blue-small-bl, +.x-btn-over .x-btn-blue-small-tr, +.x-btn-over .x-btn-blue-small-br, +.x-btn-over .x-btn-blue-small-tc, +.x-btn-over .x-btn-blue-small-bc { + background-image: url(images/btn/btn-blue-small-over-corners.gif); +} +.x-btn-over .x-btn-blue-small-ml, +.x-btn-over .x-btn-blue-small-mr { + background-image: url(images/btn/btn-blue-small-over-sides.gif); +} +.x-btn-over .x-btn-blue-small-mc { + background-color: #1470ad; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-small-bc { + background-image: url(images/btn/btn-blue-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-small-mr { + background-image: url(images/btn/btn-blue-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-small-mc { + background-color: #1470ad; +} +.x-btn.x-btn-menu-active .x-btn-blue-small-tl, +.x-btn.x-btn-menu-active .x-btn-blue-small-bl, +.x-btn.x-btn-menu-active .x-btn-blue-small-tr, +.x-btn.x-btn-menu-active .x-btn-blue-small-br, +.x-btn.x-btn-menu-active .x-btn-blue-small-tc, +.x-btn.x-btn-menu-active .x-btn-blue-small-bc, +.x-btn.x-btn-pressed .x-btn-blue-small-tl, +.x-btn.x-btn-pressed .x-btn-blue-small-bl, +.x-btn.x-btn-pressed .x-btn-blue-small-tr, +.x-btn.x-btn-pressed .x-btn-blue-small-br, +.x-btn.x-btn-pressed .x-btn-blue-small-tc, +.x-btn.x-btn-pressed .x-btn-blue-small-bc { + background-image: url(images/btn/btn-blue-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-blue-small-ml, +.x-btn.x-btn-menu-active .x-btn-blue-small-mr, +.x-btn.x-btn-pressed .x-btn-blue-small-ml, +.x-btn.x-btn-pressed .x-btn-blue-small-mr { + background-image: url(images/btn/btn-blue-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-blue-small-mc, +.x-btn.x-btn-pressed .x-btn-blue-small-mc { + background-color: #115c8d; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-small-bc { + background-image: url(images/btn/btn-blue-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-small-mr { + background-image: url(images/btn/btn-blue-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-small-mc { + background-color: #115c8d; +} +.x-btn.x-btn-disabled .x-btn-blue-small-tl, +.x-btn.x-btn-disabled .x-btn-blue-small-bl, +.x-btn.x-btn-disabled .x-btn-blue-small-tr, +.x-btn.x-btn-disabled .x-btn-blue-small-br, +.x-btn.x-btn-disabled .x-btn-blue-small-tc, +.x-btn.x-btn-disabled .x-btn-blue-small-bc { + background-image: url(images/btn/btn-blue-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-blue-small-ml, +.x-btn.x-btn-disabled .x-btn-blue-small-mr { + background-image: url(images/btn/btn-blue-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-blue-small-mc { + background-color: #167abc; +} +.x-nbr .x-btn-blue-small { + background-image: none; +} +.x-btn-disabled.x-btn-blue-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-small.x-segmented-button-first .x-btn-blue-small-mc { + padding-right: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-small.x-segmented-button-middle .x-btn-blue-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-small.x-segmented-button-last .x-btn-blue-small-mc { + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-small.x-segmented-button-first .x-btn-blue-small-mc { + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-small.x-segmented-button-middle .x-btn-blue-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-small.x-segmented-button-last .x-btn-blue-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-blue-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-blue-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-blue-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-blue-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-blue-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-blue-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #167abc; +} +.x-btn-blue-toolbar-small-mc { + background-color: #167abc; +} +.x-nbr .x-btn-blue-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-blue-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-blue-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-blue-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-blue-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-blue-toolbar-small-br { + background-position: right -5px; +} +.x-btn-blue-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-blue-toolbar-small-mr { + background-position: right top; +} +.x-btn-blue-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-blue-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-blue-toolbar-small-tr, +.x-btn-blue-toolbar-small-br, +.x-btn-blue-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-blue-toolbar-small-tl, +.x-btn-blue-toolbar-small-bl, +.x-btn-blue-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-blue-toolbar-small-tc { + height: 1px; +} +.x-btn-blue-toolbar-small-bc { + height: 1px; +} +.x-btn-blue-toolbar-small-tl, +.x-btn-blue-toolbar-small-bl, +.x-btn-blue-toolbar-small-tr, +.x-btn-blue-toolbar-small-br, +.x-btn-blue-toolbar-small-tc, +.x-btn-blue-toolbar-small-bc, +.x-btn-blue-toolbar-small-ml, +.x-btn-blue-toolbar-small-mr { + background-image: url(images/btn/btn-blue-toolbar-small-corners.gif); +} +.x-btn-blue-toolbar-small-ml, +.x-btn-blue-toolbar-small-mr { + background-image: url(images/btn/btn-blue-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-blue-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-blue-toolbar-small { + border-color: #136ba5; +} +.x-btn-button-blue-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-blue-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-blue-toolbar-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-blue-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-blue-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-blue-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-blue-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-blue-toolbar-small { + max-width: none; +} +.x-btn-icon-el-blue-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-blue-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-blue-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-blue-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-blue-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-blue-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-blue-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-blue-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-blue-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-blue-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-blue-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-blue-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-blue-toolbar-small, +.x-btn-split-bottom > .x-btn-button-blue-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-blue-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-blue-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-blue-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-blue-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-blue-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-blue-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-blue-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-blue-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-blue-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-blue-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-blue-toolbar-small { + background-image: none; + background-color: #167abc; + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; +} +.x-btn-blue-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-blue-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5aaed4; +} +.x-btn-over.x-btn-blue-toolbar-small { + border-color: #13679f; + background-image: none; + background-color: #1575b4; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-blue-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-blue-toolbar-small, +.x-btn.x-btn-pressed.x-btn-blue-toolbar-small { + border-color: #126398; + background-image: none; + background-color: #1470ad; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-blue-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-blue-toolbar-small { + -webkit-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + -moz-box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; + box-shadow: #5aaed4 0 1px 0px 0 inset, #5aaed4 0 -1px 0px 0 inset, #5aaed4 -1px 0 0px 0 inset, + #5aaed4 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-blue-toolbar-small { + background-image: none; + background-color: #167abc; +} +.x-keyboard-mode .x-btn-focus .x-btn-blue-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-blue-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-blue-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-blue-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-blue-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-blue-toolbar-small-bc { + background-image: url(images/btn/btn-blue-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-blue-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-blue-toolbar-small-mr { + background-image: url(images/btn/btn-blue-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-blue-toolbar-small-mc { + background-color: #167abc; +} +.x-btn-over .x-btn-blue-toolbar-small-tl, +.x-btn-over .x-btn-blue-toolbar-small-bl, +.x-btn-over .x-btn-blue-toolbar-small-tr, +.x-btn-over .x-btn-blue-toolbar-small-br, +.x-btn-over .x-btn-blue-toolbar-small-tc, +.x-btn-over .x-btn-blue-toolbar-small-bc { + background-image: url(images/btn/btn-blue-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-blue-toolbar-small-ml, +.x-btn-over .x-btn-blue-toolbar-small-mr { + background-image: url(images/btn/btn-blue-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-blue-toolbar-small-mc { + background-color: #1575b4; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-toolbar-small-bc { + background-image: url(images/btn/btn-blue-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-toolbar-small-mr { + background-image: url(images/btn/btn-blue-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-blue-toolbar-small-mc { + background-color: #1575b4; +} +.x-btn.x-btn-menu-active .x-btn-blue-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-blue-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-blue-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-blue-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-blue-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-blue-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-blue-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-blue-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-blue-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-blue-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-blue-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-blue-toolbar-small-bc { + background-image: url(images/btn/btn-blue-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-blue-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-blue-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-blue-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-blue-toolbar-small-mr { + background-image: url(images/btn/btn-blue-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-blue-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-blue-toolbar-small-mc { + background-color: #1470ad; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-toolbar-small-bc { + background-image: url(images/btn/btn-blue-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-toolbar-small-mr { + background-image: url(images/btn/btn-blue-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-blue-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-blue-toolbar-small-mc { + background-color: #1470ad; +} +.x-btn.x-btn-disabled .x-btn-blue-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-blue-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-blue-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-blue-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-blue-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-blue-toolbar-small-bc { + background-image: url(images/btn/btn-blue-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-blue-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-blue-toolbar-small-mr { + background-image: url(images/btn/btn-blue-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-blue-toolbar-small-mc { + background-color: #167abc; +} +.x-nbr .x-btn-blue-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-blue-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-blue-toolbar-small.x-segmented-button-first + .x-btn-blue-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-blue-toolbar-small.x-segmented-button-middle + .x-btn-blue-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-blue-toolbar-small.x-segmented-button-last + .x-btn-blue-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-blue-toolbar-small.x-segmented-button-first + .x-btn-blue-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-blue-toolbar-small.x-segmented-button-middle + .x-btn-blue-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-toolbar-small.x-segmented-button-last .x-btn-blue-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-blue-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-blue-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-blue-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-blue-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-blue-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-blue-toolbar-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-blue-toolbar-small:after { + border-width: 1px; + border-color: #5aaed4; +} +.x-btn-header-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 0; + border-style: solid; + background-color: transparent; +} +.x-btn-header-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-header-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-header-small-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-7-7-7-7; +} +.x-btn-header-small-tl { + background-position: 0 0; +} +.x-btn-header-small-tr { + background-position: right 0; +} +.x-btn-header-small-bl { + background-position: 0 0; +} +.x-btn-header-small-br { + background-position: right 0; +} +.x-btn-header-small-ml { + background-position: 0 top; +} +.x-btn-header-small-mr { + background-position: right top; +} +.x-btn-header-small-tc { + background-position: 0 0; +} +.x-btn-header-small-bc { + background-position: 0 0; +} +.x-btn-header-small-tr, +.x-btn-header-small-br, +.x-btn-header-small-mr { + padding-right: 0; +} +.x-btn-header-small-tl, +.x-btn-header-small-bl, +.x-btn-header-small-ml { + padding-left: 0; +} +.x-btn-header-small-tc { + height: 0; +} +.x-btn-header-small-bc { + height: 0; +} +.x-btn-header-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-header-small { + border-color: #31ade5; +} +.x-btn-button-header-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-header-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-header-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; + color: #999; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-header-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-header-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-header-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-header-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-header-small { + max-width: none; +} +.x-btn-icon-el-header-small { + font-size: 16px; + height: 16px; + color: #ffffff; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-header-small, +.x-btn-icon-right > .x-btn-icon-el-header-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-header-small, +.x-btn-icon-bottom > .x-btn-icon-el-header-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-header-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-header-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-header-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-header-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-header-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-header-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-header-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-header-small, +.x-btn-split-bottom > .x-btn-button-header-small { + padding-bottom: 7px; +} +.x-btn-wrap-header-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-header-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-header-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-header-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-header-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-header-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-header-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-header-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-header-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-header-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-header-small { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, #cbe5f1 -1px 0 0px 0 inset, + #cbe5f1 1px 0 0px 0 inset; + -moz-box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, #cbe5f1 -1px 0 0px 0 inset, + #cbe5f1 1px 0 0px 0 inset; + box-shadow: #cbe5f1 0 1px 0px 0 inset, #cbe5f1 0 -1px 0px 0 inset, #cbe5f1 -1px 0 0px 0 inset, + #cbe5f1 1px 0 0px 0 inset; +} +.x-btn-header-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-header-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-header-small { + border-color: #2d9fd2; + background-image: none; + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-header-small { + -webkit-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, #cae2ed -1px 0 0px 0 inset, + #cae2ed 1px 0 0px 0 inset; + -moz-box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, #cae2ed -1px 0 0px 0 inset, + #cae2ed 1px 0 0px 0 inset; + box-shadow: #cae2ed 0 1px 0px 0 inset, #cae2ed 0 -1px 0px 0 inset, #cae2ed -1px 0 0px 0 inset, + #cae2ed 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-header-small, +.x-btn.x-btn-pressed.x-btn-header-small { + border-color: #2582ac; + background-image: none; + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-header-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-header-small { + -webkit-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; + -moz-box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; + box-shadow: #c8dce5 0 1px 0px 0 inset, #c8dce5 0 -1px 0px 0 inset, #c8dce5 -1px 0 0px 0 inset, + #c8dce5 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-header-small { + background-image: none; + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus .x-btn-header-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-header-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-header-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-header-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-header-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-header-small-bc { + background-image: url(images/btn/btn-header-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-header-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-header-small-mr { + background-image: url(images/btn/btn-header-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-header-small-mc { + background-color: transparent; +} +.x-btn-over .x-btn-header-small-tl, +.x-btn-over .x-btn-header-small-bl, +.x-btn-over .x-btn-header-small-tr, +.x-btn-over .x-btn-header-small-br, +.x-btn-over .x-btn-header-small-tc, +.x-btn-over .x-btn-header-small-bc { + background-image: url(images/btn/btn-header-small-over-corners.gif); +} +.x-btn-over .x-btn-header-small-ml, +.x-btn-over .x-btn-header-small-mr { + background-image: url(images/btn/btn-header-small-over-sides.gif); +} +.x-btn-over .x-btn-header-small-mc { + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-header-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-header-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-header-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-header-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-header-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-header-small-bc { + background-image: url(images/btn/btn-header-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-header-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-header-small-mr { + background-image: url(images/btn/btn-header-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-header-small-mc { + background-color: transparent; +} +.x-btn.x-btn-menu-active .x-btn-header-small-tl, +.x-btn.x-btn-menu-active .x-btn-header-small-bl, +.x-btn.x-btn-menu-active .x-btn-header-small-tr, +.x-btn.x-btn-menu-active .x-btn-header-small-br, +.x-btn.x-btn-menu-active .x-btn-header-small-tc, +.x-btn.x-btn-menu-active .x-btn-header-small-bc, +.x-btn.x-btn-pressed .x-btn-header-small-tl, +.x-btn.x-btn-pressed .x-btn-header-small-bl, +.x-btn.x-btn-pressed .x-btn-header-small-tr, +.x-btn.x-btn-pressed .x-btn-header-small-br, +.x-btn.x-btn-pressed .x-btn-header-small-tc, +.x-btn.x-btn-pressed .x-btn-header-small-bc { + background-image: url(images/btn/btn-header-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-header-small-ml, +.x-btn.x-btn-menu-active .x-btn-header-small-mr, +.x-btn.x-btn-pressed .x-btn-header-small-ml, +.x-btn.x-btn-pressed .x-btn-header-small-mr { + background-image: url(images/btn/btn-header-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-header-small-mc, +.x-btn.x-btn-pressed .x-btn-header-small-mc { + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-header-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-header-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-header-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-header-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-header-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-header-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-header-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-header-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-header-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-header-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-header-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-header-small-bc { + background-image: url(images/btn/btn-header-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-header-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-header-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-header-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-header-small-mr { + background-image: url(images/btn/btn-header-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-header-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-header-small-mc { + background-color: transparent; +} +.x-btn.x-btn-disabled .x-btn-header-small-tl, +.x-btn.x-btn-disabled .x-btn-header-small-bl, +.x-btn.x-btn-disabled .x-btn-header-small-tr, +.x-btn.x-btn-disabled .x-btn-header-small-br, +.x-btn.x-btn-disabled .x-btn-header-small-tc, +.x-btn.x-btn-disabled .x-btn-header-small-bc { + background-image: url(images/btn/btn-header-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-header-small-ml, +.x-btn.x-btn-disabled .x-btn-header-small-mr { + background-image: url(images/btn/btn-header-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-header-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-header-small { + background-image: none; +} +.x-btn-disabled.x-btn-header-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-header-small.x-segmented-button-first { + border-right-width: 0 !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-header-small.x-segmented-button-first .x-btn-header-small-mc { + padding-right: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-header-small.x-segmented-button-middle { + border-right-width: 0 !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-header-small.x-segmented-button-middle .x-btn-header-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-header-small.x-segmented-button-last .x-btn-header-small-mc { + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-header-small.x-segmented-button-first { + border-bottom-width: 0 !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-header-small.x-segmented-button-first .x-btn-header-small-mc { + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-header-small.x-segmented-button-middle { + border-bottom-width: 0 !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-header-small.x-segmented-button-middle .x-btn-header-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-header-small.x-segmented-button-last .x-btn-header-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-header-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-header-small:after { + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-header-small.x-segmented-button-first:after { + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-header-small.x-segmented-button-last:after { + right: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-header-small:after { + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-header-small.x-segmented-button-first:after { + top: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-header-small.x-segmented-button-last:after { + bottom: 0; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-header-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-header-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-header-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-header-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-menu-header { + z-index: 0 !important; +} +.x-css-shadow { + box-shadow: none !important; +} +.x-fa { + display: inline-block; + font: normal normal normal 14px/1 "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; +} +.alignRight { + float: right; +} +.boldFont { + font-weight: bold; +} +.auth-dialog .auth-profile-wrap { + background: #5aaed4; + color: #fff; + line-height: 24px; +} +.auth-dialog .auth-profile-wrap .user-name-text { + font-size: 18px; + font-weight: bold; +} +.auth-dialog .auth-profile-wrap .user-post-text { + font-size: 14px; +} +.auth-dialog .auth-profile-wrap .auth-profile-img { + -webkit-border-radius: 50%; + -moz-border-radius: 50%; + -ms-border-radius: 50%; + border-radius: 50%; +} +.auth-dialog .x-form-text-default, +.auth-dialog .x-placeholder-label-default { + padding: 15px; +} +.auth-dialog .register-page-back-button, +.auth-dialog .register-page-back-button .x-frame-mc { + background-color: #fff; + border: none; + padding: 5px 0 0 0; +} +.auth-dialog .register-page-back-button .x-btn-inner-default-small, +.auth-dialog .register-page-back-button .x-frame-mc .x-btn-inner-default-small { + padding: 0; + height: 20px; + color: #5aaed4; +} +.auth-dialog .register-page-back-button .x-btn-inner-default-small:hover, +.auth-dialog .register-page-back-button .x-frame-mc .x-btn-inner-default-small:hover { + text-decoration: underline; +} +.auth-dialog .register-page-back-button.x-btn-pressed.x-btn-default-small, +.auth-dialog .register-page-back-button .x-frame-mc.x-btn-pressed.x-btn-default-small { + background-color: transparent; +} +.auth-dialog .trigger-glyph-noop { + cursor: default; +} +.auth-dialog .x-form-trigger { + text-align: right; + width: 50px; +} +.auth-dialog .password-trigger:before, +.auth-dialog .auth-email-trigger:before, +.auth-dialog .auth-password-trigger:before, +.auth-dialog .auth-envelope-trigger:before { + top: 10px; + left: -18px; + position: relative; + color: #e5e5e5; + font-size: 30px; +} +.auth-dialog .password-trigger.password-trigger:before, +.auth-dialog .password-trigger.auth-password-trigger:before, +.auth-dialog .auth-email-trigger.password-trigger:before, +.auth-dialog .auth-email-trigger.auth-password-trigger:before, +.auth-dialog .auth-password-trigger.password-trigger:before, +.auth-dialog .auth-password-trigger.auth-password-trigger:before, +.auth-dialog .auth-envelope-trigger.password-trigger:before, +.auth-dialog .auth-envelope-trigger.auth-password-trigger:before { + content: "\f023"; +} +.auth-dialog .password-trigger.auth-email-trigger:before, +.auth-dialog .auth-email-trigger.auth-email-trigger:before, +.auth-dialog .auth-password-trigger.auth-email-trigger:before, +.auth-dialog .auth-envelope-trigger.auth-email-trigger:before { + content: "\f007"; +} +.auth-dialog .password-trigger.auth-envelope-trigger:before, +.auth-dialog .auth-email-trigger.auth-envelope-trigger:before, +.auth-dialog .auth-password-trigger.auth-envelope-trigger:before, +.auth-dialog .auth-envelope-trigger.auth-envelope-trigger:before { + content: "\f0e0"; +} +.auth-dialog .seperator { + text-align: center; + color: #a1a1a2; + font-family: "Open Sans"; + display: inline-block; + background: #fff; + position: relative; + z-index: 1; + padding: 0 8px; +} +.auth-dialog .link-forgot-password { + line-height: 32px; + color: #5aaed4; + text-decoration: none; + margin-left: 5px; +} +.auth-dialog .link-forgot-password:hover { + text-decoration: underline; +} +.auth-dialog .x-btn .x-btn-icon-el:before { + right: 10px; + font-size: 24px; + position: absolute; +} +.auth-dialog .auth-facebook-button .x-fa { + color: #fff; + font-size: 24px; + top: 10px; + right: 13px; +} +.auth-dialog .auth-login-button .x-fa, +.auth-dialog .auth-resetpassword-button .x-fa { + font-size: 32px; + right: 11px; + top: 10px; + line-height: 16px; +} +.auth-dialog .auth-create-account-button .x-fa { + color: #fff; + right: 24px; + top: 10px; +} +.auth-dialog .outer-div { + width: 100%; + text-align: center; +} +.auth-dialog .outer-div:after { + content: " "; + width: 100%; + height: 1px; + background-color: #cacaca; + position: absolute; + left: 0; + top: 9px; +} +.auth-locked-window .x-window-body { + background-image: url("images/lock-screen-background.jpg"); + background-size: cover; + background-repeat: repeat; +} +.auth-locked-window.x-window-default { + border: none; + border-radius: 0; + padding: 0; +} +.dashboard-main-chart .x-panel-body-default { + color: #404040; +} +.top-info-container { + color: #4590d3; + font-size: 13px; + font-family: "Open Sans"; +} +.top-info-container .inner { + white-space: nowrap; + width: 100%; + overflow: hidden; + text-overflow: ellipsis; +} +.top-info-container .dashboard-analytics-percentage { + font-size: 14px; +} +.graph-analysis-left .x-progress-bar { + background-color: #458fd2; +} +.quick-graph-panel .x-panel-header { + padding-left: 22px; +} +.quick-graph-panel .x-title-icon { + position: relative; +} +.quick-graph-panel .x-title-icon:before { + position: absolute; + height: 30px; + width: 30px; + top: -7px; + left: -7px; + border-radius: 15px; + background-color: #f1f1f1; + line-height: 30px; + text-align: center; +} +.quick-graph-panel .x-title-text { + padding-left: 8px; +} +.graph-analysis-right { + border-left: 1px solid #ddd; +} +.graph-analysis-right .right-value { + text-align: right; +} +.dashboard-member-grid .x-fa, +.user-grid .x-fa { + height: 20px; + width: 20px; + background: #e9e9e9; + line-height: 20px; + float: left; + margin-right: 10px; +} +.dashboard-member-grid .x-fa:before, +.user-grid .x-fa:before { + display: block; + line-height: 20px; + text-align: center; +} +.dashboard-member-grid .x-fa.fa-close, +.user-grid .x-fa.fa-close { + background-color: #fc8999; + color: #fff; +} +.dashboard-member-grid .x-fa.fa-ban, +.user-grid .x-fa.fa-ban { + background-color: #ffc000; + color: #fff; +} +.dashboard-member-grid .x-fa.x-action-col-icon, +.user-grid .x-fa.x-action-col-icon { + font-size: 13px !important; +} +.overflow-ellipsis { + overflow: hidden; +} +.pie-legend-container { + font-size: 11px; + text-overflow: ellipsis; +} +.pie-legend-container .quick-graph-pie-legend { + height: 15px; + width: 15px; +} +.pie-legend-container .x-autocontainer-innerCt { + padding-left: 10px; + text-overflow: ellipsis; + overflow: hidden; + line-height: 14px; +} +.bottom-indent { + margin-bottom: 16px; +} +.left-aligned-div { + float: left; +} +.right-aligned-div { + float: right; +} +.services-text { + margin: 0 0 10px 5px; + height: 86px; + text-overflow: ellipsis; + overflow: hidden; +} +.services-legend { + min-width: 240px; +} +.services-legend div { + width: 15px; + height: 15px; + float: left; + margin: 1px 5px 0 0; +} +.services-legend span { + font-size: 11px; + width: 33%; + display: inline-block; + text-overflow: ellipsis; + overflow: hidden; +} +.service-finance .x-progress-bar, +.legend-finance { + background-color: #ffc000; +} +.service-research .x-progress-bar, +.legend-research, +.widget-progressbar .x-progress-bar { + background-color: #6aa5db; +} +.service-marketing .x-progress-bar, +.legend-marketing { + background-color: #ee929c; +} +.force-notext-button, +.force-notext-button .x-frame-mc { + background-color: #56b750; + border-color: #56b750 !important; +} +.force-notext-button .x-btn-inner-default-toolbar-small, +.force-notext-button .x-frame-mc .x-btn-inner-default-toolbar-small { + color: #fff; +} +.force-notext-button:hover, +.force-notext-button .x-frame-mc:hover { + background-color: transparent; +} +.force-notext-button:hover .x-btn-inner-default-toolbar-small, +.force-notext-button:hover .x-btn-inner-default-small, +.force-notext-button .x-frame-mc:hover .x-btn-inner-default-toolbar-small, +.force-notext-button .x-frame-mc:hover .x-btn-inner-default-small { + color: #56b750; +} +.force-notext-button:hover .x-btn-icon-el-default-small, +.force-notext-button:hover .x-btn-icon-el-default-toolbar-small, +.force-notext-button .x-frame-mc:hover .x-btn-icon-el-default-small, +.force-notext-button .x-frame-mc:hover .x-btn-icon-el-default-toolbar-small { + color: #56b750; +} +.white-panel { + background: #fff; +} +.x-tool-wrench { + font: 16px/1 FontAwesome; + background: none; +} +.x-tool-wrench:before { + content: "\f0ad"; +} +.email-sender-img { + -webkit-border-radius: 64px; + -moz-border-radius: 64px; + -ms-border-radius: 64px; + border-radius: 64px; + border: 1px solid #eee; +} +.single-mail-email-subject { + line-height: 1.7em; +} +.single-mail-email-subject .user-name { + font-size: 16px; +} +.single-mail-email-subject .user-info { + font-size: 22px; + max-width: 95%; + text-overflow: ellipsis; + overflow: hidden; + white-space: nowrap; +} +.mail-body { + font-size: 14px; + line-height: 1.6em; + padding-bottom: 14px; + border-bottom: 1px solid #eee; +} +.single-mail-top-toolbar { + background-color: #fff; + border-bottom: 1px solid #eee !important; +} +.single-mail-top-toolbar .x-btn-inner-default-toolbar-small { + color: #404040; +} +.single-mail-top-toolbar a:first-child { + left: 2px !important; +} +.single-mail-attachment { + border: 1px solid #eee; + border-left-width: 0; + border-right-width: 0; + margin-right: 15px; + width: 100px; + height: 100px; +} +.single-mail-action-button .email-compose-save-button, +.single-mail-action-button .email-compose-save-button .x-frame-mc { + background-color: #9da6a3; + border-color: #9da6a3 !important; +} +.single-mail-action-button .email-compose-save-button .x-btn-inner-default-toolbar-small, +.single-mail-action-button .email-compose-save-button .x-frame-mc .x-btn-inner-default-toolbar-small { + color: #fff; +} +.single-mail-action-button .email-compose-save-button:hover, +.single-mail-action-button .email-compose-save-button .x-frame-mc:hover { + background-color: transparent; +} +.single-mail-action-button .email-compose-save-button:hover .x-btn-inner-default-toolbar-small, +.single-mail-action-button .email-compose-save-button:hover .x-btn-inner-default-small, +.single-mail-action-button .email-compose-save-button .x-frame-mc:hover .x-btn-inner-default-toolbar-small, +.single-mail-action-button .email-compose-save-button .x-frame-mc:hover .x-btn-inner-default-small { + color: #9da6a3; +} +.single-mail-action-button .email-compose-save-button:hover .x-btn-icon-el-default-small, +.single-mail-action-button .email-compose-save-button:hover .x-btn-icon-el-default-toolbar-small, +.single-mail-action-button .email-compose-save-button .x-frame-mc:hover .x-btn-icon-el-default-small, +.single-mail-action-button .email-compose-save-button .x-frame-mc:hover .x-btn-icon-el-default-toolbar-small { + color: #9da6a3; +} +.single-mail-action-button .email-compose-send-button, +.single-mail-action-button .email-compose-send-button .x-frame-mc { + background-color: #56b750; + border-color: #56b750 !important; +} +.single-mail-action-button .email-compose-send-button .x-btn-inner-default-toolbar-small, +.single-mail-action-button .email-compose-send-button .x-frame-mc .x-btn-inner-default-toolbar-small { + color: #fff; +} +.single-mail-action-button .email-compose-send-button:hover, +.single-mail-action-button .email-compose-send-button .x-frame-mc:hover { + background-color: transparent; +} +.single-mail-action-button .email-compose-send-button:hover .x-btn-inner-default-toolbar-small, +.single-mail-action-button .email-compose-send-button:hover .x-btn-inner-default-small, +.single-mail-action-button .email-compose-send-button .x-frame-mc:hover .x-btn-inner-default-toolbar-small, +.single-mail-action-button .email-compose-send-button .x-frame-mc:hover .x-btn-inner-default-small { + color: #56b750; +} +.single-mail-action-button .email-compose-send-button:hover .x-btn-icon-el-default-small, +.single-mail-action-button .email-compose-send-button:hover .x-btn-icon-el-default-toolbar-small, +.single-mail-action-button .email-compose-send-button .x-frame-mc:hover .x-btn-icon-el-default-small, +.single-mail-action-button .email-compose-send-button .x-frame-mc:hover .x-btn-icon-el-default-toolbar-small { + color: #56b750; +} +.attachment-container { + margin-top: 16px; +} +.menu-item-common, +.navigation-email .x-menu-item.online-user .x-menu-item-link:after, +.navigation-email .x-menu-item.offline-user .x-menu-item-link:after, +.navigation-email .x-menu-item .x-menu-item-link:after { + padding-right: 20px; + position: absolute; + font-family: FontAwesome; + right: 0; +} +.navigation-email { + -webkit-box-shadow: 0, 1px, 2px, 0, rgba(0, 0, 0, 0.2); + -moz-box-shadow: 0, 1px, 2px, 0, rgba(0, 0, 0, 0.2); + -ms-box-shadow: 0, 1px, 2px, 0, rgba(0, 0, 0, 0.2); + box-shadow: 0, 1px, 2px, 0, rgba(0, 0, 0, 0.2); +} +.navigation-email.x-menu-default { + border-width: 0; +} +.navigation-email .x-menu-header { + line-height: 20px; + background-color: #fff; + padding: 20px 15px; + border-bottom: 1px solid #ccc !important; +} +.navigation-email .x-menu-header .x-title-icon-wrap { + width: 40px; + padding-right: 28px; + text-align: left; +} +.navigation-email .x-menu-header .x-title-text { + font-size: 16px; +} +.navigation-email .x-menu-item-icon-default { + padding-top: 10px; + padding-left: 12px; + font-size: 16px; + line-height: 24px; +} +.navigation-email .x-menu-item { + line-height: 50px; +} +.navigation-email .x-menu-item .x-menu-item-text-default.x-menu-item-indent-no-separator { + margin-left: 56px; +} +.navigation-email .x-menu-item.online-user .x-menu-item-text-default.x-menu-item-indent-no-separator { + margin-left: 18px; +} +.navigation-email .x-menu-item.online-user .x-menu-item-link:after { + color: #86c747; + content: "\f111"; +} +.navigation-email .x-menu-item.online-user.x-menu-item-active .x-menu-item-link:after { + color: white; +} +.navigation-email .x-menu-item.offline-user .x-menu-item-link:after { + color: #9e9f9f; + content: "\f111"; +} +.navigation-email .x-menu-item.offline-user .x-menu-item-text-default.x-menu-item-indent-no-separator { + margin-left: 20px; +} +.navigation-email .x-menu-item .x-menu-item-link:after { + color: #858585; + content: "\f105"; +} +.email-main-wrap .x-menu-item-default.x-menu-item-active { + background-color: #88bf4c; +} +.email-main-wrap .x-menu-item-default.x-menu-item-active .fa, +.email-main-wrap .x-menu-item-default.x-menu-item-active .x-menu-item-link:after, +.email-main-wrap .x-menu-item-default.x-menu-item-active .x-menu-item.offline-user .x-menu-item-link:after { + color: #fff; +} +.email-inbox-panel .fa-heart:before { + color: #facc6e; +} +.email-inbox-panel .fa-heart-o:before { + color: #b2b2b2; +} +.email-inbox-panel .x-grid-body { + border-width: 1px; +} +.email-inbox-panel .x-grid-cell-special { + border-right-width: 0; +} +.wizards .x-panel { + background: #fff; +} +.wizardthree .wizardprogressbar { + background-color: #9cc96b; +} +.x-btn-wizard-blue-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 0; + border-style: solid; + background-color: transparent; +} +.x-btn-wizard-blue-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-wizard-blue-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-wizard-blue-small-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-7-7-7-7; +} +.x-btn-wizard-blue-small-tl { + background-position: 0 0; +} +.x-btn-wizard-blue-small-tr { + background-position: right 0; +} +.x-btn-wizard-blue-small-bl { + background-position: 0 0; +} +.x-btn-wizard-blue-small-br { + background-position: right 0; +} +.x-btn-wizard-blue-small-ml { + background-position: 0 top; +} +.x-btn-wizard-blue-small-mr { + background-position: right top; +} +.x-btn-wizard-blue-small-tc { + background-position: 0 0; +} +.x-btn-wizard-blue-small-bc { + background-position: 0 0; +} +.x-btn-wizard-blue-small-tr, +.x-btn-wizard-blue-small-br, +.x-btn-wizard-blue-small-mr { + padding-right: 0; +} +.x-btn-wizard-blue-small-tl, +.x-btn-wizard-blue-small-bl, +.x-btn-wizard-blue-small-ml { + padding-left: 0; +} +.x-btn-wizard-blue-small-tc { + height: 0; +} +.x-btn-wizard-blue-small-bc { + height: 0; +} +.x-btn-wizard-blue-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-wizard-blue-small { + border-color: #31ade5; +} +.x-btn-button-wizard-blue-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-wizard-blue-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-wizard-blue-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-wizard-blue-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-wizard-blue-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-wizard-blue-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-wizard-blue-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-wizard-blue-small { + max-width: none; +} +.x-btn-icon-el-wizard-blue-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-wizard-blue-small, +.x-btn-icon-right > .x-btn-icon-el-wizard-blue-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-wizard-blue-small, +.x-btn-icon-bottom > .x-btn-icon-el-wizard-blue-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-wizard-blue-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-wizard-blue-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-wizard-blue-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-wizard-blue-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-wizard-blue-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-wizard-blue-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-wizard-blue-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-wizard-blue-small, +.x-btn-split-bottom > .x-btn-button-wizard-blue-small { + padding-bottom: 7px; +} +.x-btn-wrap-wizard-blue-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-wizard-blue-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-wizard-blue-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-wizard-blue-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-wizard-blue-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-wizard-blue-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-wizard-blue-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-wizard-blue-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-wizard-blue-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-wizard-blue-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-wizard-blue-small { + background-image: none; + background-color: transparent; +} +.x-btn-wizard-blue-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-wizard-blue-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-wizard-blue-small { + border-color: #2d9fd2; + background-image: none; + background-color: transparent; +} +.x-btn.x-btn-menu-active.x-btn-wizard-blue-small, +.x-btn.x-btn-pressed.x-btn-wizard-blue-small { + border-color: #2582ac; + background-image: none; + background-color: transparent; +} +.x-btn.x-btn-menu-active.x-btn-wizard-blue-small .x-btn-inner, +.x-btn.x-btn-pressed.x-btn-wizard-blue-small .x-btn-inner { + color: #579ddb; +} +.x-btn.x-btn-disabled.x-btn-wizard-blue-small { + background-image: none; + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus .x-btn-wizard-blue-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-blue-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-blue-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-blue-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-blue-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-blue-small-bc { + background-image: url(images/btn/btn-wizard-blue-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-wizard-blue-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-blue-small-mr { + background-image: url(images/btn/btn-wizard-blue-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-wizard-blue-small-mc { + background-color: transparent; +} +.x-btn-over .x-btn-wizard-blue-small-tl, +.x-btn-over .x-btn-wizard-blue-small-bl, +.x-btn-over .x-btn-wizard-blue-small-tr, +.x-btn-over .x-btn-wizard-blue-small-br, +.x-btn-over .x-btn-wizard-blue-small-tc, +.x-btn-over .x-btn-wizard-blue-small-bc { + background-image: url(images/btn/btn-wizard-blue-small-over-corners.gif); +} +.x-btn-over .x-btn-wizard-blue-small-ml, +.x-btn-over .x-btn-wizard-blue-small-mr { + background-image: url(images/btn/btn-wizard-blue-small-over-sides.gif); +} +.x-btn-over .x-btn-wizard-blue-small-mc { + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-blue-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-blue-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-blue-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-blue-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-blue-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-blue-small-bc { + background-image: url(images/btn/btn-wizard-blue-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-blue-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-blue-small-mr { + background-image: url(images/btn/btn-wizard-blue-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-blue-small-mc { + background-color: transparent; +} +.x-btn.x-btn-menu-active .x-btn-wizard-blue-small-tl, +.x-btn.x-btn-menu-active .x-btn-wizard-blue-small-bl, +.x-btn.x-btn-menu-active .x-btn-wizard-blue-small-tr, +.x-btn.x-btn-menu-active .x-btn-wizard-blue-small-br, +.x-btn.x-btn-menu-active .x-btn-wizard-blue-small-tc, +.x-btn.x-btn-menu-active .x-btn-wizard-blue-small-bc, +.x-btn.x-btn-pressed .x-btn-wizard-blue-small-tl, +.x-btn.x-btn-pressed .x-btn-wizard-blue-small-bl, +.x-btn.x-btn-pressed .x-btn-wizard-blue-small-tr, +.x-btn.x-btn-pressed .x-btn-wizard-blue-small-br, +.x-btn.x-btn-pressed .x-btn-wizard-blue-small-tc, +.x-btn.x-btn-pressed .x-btn-wizard-blue-small-bc { + background-image: url(images/btn/btn-wizard-blue-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-wizard-blue-small-ml, +.x-btn.x-btn-menu-active .x-btn-wizard-blue-small-mr, +.x-btn.x-btn-pressed .x-btn-wizard-blue-small-ml, +.x-btn.x-btn-pressed .x-btn-wizard-blue-small-mr { + background-image: url(images/btn/btn-wizard-blue-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-wizard-blue-small-mc, +.x-btn.x-btn-pressed .x-btn-wizard-blue-small-mc { + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-blue-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-blue-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-blue-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-blue-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-blue-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-blue-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-blue-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-blue-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-blue-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-blue-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-blue-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-blue-small-bc { + background-image: url(images/btn/btn-wizard-blue-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-blue-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-blue-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-blue-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-blue-small-mr { + background-image: url(images/btn/btn-wizard-blue-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-blue-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-blue-small-mc { + background-color: transparent; +} +.x-btn.x-btn-disabled .x-btn-wizard-blue-small-tl, +.x-btn.x-btn-disabled .x-btn-wizard-blue-small-bl, +.x-btn.x-btn-disabled .x-btn-wizard-blue-small-tr, +.x-btn.x-btn-disabled .x-btn-wizard-blue-small-br, +.x-btn.x-btn-disabled .x-btn-wizard-blue-small-tc, +.x-btn.x-btn-disabled .x-btn-wizard-blue-small-bc { + background-image: url(images/btn/btn-wizard-blue-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-wizard-blue-small-ml, +.x-btn.x-btn-disabled .x-btn-wizard-blue-small-mr { + background-image: url(images/btn/btn-wizard-blue-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-wizard-blue-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-wizard-blue-small { + background-image: none; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-blue-small.x-segmented-button-first { + border-right-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-wizard-blue-small.x-segmented-button-first + .x-btn-wizard-blue-small-mc { + padding-right: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-blue-small.x-segmented-button-middle { + border-right-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-wizard-blue-small.x-segmented-button-middle + .x-btn-wizard-blue-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-blue-small.x-segmented-button-last .x-btn-wizard-blue-small-mc { + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-blue-small.x-segmented-button-first { + border-bottom-width: 0 !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-blue-small.x-segmented-button-first .x-btn-wizard-blue-small-mc { + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-blue-small.x-segmented-button-middle { + border-bottom-width: 0 !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-blue-small.x-segmented-button-middle .x-btn-wizard-blue-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-blue-small.x-segmented-button-last .x-btn-wizard-blue-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-wizard-blue-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-blue-small:after { + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-blue-small.x-segmented-button-first:after { + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-blue-small.x-segmented-button-last:after { + right: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-blue-small:after { + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-blue-small.x-segmented-button-first:after { + top: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-blue-small.x-segmented-button-last:after { + bottom: 0; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-wizard-blue-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-wizard-blue-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-wizard-blue-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-wizard-blue-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-wizard-soft-purple-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 0; + border-style: solid; + background-color: transparent; +} +.x-btn-wizard-soft-purple-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-wizard-soft-purple-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-wizard-soft-purple-small-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-7-7-7-7; +} +.x-btn-wizard-soft-purple-small-tl { + background-position: 0 0; +} +.x-btn-wizard-soft-purple-small-tr { + background-position: right 0; +} +.x-btn-wizard-soft-purple-small-bl { + background-position: 0 0; +} +.x-btn-wizard-soft-purple-small-br { + background-position: right 0; +} +.x-btn-wizard-soft-purple-small-ml { + background-position: 0 top; +} +.x-btn-wizard-soft-purple-small-mr { + background-position: right top; +} +.x-btn-wizard-soft-purple-small-tc { + background-position: 0 0; +} +.x-btn-wizard-soft-purple-small-bc { + background-position: 0 0; +} +.x-btn-wizard-soft-purple-small-tr, +.x-btn-wizard-soft-purple-small-br, +.x-btn-wizard-soft-purple-small-mr { + padding-right: 0; +} +.x-btn-wizard-soft-purple-small-tl, +.x-btn-wizard-soft-purple-small-bl, +.x-btn-wizard-soft-purple-small-ml { + padding-left: 0; +} +.x-btn-wizard-soft-purple-small-tc { + height: 0; +} +.x-btn-wizard-soft-purple-small-bc { + height: 0; +} +.x-btn-wizard-soft-purple-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-wizard-soft-purple-small { + border-color: #31ade5; +} +.x-btn-button-wizard-soft-purple-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-wizard-soft-purple-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-wizard-soft-purple-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-wizard-soft-purple-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-wizard-soft-purple-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-wizard-soft-purple-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-wizard-soft-purple-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-wizard-soft-purple-small { + max-width: none; +} +.x-btn-icon-el-wizard-soft-purple-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-wizard-soft-purple-small, +.x-btn-icon-right > .x-btn-icon-el-wizard-soft-purple-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-wizard-soft-purple-small, +.x-btn-icon-bottom > .x-btn-icon-el-wizard-soft-purple-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-wizard-soft-purple-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-wizard-soft-purple-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-wizard-soft-purple-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-wizard-soft-purple-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-wizard-soft-purple-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-wizard-soft-purple-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-wizard-soft-purple-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-wizard-soft-purple-small, +.x-btn-split-bottom > .x-btn-button-wizard-soft-purple-small { + padding-bottom: 7px; +} +.x-btn-wrap-wizard-soft-purple-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-wizard-soft-purple-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-wizard-soft-purple-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-wizard-soft-purple-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-wizard-soft-purple-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-wizard-soft-purple-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-wizard-soft-purple-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-wizard-soft-purple-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-wizard-soft-purple-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-wizard-soft-purple-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-wizard-soft-purple-small { + background-image: none; + background-color: transparent; +} +.x-btn-wizard-soft-purple-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-wizard-soft-purple-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-wizard-soft-purple-small { + border-color: #2d9fd2; + background-image: none; + background-color: transparent; +} +.x-btn.x-btn-menu-active.x-btn-wizard-soft-purple-small, +.x-btn.x-btn-pressed.x-btn-wizard-soft-purple-small { + border-color: #2582ac; + background-image: none; + background-color: #925e8b; +} +.x-btn.x-btn-menu-active.x-btn-wizard-soft-purple-small .x-btn-inner, +.x-btn.x-btn-pressed.x-btn-wizard-soft-purple-small .x-btn-inner { + color: #fff; +} +.x-btn.x-btn-disabled.x-btn-wizard-soft-purple-small { + background-image: none; + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-purple-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-purple-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-purple-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-purple-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-purple-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-purple-small-bc { + background-image: url(images/btn/btn-wizard-soft-purple-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-purple-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-purple-small-mr { + background-image: url(images/btn/btn-wizard-soft-purple-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-purple-small-mc { + background-color: transparent; +} +.x-btn-over .x-btn-wizard-soft-purple-small-tl, +.x-btn-over .x-btn-wizard-soft-purple-small-bl, +.x-btn-over .x-btn-wizard-soft-purple-small-tr, +.x-btn-over .x-btn-wizard-soft-purple-small-br, +.x-btn-over .x-btn-wizard-soft-purple-small-tc, +.x-btn-over .x-btn-wizard-soft-purple-small-bc { + background-image: url(images/btn/btn-wizard-soft-purple-small-over-corners.gif); +} +.x-btn-over .x-btn-wizard-soft-purple-small-ml, +.x-btn-over .x-btn-wizard-soft-purple-small-mr { + background-image: url(images/btn/btn-wizard-soft-purple-small-over-sides.gif); +} +.x-btn-over .x-btn-wizard-soft-purple-small-mc { + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-purple-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-purple-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-purple-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-purple-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-purple-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-purple-small-bc { + background-image: url(images/btn/btn-wizard-soft-purple-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-purple-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-purple-small-mr { + background-image: url(images/btn/btn-wizard-soft-purple-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-purple-small-mc { + background-color: transparent; +} +.x-btn.x-btn-menu-active .x-btn-wizard-soft-purple-small-tl, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-purple-small-bl, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-purple-small-tr, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-purple-small-br, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-purple-small-tc, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-purple-small-bc, +.x-btn.x-btn-pressed .x-btn-wizard-soft-purple-small-tl, +.x-btn.x-btn-pressed .x-btn-wizard-soft-purple-small-bl, +.x-btn.x-btn-pressed .x-btn-wizard-soft-purple-small-tr, +.x-btn.x-btn-pressed .x-btn-wizard-soft-purple-small-br, +.x-btn.x-btn-pressed .x-btn-wizard-soft-purple-small-tc, +.x-btn.x-btn-pressed .x-btn-wizard-soft-purple-small-bc { + background-image: url(images/btn/btn-wizard-soft-purple-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-wizard-soft-purple-small-ml, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-purple-small-mr, +.x-btn.x-btn-pressed .x-btn-wizard-soft-purple-small-ml, +.x-btn.x-btn-pressed .x-btn-wizard-soft-purple-small-mr { + background-image: url(images/btn/btn-wizard-soft-purple-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-wizard-soft-purple-small-mc, +.x-btn.x-btn-pressed .x-btn-wizard-soft-purple-small-mc { + background-color: #925e8b; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-purple-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-purple-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-purple-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-purple-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-purple-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-purple-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-purple-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-purple-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-purple-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-purple-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-purple-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-purple-small-bc { + background-image: url(images/btn/btn-wizard-soft-purple-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-purple-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-purple-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-purple-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-purple-small-mr { + background-image: url(images/btn/btn-wizard-soft-purple-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-purple-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-purple-small-mc { + background-color: #925e8b; +} +.x-btn.x-btn-disabled .x-btn-wizard-soft-purple-small-tl, +.x-btn.x-btn-disabled .x-btn-wizard-soft-purple-small-bl, +.x-btn.x-btn-disabled .x-btn-wizard-soft-purple-small-tr, +.x-btn.x-btn-disabled .x-btn-wizard-soft-purple-small-br, +.x-btn.x-btn-disabled .x-btn-wizard-soft-purple-small-tc, +.x-btn.x-btn-disabled .x-btn-wizard-soft-purple-small-bc { + background-image: url(images/btn/btn-wizard-soft-purple-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-wizard-soft-purple-small-ml, +.x-btn.x-btn-disabled .x-btn-wizard-soft-purple-small-mr { + background-image: url(images/btn/btn-wizard-soft-purple-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-wizard-soft-purple-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-wizard-soft-purple-small { + background-image: none; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-purple-small.x-segmented-button-first { + border-right-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-wizard-soft-purple-small.x-segmented-button-first + .x-btn-wizard-soft-purple-small-mc { + padding-right: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-purple-small.x-segmented-button-middle { + border-right-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-wizard-soft-purple-small.x-segmented-button-middle + .x-btn-wizard-soft-purple-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-wizard-soft-purple-small.x-segmented-button-last + .x-btn-wizard-soft-purple-small-mc { + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-purple-small.x-segmented-button-first { + border-bottom-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-wizard-soft-purple-small.x-segmented-button-first + .x-btn-wizard-soft-purple-small-mc { + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-purple-small.x-segmented-button-middle { + border-bottom-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-wizard-soft-purple-small.x-segmented-button-middle + .x-btn-wizard-soft-purple-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-wizard-soft-purple-small.x-segmented-button-last + .x-btn-wizard-soft-purple-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-wizard-soft-purple-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-purple-small:after { + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-purple-small.x-segmented-button-first:after { + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-purple-small.x-segmented-button-last:after { + right: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-purple-small:after { + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-purple-small.x-segmented-button-first:after { + top: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-purple-small.x-segmented-button-last:after { + bottom: 0; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-wizard-soft-purple-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-wizard-soft-purple-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-wizard-soft-purple-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-wizard-soft-purple-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-wizard-soft-green-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 0; + border-style: solid; + background-color: transparent; +} +.x-btn-wizard-soft-green-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-wizard-soft-green-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-wizard-soft-green-small-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-7-7-7-7; +} +.x-btn-wizard-soft-green-small-tl { + background-position: 0 0; +} +.x-btn-wizard-soft-green-small-tr { + background-position: right 0; +} +.x-btn-wizard-soft-green-small-bl { + background-position: 0 0; +} +.x-btn-wizard-soft-green-small-br { + background-position: right 0; +} +.x-btn-wizard-soft-green-small-ml { + background-position: 0 top; +} +.x-btn-wizard-soft-green-small-mr { + background-position: right top; +} +.x-btn-wizard-soft-green-small-tc { + background-position: 0 0; +} +.x-btn-wizard-soft-green-small-bc { + background-position: 0 0; +} +.x-btn-wizard-soft-green-small-tr, +.x-btn-wizard-soft-green-small-br, +.x-btn-wizard-soft-green-small-mr { + padding-right: 0; +} +.x-btn-wizard-soft-green-small-tl, +.x-btn-wizard-soft-green-small-bl, +.x-btn-wizard-soft-green-small-ml { + padding-left: 0; +} +.x-btn-wizard-soft-green-small-tc { + height: 0; +} +.x-btn-wizard-soft-green-small-bc { + height: 0; +} +.x-btn-wizard-soft-green-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-wizard-soft-green-small { + border-color: #31ade5; +} +.x-btn-button-wizard-soft-green-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-wizard-soft-green-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-wizard-soft-green-small { + font: 500 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, sans-serif; + color: #fff; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-wizard-soft-green-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-wizard-soft-green-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-wizard-soft-green-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-wizard-soft-green-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-wizard-soft-green-small { + max-width: none; +} +.x-btn-icon-el-wizard-soft-green-small { + font-size: 16px; + height: 16px; + color: #fff; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-wizard-soft-green-small, +.x-btn-icon-right > .x-btn-icon-el-wizard-soft-green-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-wizard-soft-green-small, +.x-btn-icon-bottom > .x-btn-icon-el-wizard-soft-green-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-wizard-soft-green-small.x-btn-glyph { + color: #fff; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-wizard-soft-green-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-wizard-soft-green-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-wizard-soft-green-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-wizard-soft-green-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-wizard-soft-green-small { + padding-right: 8px; +} +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-wizard-soft-green-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-wizard-soft-green-small, +.x-btn-split-bottom > .x-btn-button-wizard-soft-green-small { + padding-bottom: 7px; +} +.x-btn-wrap-wizard-soft-green-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-wizard-soft-green-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-wizard-soft-green-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-wizard-soft-green-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-wizard-soft-green-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-wizard-soft-green-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-wizard-soft-green-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-wizard-soft-green-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-wizard-soft-green-small { + padding-right: 8px; +} +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-wizard-soft-green-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-wizard-soft-green-small { + background-image: none; + background-color: transparent; +} +.x-btn-wizard-soft-green-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-wizard-soft-green-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #cbe5f1; +} +.x-btn-over.x-btn-wizard-soft-green-small { + border-color: #2d9fd2; + background-image: none; + background-color: transparent; +} +.x-btn.x-btn-menu-active.x-btn-wizard-soft-green-small, +.x-btn.x-btn-pressed.x-btn-wizard-soft-green-small { + border-color: #2582ac; + background-image: none; + background-color: transparent; +} +.x-btn.x-btn-menu-active.x-btn-wizard-soft-green-small .x-btn-inner, +.x-btn.x-btn-pressed.x-btn-wizard-soft-green-small .x-btn-inner { + color: #404040; +} +.x-btn.x-btn-disabled.x-btn-wizard-soft-green-small { + background-image: none; + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-green-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-green-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-green-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-green-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-green-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-green-small-bc { + background-image: url(images/btn/btn-wizard-soft-green-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-green-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-green-small-mr { + background-image: url(images/btn/btn-wizard-soft-green-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-wizard-soft-green-small-mc { + background-color: transparent; +} +.x-btn-over .x-btn-wizard-soft-green-small-tl, +.x-btn-over .x-btn-wizard-soft-green-small-bl, +.x-btn-over .x-btn-wizard-soft-green-small-tr, +.x-btn-over .x-btn-wizard-soft-green-small-br, +.x-btn-over .x-btn-wizard-soft-green-small-tc, +.x-btn-over .x-btn-wizard-soft-green-small-bc { + background-image: url(images/btn/btn-wizard-soft-green-small-over-corners.gif); +} +.x-btn-over .x-btn-wizard-soft-green-small-ml, +.x-btn-over .x-btn-wizard-soft-green-small-mr { + background-image: url(images/btn/btn-wizard-soft-green-small-over-sides.gif); +} +.x-btn-over .x-btn-wizard-soft-green-small-mc { + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-green-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-green-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-green-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-green-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-green-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-green-small-bc { + background-image: url(images/btn/btn-wizard-soft-green-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-green-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-green-small-mr { + background-image: url(images/btn/btn-wizard-soft-green-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-wizard-soft-green-small-mc { + background-color: transparent; +} +.x-btn.x-btn-menu-active .x-btn-wizard-soft-green-small-tl, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-green-small-bl, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-green-small-tr, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-green-small-br, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-green-small-tc, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-green-small-bc, +.x-btn.x-btn-pressed .x-btn-wizard-soft-green-small-tl, +.x-btn.x-btn-pressed .x-btn-wizard-soft-green-small-bl, +.x-btn.x-btn-pressed .x-btn-wizard-soft-green-small-tr, +.x-btn.x-btn-pressed .x-btn-wizard-soft-green-small-br, +.x-btn.x-btn-pressed .x-btn-wizard-soft-green-small-tc, +.x-btn.x-btn-pressed .x-btn-wizard-soft-green-small-bc { + background-image: url(images/btn/btn-wizard-soft-green-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-wizard-soft-green-small-ml, +.x-btn.x-btn-menu-active .x-btn-wizard-soft-green-small-mr, +.x-btn.x-btn-pressed .x-btn-wizard-soft-green-small-ml, +.x-btn.x-btn-pressed .x-btn-wizard-soft-green-small-mr { + background-image: url(images/btn/btn-wizard-soft-green-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-wizard-soft-green-small-mc, +.x-btn.x-btn-pressed .x-btn-wizard-soft-green-small-mc { + background-color: transparent; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-green-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-green-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-green-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-green-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-green-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-green-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-green-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-green-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-green-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-green-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-green-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-green-small-bc { + background-image: url(images/btn/btn-wizard-soft-green-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-green-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-green-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-green-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-green-small-mr { + background-image: url(images/btn/btn-wizard-soft-green-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-wizard-soft-green-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-wizard-soft-green-small-mc { + background-color: transparent; +} +.x-btn.x-btn-disabled .x-btn-wizard-soft-green-small-tl, +.x-btn.x-btn-disabled .x-btn-wizard-soft-green-small-bl, +.x-btn.x-btn-disabled .x-btn-wizard-soft-green-small-tr, +.x-btn.x-btn-disabled .x-btn-wizard-soft-green-small-br, +.x-btn.x-btn-disabled .x-btn-wizard-soft-green-small-tc, +.x-btn.x-btn-disabled .x-btn-wizard-soft-green-small-bc { + background-image: url(images/btn/btn-wizard-soft-green-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-wizard-soft-green-small-ml, +.x-btn.x-btn-disabled .x-btn-wizard-soft-green-small-mr { + background-image: url(images/btn/btn-wizard-soft-green-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-wizard-soft-green-small-mc { + background-color: transparent; +} +.x-nbr .x-btn-wizard-soft-green-small { + background-image: none; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-green-small.x-segmented-button-first { + border-right-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-wizard-soft-green-small.x-segmented-button-first + .x-btn-wizard-soft-green-small-mc { + padding-right: 7px !important; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-green-small.x-segmented-button-middle { + border-right-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-wizard-soft-green-small.x-segmented-button-middle + .x-btn-wizard-soft-green-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-wizard-soft-green-small.x-segmented-button-last + .x-btn-wizard-soft-green-small-mc { + padding-left: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-green-small.x-segmented-button-first { + border-bottom-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-wizard-soft-green-small.x-segmented-button-first + .x-btn-wizard-soft-green-small-mc { + padding-bottom: 7px !important; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-green-small.x-segmented-button-middle { + border-bottom-width: 0 !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-wizard-soft-green-small.x-segmented-button-middle + .x-btn-wizard-soft-green-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-wizard-soft-green-small.x-segmented-button-last + .x-btn-wizard-soft-green-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-wizard-soft-green-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-green-small:after { + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-green-small.x-segmented-button-first:after { + left: 0; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-wizard-soft-green-small.x-segmented-button-last:after { + right: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-green-small:after { + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-green-small.x-segmented-button-first:after { + top: 0; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-wizard-soft-green-small.x-segmented-button-last:after { + bottom: 0; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-wizard-soft-green-small:after { + border-width: 1px; + border-color: #cbe5f1; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-wizard-soft-green-small:after { + border-width: 1px; + border-color: #cae2ed; +} +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-wizard-soft-green-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-wizard-soft-green-small:after { + border-width: 1px; + border-color: #c8dce5; +} +.x-btn-pressed .x-btn-icon-el-wizard-blue-small { + color: #579ddb; +} +.x-btn-pressed.x-btn-disabled.x-btn-wizard-soft-purple-small, +.x-btn-pressed.x-btn-disabled .x-btn-wizard-soft-purple-small-mc { + background-color: #925e8b; +} +.x-btn-pressed .x-btn-icon-el-wizard-soft-purple-small { + color: #fff; +} +.x-btn-pressed .x-btn-icon-el-wizard-soft-green-small { + color: #404040; +} +.blank-page-container { + text-align: center; + color: #cacaca; +} +.blank-page-container .fa-outer-class { + margin: auto; + width: 150px; + height: 150px; + border-radius: 75px; + background-color: #ebebeb; + text-align: center; +} +.blank-page-container .fa-outer-class .x-fa:before { + line-height: 150px; + font-size: 80px; + color: #cacaca; +} +.blank-page-container h1 { + margin: 5px; + line-height: 30px; + font-weight: normal; +} +.error-page-container .error-page-inner-container { + margin-top: -50px; +} +.error-page-container .x-window-body-default { + background-image: url("images/error-page-background.jpg"); + background-size: cover; + color: #fff; +} +.error-page-container.x-window-default { + border: none; +} +.error-page-container .error-page-top-text { + font-size: 150px; + line-height: 150px; +} +.error-page-container .error-page-bottom-text { + font-size: 18px; +} +.error-page-container .error-page-desc { + line-height: 24px; + text-align: center; + font-size: 18px; +} +.error-page-container .error-page-desc a { + color: #5aaed4; + text-decoration: none; +} +.error-page-container .error-page-desc a:hover { + text-decoration: underline; +} +.pages-faq-container .x-header.x-panel-header-light { + border-bottom: 1px solid #ddd !important; + padding: 15px 16px; +} +.pages-faq-container .x-header.x-panel-header-light .x-panel-header-title-light { + color: #404040; + font-size: 14px; + font-family: "Open Sans"; + font-weight: Bold; +} +.pages-faq-container .x-header .x-fa { + line-height: 16px; +} +.pages-faq-container .x-header .x-tool-after-title .x-tool-img { + display: none; +} +.pages-faq-container .x-accordion-body { + padding-left: 34px; +} +.pages-faq-container .round-btn { + background-color: #5aaed4; + border-color: #5aaed4 !important; +} +.pages-faq-container .round-btn .x-btn-inner-default-toolbar-small { + color: #fff; +} +.pages-faq-container .round-btn:hover { + background-color: transparent; +} +.pages-faq-container .round-btn:hover .x-btn-inner-default-toolbar-small, +.pages-faq-container .round-btn:hover .x-btn-inner-default-small { + color: #5aaed4; +} +.pages-faq-container .round-btn:hover .x-btn-icon-el-default-small, +.pages-faq-container .round-btn:hover .x-btn-icon-el-default-toolbar-small { + color: #5aaed4; +} +.pages-faq-container .x-accordion-hd .x-title-icon { + color: #404040 !important; +} +.pages-faq-container .x-accordion-hd.x-collapsed .x-title-icon:before { + content: "\f0da" !important; +} +.faq-left-sidebar .x-fa { + font-size: 16px; + margin-right: 10px; +} +.faq-left-sidebar .faq-tips-list { + list-style: none; + padding: 0; + margin: 0; +} +.faq-left-sidebar .faq-tips-list li { + margin: 15px 0; +} +.faq-left-sidebar .faq-tips-list li:before { + font-family: FontAwesome; + content: "\f111"; + padding-right: 10px; +} +.faq-left-sidebar .faq-tips-list li.pointone:before { + color: #56b650; +} +.faq-left-sidebar .faq-tips-list li.pointtwo:before { + color: #ffc037; +} +.faq-left-sidebar .faq-tips-list li.pointthree:before { + color: #e55149; +} +.faq-left-sidebar .faq-tips-list li.pointfour:before { + color: #a97fe3; +} +.faq-left-sidebar .borderCls { + border-bottom: 1px solid #ddd; +} +.FAQPanel .x-title-text-default { + font-size: 16px; + font-weight: normal; +} +.allRecordsCls .x-grid-cell-inner { + padding: 15px; +} +.allRecordsCls .x-grid-cell-inner div { + white-space: normal; +} +.allRecordsCls .x-grid-cell-inner .resultsTitleCls { + font-size: 14px; + color: #333; +} +.allRecordsCls .x-grid-cell-inner .resultsUrlCls a { + color: #5aaed4; + text-decoration: none; +} +.allRecordsCls .x-grid-cell-inner .resultsUrlCls a:hover { + text-decoration: underline; +} +.allRecordsCls .x-grid-cell-inner .imageRowCls img { + margin-right: 15px; +} +.user-grid .x-grid-td { + vertical-align: middle; +} +.user-grid .x-grid-td img { + -webkit-border-radius: 50%; + -moz-border-radius: 50%; + -ms-border-radius: 50%; + border-radius: 50%; +} +.user-grid .x-grid-body { + border-width: 1px; +} +.x-action-col-icon { + font-size: 13px !important; +} +.widget-top-first-container { + background-color: #468fd3; +} +.widget-bottom-first-container { + background-color: #fff; +} +.postion-class { + position: relative; +} +.widget-name-text { + font-family: "Open Sans"; + font-weight: Bold; + font-size: 16px; + line-height: 16px; +} +.widget-tool-button .widget-follow-button, +.widget-tool-button .widget-follow-button .x-frame-mc { + background-color: #82c748; + border-color: #82c748 !important; +} +.widget-tool-button .widget-follow-button .x-btn-inner-default-toolbar-small, +.widget-tool-button .widget-follow-button .x-frame-mc .x-btn-inner-default-toolbar-small { + color: #fff; +} +.widget-tool-button .widget-follow-button:hover, +.widget-tool-button .widget-follow-button .x-frame-mc:hover { + background-color: transparent; +} +.widget-tool-button .widget-follow-button:hover .x-btn-inner-default-toolbar-small, +.widget-tool-button .widget-follow-button:hover .x-btn-inner-default-small, +.widget-tool-button .widget-follow-button .x-frame-mc:hover .x-btn-inner-default-toolbar-small, +.widget-tool-button .widget-follow-button .x-frame-mc:hover .x-btn-inner-default-small { + color: #82c748; +} +.widget-tool-button .widget-follow-button:hover .x-btn-icon-el-default-small, +.widget-tool-button .widget-follow-button:hover .x-btn-icon-el-default-toolbar-small, +.widget-tool-button .widget-follow-button .x-frame-mc:hover .x-btn-icon-el-default-small, +.widget-tool-button .widget-follow-button .x-frame-mc:hover .x-btn-icon-el-default-toolbar-small { + color: #82c748; +} +.widget-tool-button .widget-message-button, +.widget-tool-button .widget-message-button .x-frame-mc { + background-color: #5aaed4; + border-color: #5aaed4 !important; +} +.widget-tool-button .widget-message-button .x-btn-inner-default-toolbar-small, +.widget-tool-button .widget-message-button .x-frame-mc .x-btn-inner-default-toolbar-small { + color: #fff; +} +.widget-tool-button .widget-message-button:hover, +.widget-tool-button .widget-message-button .x-frame-mc:hover { + background-color: transparent; +} +.widget-tool-button .widget-message-button:hover .x-btn-inner-default-toolbar-small, +.widget-tool-button .widget-message-button:hover .x-btn-inner-default-small, +.widget-tool-button .widget-message-button .x-frame-mc:hover .x-btn-inner-default-toolbar-small, +.widget-tool-button .widget-message-button .x-frame-mc:hover .x-btn-inner-default-small { + color: #5aaed4; +} +.widget-tool-button .widget-message-button:hover .x-btn-icon-el-default-small, +.widget-tool-button .widget-message-button:hover .x-btn-icon-el-default-toolbar-small, +.widget-tool-button .widget-message-button .x-frame-mc:hover .x-btn-icon-el-default-small, +.widget-tool-button .widget-message-button .x-frame-mc:hover .x-btn-icon-el-default-toolbar-small { + color: #5aaed4; +} +.widget-tool-button .x-btn-inner-default-toolbar-small { + color: #fff; +} +.widget-top-container-first-img { + position: absolute; + z-index: 200; + margin-top: 94px; + border: 3px solid #fff; + -webkit-border-radius: 36px; + -moz-border-radius: 36px; + -ms-border-radius: 36px; + border-radius: 36px; + left: 50%; + margin-left: -33px; +} +.widget-top-second-container { + background-color: #8dc153; +} +.widget-top-first-third-container { + background-color: #607d8b; +} +.widget-top-first-fourth-container { + background: url("images/img2.jpg"); + background-size: 100% auto; +} +.widget-top-second-panel .x-fa { + color: #fff; +} +.widget-follower-toolbar { + background-color: #fafafa; + font-size: 12px; + padding: 0; + text-align: center; + border-top: 1px solid #ddd; + border-bottom: 1px solid #ddd; +} +.widget-follower-toolbar .x-form-display-field { + font-size: 13px; + color: #333; + font-family: "Open Sans"; +} +.widget-follower-toolbar .x-form-display-field .label { + color: #404040; + font-size: 12px; +} +.widget-follower-toolbar .widget-follower-tool-label { + border-left: 1px solid #ddd; + border-right: 1px solid #ddd; +} +.info-card-item { + text-align: center; + background: #fff; + padding: 20px 10px !important; + font-size: 24px; +} +.info-card-item.info-card-large-wrap h2 { + font-size: 48px; + line-height: 48px; +} +.info-card-item.info-card-large-wrap span.x-fa { + height: 75px; + width: 75px; + border-radius: 38px; + color: #fff; + font-size: 30px; + line-height: 75px; + margin: 15px 0; +} +.info-card-item.info-card-large-wrap span.x-fa.fa-shopping-cart { + background-color: #458fd2; +} +.info-card-item.info-card-large-wrap span.x-fa.fa-envelope { + background-color: #4caf50; +} +.info-card-item.info-card-large-wrap span.x-fa.fa-code { + background-color: #9c27b0; +} +.info-card-item.info-card-large-wrap span.x-fa.fa-file-text { + background-color: #e91e63; +} +.info-card-item.info-card-large-wrap .infodiv { + font-size: 14px; + line-height: 16px; +} +.info-card-item.cornflower-blue:before { + background: #458fd2; +} +.info-card-item.green:before { + background: #4caf50; +} +.info-card-item.magenta:before { + background: #9c27b0; +} +.info-card-item.pink:before { + background: #e91e63; +} +.info-card-item.orange:before { + background: #ffc107; +} +.info-card-item.blue:before { + background: #673ab7; +} +.info-card-item h2 { + font-size: 30px; + font-weight: normal; + margin: 0; + margin: 0; + line-height: 32px; +} +.info-card-item div { + line-height: 24px; +} +.info-card-item span { + font-size: 24px; + line-height: 24px; +} +.info-card-item:before { + width: 100%; + position: absolute; + height: 3px; + content: ""; + top: 0; + left: 0; +} +.nav-tree-badge:after { + position: absolute; + height: 18px; + width: 3.3em; + display: inline-block; + text-align: center; + top: 50%; + margin-top: -9px; + right: 12px; + color: #fff; + font-weight: 600; + font-size: 11px; + line-height: 18px; +} +.nav-tree-badge-hot:after { + content: "NEW"; + background-color: #e3495a; +} +.nav-tree-badge-new:after { + content: "NEW"; + background-color: #2eadf5; +} +.circular { + border-radius: 50%; +} +.x-fa.fa-google-plus { + min-width: 16px; + width: auto; +} +body.x-ios.x-webview.x-portrait { + margin-top: 20px; +} +.search-result-attachment { + width: 160px; + height: 100px; +} + +.message-textarea { + line-height: 20px; + min-height: 45px; + border-radius: 21px; +} + +.speech-wrapper { + padding: 5px 6px; + /* overflow: hidden; */ +} +.chat-outbox-out { + float: right; +} +.chat-outbox-in { + float: left; +} +.chatbox { + padding: 10px 5px 5px 10px; + margin-left: 5px; + margin-right: 5px; + margin-top: 0px; + background: #ff952ee3; + color: #000; + position: relative; + border-radius: 10px; + overflow-wrap: break-word; + word-wrap: break-word; + hyphens: auto; + box-shadow: 0 6px 6px -6px black; + font-size: 16px; + max-width: 400px; +} +.chatbox_other { + padding: 5px 5px 5px 10px; + margin-left: 5px; + margin-right: 5px; + margin-top: 0px; + background: #f8f27d91; + color: #000; + position: relative; + border-radius: 10px; + overflow-wrap: break-word; + word-wrap: break-word; + hyphens: auto; + box-shadow: 0 6px 6px -6px black; + font-size: 16px; + max-width: 400px; +} +.timestamp { + font-size: 11px; + position: initial; + bottom: 0px; + right: 10px; + color: #494949; + margin-top: 5px; +} +/* speech bubble 13 */ +.name { + font-weight: 600; + font-size: 12px; + margin: 0px 0px 9px; + color: #1647bc; +} \ No newline at end of file diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow-open-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow-open-rtl.png new file mode 100644 index 0000000..d9968ae Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow-open-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow-open.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow-open.png new file mode 100644 index 0000000..04b1132 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow-open.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow-rtl.png new file mode 100644 index 0000000..90f717b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow.png new file mode 100644 index 0000000..51d2861 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-scroll-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-scroll-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-scroll-right.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-scroll-right.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-open-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-open-rtl.png new file mode 100644 index 0000000..a8801df Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-open-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-open.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-open.png new file mode 100644 index 0000000..19a6673 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-open.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-over-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-over-rtl.png new file mode 100644 index 0000000..db04b9d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-over-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-over.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-over.png new file mode 100644 index 0000000..5106cdf Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-over.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-rtl.png new file mode 100644 index 0000000..658194b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow.png new file mode 100644 index 0000000..d3d375c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/breadcrumb/default-split-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-corners.gif new file mode 100644 index 0000000..c8f6651 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-notitle-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-notitle-corners.gif new file mode 100644 index 0000000..4a712ba Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-notitle-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-notitle-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-notitle-sides.gif new file mode 100644 index 0000000..88156ca Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-notitle-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-sides.gif new file mode 100644 index 0000000..9228d0a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn-group/btn-group-default-framed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-corners.gif new file mode 100644 index 0000000..bf9ead0 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-disabled-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-disabled-corners.gif new file mode 100644 index 0000000..b900ce2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-disabled-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-disabled-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-disabled-sides.gif new file mode 100644 index 0000000..a541a7f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-disabled-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-corners.gif new file mode 100644 index 0000000..4f2f576 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-over-corners.gif new file mode 100644 index 0000000..3c9cfec Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-over-sides.gif new file mode 100644 index 0000000..5372a67 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-pressed-corners.gif new file mode 100644 index 0000000..4d6c3fc Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-pressed-sides.gif new file mode 100644 index 0000000..57d0584 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-sides.gif new file mode 100644 index 0000000..9e70ac9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-focus-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-over-corners.gif new file mode 100644 index 0000000..dd9bcac Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-over-sides.gif new file mode 100644 index 0000000..b6519b6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-pressed-corners.gif new file mode 100644 index 0000000..bf5bf7f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-pressed-sides.gif new file mode 100644 index 0000000..8b0fe23 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-sides.gif new file mode 100644 index 0000000..50b202b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-large-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-corners.gif new file mode 100644 index 0000000..bf9ead0 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-disabled-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-disabled-corners.gif new file mode 100644 index 0000000..b900ce2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-disabled-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-disabled-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-disabled-sides.gif new file mode 100644 index 0000000..a541a7f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-disabled-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-corners.gif new file mode 100644 index 0000000..4f2f576 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-over-corners.gif new file mode 100644 index 0000000..3c9cfec Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-over-sides.gif new file mode 100644 index 0000000..5372a67 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-pressed-corners.gif new file mode 100644 index 0000000..4d6c3fc Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-pressed-sides.gif new file mode 100644 index 0000000..57d0584 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-sides.gif new file mode 100644 index 0000000..9e70ac9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-focus-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-over-corners.gif new file mode 100644 index 0000000..dd9bcac Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-over-sides.gif new file mode 100644 index 0000000..b6519b6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-pressed-corners.gif new file mode 100644 index 0000000..bf5bf7f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-pressed-sides.gif new file mode 100644 index 0000000..8b0fe23 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-sides.gif new file mode 100644 index 0000000..2e6d5cd Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-medium-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-corners.gif new file mode 100644 index 0000000..bf9ead0 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-disabled-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-disabled-corners.gif new file mode 100644 index 0000000..b900ce2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-disabled-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-disabled-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-disabled-sides.gif new file mode 100644 index 0000000..a541a7f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-disabled-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-corners.gif new file mode 100644 index 0000000..4f2f576 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-over-corners.gif new file mode 100644 index 0000000..3c9cfec Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-over-sides.gif new file mode 100644 index 0000000..5372a67 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-pressed-corners.gif new file mode 100644 index 0000000..4d6c3fc Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-pressed-sides.gif new file mode 100644 index 0000000..57d0584 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-sides.gif new file mode 100644 index 0000000..9e70ac9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-focus-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-over-corners.gif new file mode 100644 index 0000000..dd9bcac Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-over-sides.gif new file mode 100644 index 0000000..b6519b6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-pressed-corners.gif new file mode 100644 index 0000000..bf5bf7f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-pressed-sides.gif new file mode 100644 index 0000000..8b0fe23 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-sides.gif new file mode 100644 index 0000000..35978e3 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-small-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-corners.gif new file mode 100644 index 0000000..ad37011 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-disabled-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-disabled-corners.gif new file mode 100644 index 0000000..56d6218 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-disabled-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-disabled-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-disabled-sides.gif new file mode 100644 index 0000000..de517ca Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-disabled-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-corners.gif new file mode 100644 index 0000000..c0f0e02 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-over-corners.gif new file mode 100644 index 0000000..3f636d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-over-sides.gif new file mode 100644 index 0000000..72e0da8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-pressed-corners.gif new file mode 100644 index 0000000..25633ff Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-pressed-sides.gif new file mode 100644 index 0000000..da3275d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-sides.gif new file mode 100644 index 0000000..a370df4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-focus-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-sides.gif new file mode 100644 index 0000000..6847cc4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-large-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-corners.gif new file mode 100644 index 0000000..ad37011 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-disabled-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-disabled-corners.gif new file mode 100644 index 0000000..56d6218 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-disabled-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-disabled-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-disabled-sides.gif new file mode 100644 index 0000000..de517ca Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-disabled-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-corners.gif new file mode 100644 index 0000000..c0f0e02 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-over-corners.gif new file mode 100644 index 0000000..3f636d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-over-sides.gif new file mode 100644 index 0000000..72e0da8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif new file mode 100644 index 0000000..25633ff Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif new file mode 100644 index 0000000..da3275d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-sides.gif new file mode 100644 index 0000000..a370df4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-focus-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-sides.gif new file mode 100644 index 0000000..7092cbc Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-medium-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-corners.gif new file mode 100644 index 0000000..ad37011 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-disabled-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-disabled-corners.gif new file mode 100644 index 0000000..56d6218 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-disabled-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-disabled-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-disabled-sides.gif new file mode 100644 index 0000000..de517ca Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-disabled-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-corners.gif new file mode 100644 index 0000000..c0f0e02 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-over-corners.gif new file mode 100644 index 0000000..3f636d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-over-sides.gif new file mode 100644 index 0000000..72e0da8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-pressed-corners.gif new file mode 100644 index 0000000..25633ff Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-pressed-sides.gif new file mode 100644 index 0000000..da3275d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-sides.gif new file mode 100644 index 0000000..a370df4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-focus-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-sides.gif new file mode 100644 index 0000000..d6e6314 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-default-toolbar-small-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-over-corners.gif new file mode 100644 index 0000000..3f636d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-over-sides.gif new file mode 100644 index 0000000..72e0da8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif new file mode 100644 index 0000000..25633ff Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif new file mode 100644 index 0000000..da3275d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-large-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-over-corners.gif new file mode 100644 index 0000000..3f636d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-over-sides.gif new file mode 100644 index 0000000..72e0da8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif new file mode 100644 index 0000000..25633ff Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif new file mode 100644 index 0000000..da3275d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-medium-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-over-corners.gif new file mode 100644 index 0000000..3f636d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-over-sides.gif new file mode 100644 index 0000000..72e0da8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif new file mode 100644 index 0000000..25633ff Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif new file mode 100644 index 0000000..da3275d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-over-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-over-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-over-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-over-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-pressed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-pressed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-pressed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/btn/btn-plain-toolbar-small-pressed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-arrow-rtl.png new file mode 100644 index 0000000..76beeab Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-arrow.png new file mode 100644 index 0000000..32674e4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow-b-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..79677a4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow-b.png new file mode 100644 index 0000000..9f3928a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow-rtl.png new file mode 100644 index 0000000..7985050 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow.png new file mode 100644 index 0000000..06ad27b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-large-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-arrow-rtl.png new file mode 100644 index 0000000..d54d3a0 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-arrow.png new file mode 100644 index 0000000..e565db4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..f2fb53b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow-b.png new file mode 100644 index 0000000..ee39ae2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow-rtl.png new file mode 100644 index 0000000..fb11140 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow.png new file mode 100644 index 0000000..c1d1875 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-arrow-rtl.png new file mode 100644 index 0000000..3538445 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-arrow.png new file mode 100644 index 0000000..17a9beb Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow-b-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..2f8b2e5 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow-b.png new file mode 100644 index 0000000..afd13fb Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow-rtl.png new file mode 100644 index 0000000..f59b792 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow.png new file mode 100644 index 0000000..eaffbdc Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-small-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-arrow-rtl.png new file mode 100644 index 0000000..d8f0151 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-arrow.png new file mode 100644 index 0000000..31fc36e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow-b-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..379d2d9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow-b.png new file mode 100644 index 0000000..dcfe8ea Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow-rtl.png new file mode 100644 index 0000000..612a6b1 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow.png new file mode 100644 index 0000000..731b207 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-large-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-arrow-rtl.png new file mode 100644 index 0000000..1648e51 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-arrow.png new file mode 100644 index 0000000..65fdd03 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..8d2232b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow-b.png new file mode 100644 index 0000000..2489479 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow-rtl.png new file mode 100644 index 0000000..c81c5f2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow.png new file mode 100644 index 0000000..0a6857a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-arrow-rtl.png new file mode 100644 index 0000000..8919138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-arrow.png new file mode 100644 index 0000000..b56c2a6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow-b-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..1142351 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow-b.png new file mode 100644 index 0000000..bb1b08e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow-rtl.png new file mode 100644 index 0000000..9e9e16b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow.png new file mode 100644 index 0000000..9a72857 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/default-toolbar-small-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-arrow-rtl.png new file mode 100644 index 0000000..3d68e7e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-arrow.png new file mode 100644 index 0000000..17a9beb Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-s-arrow-b.png new file mode 100644 index 0000000..afd13fb Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-s-arrow-rtl.png new file mode 100644 index 0000000..f59b792 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-s-arrow.png new file mode 100644 index 0000000..eaffbdc Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/grid-cell-small-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-arrow-rtl.png new file mode 100644 index 0000000..d8f0151 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-arrow.png new file mode 100644 index 0000000..31fc36e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow-b-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..379d2d9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow-b.png new file mode 100644 index 0000000..dcfe8ea Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow-rtl.png new file mode 100644 index 0000000..612a6b1 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow.png new file mode 100644 index 0000000..731b207 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-large-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-arrow-rtl.png new file mode 100644 index 0000000..1648e51 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-arrow.png new file mode 100644 index 0000000..65fdd03 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..8d2232b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow-b.png new file mode 100644 index 0000000..2489479 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow-rtl.png new file mode 100644 index 0000000..c81c5f2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow.png new file mode 100644 index 0000000..0a6857a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-arrow-rtl.png new file mode 100644 index 0000000..8919138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-arrow.png new file mode 100644 index 0000000..b56c2a6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow-b-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..1142351 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow-b.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow-b.png new file mode 100644 index 0000000..bb1b08e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow-rtl.png new file mode 100644 index 0000000..9e9e16b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow.png new file mode 100644 index 0000000..9a72857 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/button/plain-toolbar-small-s-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/checkbox.png b/src/main/webapp/resources/css/adminDashboardCSS/images/checkbox.png new file mode 100644 index 0000000..7d14ce8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/checkbox.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/company-logo.png b/src/main/webapp/resources/css/adminDashboardCSS/images/company-logo.png new file mode 100644 index 0000000..9f90713 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/company-logo.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/custom-bar.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/custom-bar.gif new file mode 100644 index 0000000..2109825 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/custom-bar.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/datepicker/arrow-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/datepicker/arrow-left.png new file mode 100644 index 0000000..fc09f9a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/datepicker/arrow-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/datepicker/arrow-right.png b/src/main/webapp/resources/css/adminDashboardCSS/images/datepicker/arrow-right.png new file mode 100644 index 0000000..a22b876 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/datepicker/arrow-right.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/datepicker/month-arrow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/datepicker/month-arrow.png new file mode 100644 index 0000000..f0b572f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/datepicker/month-arrow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/dd/drop-add.png b/src/main/webapp/resources/css/adminDashboardCSS/images/dd/drop-add.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/dd/drop-add.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/dd/drop-no.png b/src/main/webapp/resources/css/adminDashboardCSS/images/dd/drop-no.png new file mode 100644 index 0000000..02e219a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/dd/drop-no.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/dd/drop-yes.png b/src/main/webapp/resources/css/adminDashboardCSS/images/dd/drop-yes.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/dd/drop-yes.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/editor/tb-sprite.png b/src/main/webapp/resources/css/adminDashboardCSS/images/editor/tb-sprite.png new file mode 100644 index 0000000..9886118 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/editor/tb-sprite.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/error-page-background.jpg b/src/main/webapp/resources/css/adminDashboardCSS/images/error-page-background.jpg new file mode 100644 index 0000000..53dcd7a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/error-page-background.jpg differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/fieldset/collapse-tool.png b/src/main/webapp/resources/css/adminDashboardCSS/images/fieldset/collapse-tool.png new file mode 100644 index 0000000..97eb83f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/fieldset/collapse-tool.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/flag-icon.png b/src/main/webapp/resources/css/adminDashboardCSS/images/flag-icon.png new file mode 100644 index 0000000..c3830b3 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/flag-icon.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/checkbox.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/checkbox.png new file mode 100644 index 0000000..7d14ce8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/checkbox.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/clear-trigger-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/clear-trigger-rtl.png new file mode 100644 index 0000000..73e1dbe Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/clear-trigger-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/clear-trigger.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/clear-trigger.png new file mode 100644 index 0000000..73e1dbe Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/clear-trigger.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/date-trigger-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/date-trigger-rtl.png new file mode 100644 index 0000000..9489493 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/date-trigger-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/date-trigger.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/date-trigger.png new file mode 100644 index 0000000..9489493 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/date-trigger.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/exclamation.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/exclamation.png new file mode 100644 index 0000000..3e6e3d0 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/exclamation.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/radio.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/radio.png new file mode 100644 index 0000000..ca9ec4b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/radio.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/search-trigger-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/search-trigger-rtl.png new file mode 100644 index 0000000..15e15f5 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/search-trigger-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/search-trigger.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/search-trigger.png new file mode 100644 index 0000000..15e15f5 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/search-trigger.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/spinner-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/spinner-rtl.png new file mode 100644 index 0000000..28d140f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/spinner-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/spinner.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/spinner.png new file mode 100644 index 0000000..28d140f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/spinner.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/tag-field-item-close.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/tag-field-item-close.png new file mode 100644 index 0000000..bcb2834 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/tag-field-item-close.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/trigger-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/trigger-rtl.png new file mode 100644 index 0000000..b4e2d5c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/trigger-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/form/trigger.png b/src/main/webapp/resources/css/adminDashboardCSS/images/form/trigger.png new file mode 100644 index 0000000..b4e2d5c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/form/trigger.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f1.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f1.png new file mode 100644 index 0000000..2a3012c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f1.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f10.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f10.png new file mode 100644 index 0000000..0372c40 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f10.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f11.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f11.png new file mode 100644 index 0000000..3a4d6df Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f11.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f12.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f12.png new file mode 100644 index 0000000..c394a8d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f12.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f13.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f13.png new file mode 100644 index 0000000..5bebdd6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f13.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f14.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f14.png new file mode 100644 index 0000000..3e7f1c9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f14.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f15.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f15.png new file mode 100644 index 0000000..7001068 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f15.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f16.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f16.png new file mode 100644 index 0000000..6eedef5 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f16.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f17.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f17.png new file mode 100644 index 0000000..25bcbac Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f17.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f2.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f2.png new file mode 100644 index 0000000..f527f82 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f2.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f3.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f3.png new file mode 100644 index 0000000..877dc96 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f3.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f4.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f4.png new file mode 100644 index 0000000..e87de34 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f4.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f5.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f5.png new file mode 100644 index 0000000..25bcbac Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f5.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f6.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f6.png new file mode 100644 index 0000000..7001068 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f6.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f7.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f7.png new file mode 100644 index 0000000..6eedef5 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f7.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f8.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f8.png new file mode 100644 index 0000000..8113bec Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f8.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f9.png b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f9.png new file mode 100644 index 0000000..e040451 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/friends/f9.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif new file mode 100644 index 0000000..e1a1cab Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif new file mode 100644 index 0000000..e8f81c9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif new file mode 100644 index 0000000..c7b54f0 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif new file mode 100644 index 0000000..e8f81c9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/col-move-bottom.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/col-move-bottom.png new file mode 100644 index 0000000..9782219 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/col-move-bottom.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/col-move-top.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/col-move-top.png new file mode 100644 index 0000000..6e28535 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/col-move-top.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/columns.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/columns.png new file mode 100644 index 0000000..70a5c87 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/columns.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dd-insert-arrow-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dd-insert-arrow-left.png new file mode 100644 index 0000000..e8177d0 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dd-insert-arrow-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dd-insert-arrow-right.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dd-insert-arrow-right.png new file mode 100644 index 0000000..d610f9d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dd-insert-arrow-right.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dirty-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dirty-rtl.png new file mode 100644 index 0000000..5f84122 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dirty-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dirty.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dirty.png new file mode 100644 index 0000000..fc06fdd Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/dirty.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/drop-no.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/drop-no.png new file mode 100644 index 0000000..02e219a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/drop-no.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/drop-yes.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/drop-yes.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/drop-yes.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/equals.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/equals.png new file mode 100644 index 0000000..c1060ca Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/equals.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/find.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/find.png new file mode 100644 index 0000000..dbfbc16 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/find.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/greater_than.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/greater_than.png new file mode 100644 index 0000000..be41c9a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/greater_than.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/less_than.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/less_than.png new file mode 100644 index 0000000..80aacdd Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/filters/less_than.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/group-by.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/group-by.png new file mode 100644 index 0000000..8508ade Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/group-by.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/group-collapse.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/group-collapse.png new file mode 100644 index 0000000..49fcc4f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/group-collapse.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/group-expand.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/group-expand.png new file mode 100644 index 0000000..d65a7df Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/group-expand.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hd-pop.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hd-pop.png new file mode 100644 index 0000000..3ad96ef Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hd-pop.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-asc.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-asc.png new file mode 100644 index 0000000..a206d35 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-asc.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-desc.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-desc.png new file mode 100644 index 0000000..55a714e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-desc.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-lock.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-lock.png new file mode 100644 index 0000000..b293e10 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-lock.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-unlock.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-unlock.png new file mode 100644 index 0000000..e9e9df5 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/hmenu-unlock.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/loading.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/loading.gif new file mode 100644 index 0000000..81b0f12 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/loading.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-first.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-first.png new file mode 100644 index 0000000..7691f32 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-first.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-last.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-last.png new file mode 100644 index 0000000..49b13d7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-last.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-next.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-next.png new file mode 100644 index 0000000..c3e72ba Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-next.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-prev.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-prev.png new file mode 100644 index 0000000..cace90b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/page-prev.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/pick-button.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/pick-button.png new file mode 100644 index 0000000..acaface Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/pick-button.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/refresh.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/refresh.png new file mode 100644 index 0000000..5320ddd Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/refresh.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/sort_asc.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/sort_asc.png new file mode 100644 index 0000000..a206d35 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/sort_asc.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/grid/sort_desc.png b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/sort_desc.png new file mode 100644 index 0000000..55a714e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/grid/sort_desc.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/icons/cloud-icon.png b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/cloud-icon.png new file mode 100644 index 0000000..838e3d8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/cloud-icon.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/icons/hot-icon.png b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/hot-icon.png new file mode 100644 index 0000000..9e28649 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/hot-icon.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/icons/hot-icon1.png b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/hot-icon1.png new file mode 100644 index 0000000..2e7333d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/hot-icon1.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/icons/new-icon.png b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/new-icon.png new file mode 100644 index 0000000..27251cd Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/new-icon.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/icons/new-icon1.png b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/new-icon1.png new file mode 100644 index 0000000..316cd23 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/icons/new-icon1.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/img1.jpg b/src/main/webapp/resources/css/adminDashboardCSS/images/img1.jpg new file mode 100644 index 0000000..495d86a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/img1.jpg differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/img2.jpg b/src/main/webapp/resources/css/adminDashboardCSS/images/img2.jpg new file mode 100644 index 0000000..f64719c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/img2.jpg differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/img3.jpg b/src/main/webapp/resources/css/adminDashboardCSS/images/img3.jpg new file mode 100644 index 0000000..f281627 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/img3.jpg differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/img4.jpg b/src/main/webapp/resources/css/adminDashboardCSS/images/img4.jpg new file mode 100644 index 0000000..3ee0ac3 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/img4.jpg differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/loadmask/loading.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/loadmask/loading.gif new file mode 100644 index 0000000..8471b4f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/loadmask/loading.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/lock-screen-background.jpg b/src/main/webapp/resources/css/adminDashboardCSS/images/lock-screen-background.jpg new file mode 100644 index 0000000..c23ebb7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/lock-screen-background.jpg differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/magnify.png b/src/main/webapp/resources/css/adminDashboardCSS/images/magnify.png new file mode 100644 index 0000000..b807c42 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/magnify.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-checked.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-checked.png new file mode 100644 index 0000000..4f5157d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-checked.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-group-checked.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-group-checked.png new file mode 100644 index 0000000..a9f0b80 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-group-checked.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menu-parent-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menu-parent-left.png new file mode 100644 index 0000000..d457564 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menu-parent-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menu-parent.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menu-parent.png new file mode 100644 index 0000000..2d2331e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menu-parent.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-checked.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-checked.png new file mode 100644 index 0000000..4f5157d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-checked.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-group-checked.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-group-checked.png new file mode 100644 index 0000000..a9f0b80 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-group-checked.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-menu-parent-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-menu-parent-left.png new file mode 100644 index 0000000..9992618 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-menu-parent-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-menu-parent.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-menu-parent.png new file mode 100644 index 0000000..cb3a569 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-menu-parent.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-scroll-bottom.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-scroll-bottom.png new file mode 100644 index 0000000..69c61f6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-scroll-bottom.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-scroll-top.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-scroll-top.png new file mode 100644 index 0000000..ca7e3e1 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-scroll-top.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-unchecked.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-unchecked.png new file mode 100644 index 0000000..bce8817 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-menubar-unchecked.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-scroll-bottom.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-scroll-bottom.png new file mode 100644 index 0000000..d89a459 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-scroll-top.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-scroll-top.png new file mode 100644 index 0000000..bbbf4af Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-scroll-top.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-unchecked.png b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-unchecked.png new file mode 100644 index 0000000..bce8817 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/menu/default-unchecked.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-bottom-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-bottom-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-bottom-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-bottom-sides.gif new file mode 100644 index 0000000..8e9495b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif new file mode 100644 index 0000000..8e9495b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-left-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-left-corners-rtl.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-left-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-left-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-left-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-left-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-left-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-left-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-right-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-right-corners-rtl.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-right-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-right-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-right-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-right-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-right-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-right-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-top-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-top-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-top-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-top-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-top-sides.gif new file mode 100644 index 0000000..8e9495b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-collapsed-top-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-left-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-left-corners-rtl.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-left-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-left-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-left-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-left-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-left-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-left-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-right-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-right-corners-rtl.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-right-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-right-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-right-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-right-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-right-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-right-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-top-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-top-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-top-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-top-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-top-sides.gif new file mode 100644 index 0000000..8e9495b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-default-framed-top-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-bottom-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-bottom-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-bottom-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-bottom-sides.gif new file mode 100644 index 0000000..4185518 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif new file mode 100644 index 0000000..4185518 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-left-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-left-corners-rtl.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-left-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-left-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-left-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-left-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-left-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-left-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-right-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-right-corners-rtl.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-right-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-right-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-right-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-right-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-right-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-right-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-top-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-top-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-top-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-top-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-top-sides.gif new file mode 100644 index 0000000..4185518 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-collapsed-top-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-left-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-left-corners-rtl.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-left-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-left-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-left-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-left-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-left-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-left-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-right-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-right-corners-rtl.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-right-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-right-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-right-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-right-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-right-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-right-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-top-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-top-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-top-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-top-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-top-sides.gif new file mode 100644 index 0000000..4185518 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel-header/panel-header-light-framed-top-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-default-framed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-default-framed-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-default-framed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-default-framed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-default-framed-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-default-framed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-light-framed-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-light-framed-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-light-framed-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-light-framed-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-light-framed-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/panel/panel-light-framed-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/profile-icon.png b/src/main/webapp/resources/css/adminDashboardCSS/images/profile-icon.png new file mode 100644 index 0000000..7a24771 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/profile-icon.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/radio.png b/src/main/webapp/resources/css/adminDashboardCSS/images/radio.png new file mode 100644 index 0000000..ca9ec4b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/radio.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-error.png b/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-error.png new file mode 100644 index 0000000..458c098 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-error.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-info.png b/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-info.png new file mode 100644 index 0000000..cbccd11 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-info.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-question.png b/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-question.png new file mode 100644 index 0000000..cac922e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-question.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-warning.png b/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-warning.png new file mode 100644 index 0000000..042ca05 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/shared/icon-warning.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/e-handle.png b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/e-handle.png new file mode 100644 index 0000000..2fe5cb1 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/e-handle.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/ne-handle.png b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/ne-handle.png new file mode 100644 index 0000000..8d8eb63 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/ne-handle.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/nw-handle.png b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/nw-handle.png new file mode 100644 index 0000000..9835bea Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/nw-handle.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/s-handle.png b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/s-handle.png new file mode 100644 index 0000000..06f914e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/s-handle.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/se-handle.png b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/se-handle.png new file mode 100644 index 0000000..5a2c695 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/se-handle.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/sw-handle.png b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/sw-handle.png new file mode 100644 index 0000000..7f68f40 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/sizer/sw-handle.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-bg.png b/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-bg.png new file mode 100644 index 0000000..1ade292 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-bg.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-thumb.png b/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-thumb.png new file mode 100644 index 0000000..d8a03de Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-thumb.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-v-bg.png b/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-v-bg.png new file mode 100644 index 0000000..c24663e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-v-bg.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-v-thumb.png b/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-v-thumb.png new file mode 100644 index 0000000..d8a03de Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/slider/slider-v-thumb.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-more-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-more-left.png new file mode 100644 index 0000000..83b0288 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-more-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-more.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-more.png new file mode 100644 index 0000000..83b0288 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-more.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-more-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-more-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-more.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-more.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-bottom.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-bottom.png new file mode 100644 index 0000000..813a4d5 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-bottom.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-left.png new file mode 100644 index 0000000..9120ea4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-right.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-right.png new file mode 100644 index 0000000..67fd5a4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-right.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-top.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-top.png new file mode 100644 index 0000000..01ad4ee Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-plain-scroll-top.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-bottom.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-bottom.png new file mode 100644 index 0000000..ffff826 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-left.png new file mode 100644 index 0000000..2c35294 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-right.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-right.png new file mode 100644 index 0000000..82dfe01 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-right.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-top.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-top.png new file mode 100644 index 0000000..b2fabfc Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab-bar/default-scroll-top.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-active-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-active-fbg.gif new file mode 100644 index 0000000..7ab3e2a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-active-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-focus-active-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-focus-active-fbg.gif new file mode 100644 index 0000000..7ab3e2a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-focus-over-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-focus-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-over-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-bottom-over-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-close.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-close.png new file mode 100644 index 0000000..46cc89f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-close.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-active-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-active-fbg.gif new file mode 100644 index 0000000..e6f77b8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-active-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-focus-active-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-focus-active-fbg.gif new file mode 100644 index 0000000..e6f77b8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-focus-over-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-focus-over-fbg.gif new file mode 100644 index 0000000..e11bf81 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-over-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-over-fbg.gif new file mode 100644 index 0000000..e11bf81 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-left-over-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-active-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-active-fbg.gif new file mode 100644 index 0000000..e6f77b8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-active-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-focus-active-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-focus-active-fbg.gif new file mode 100644 index 0000000..e6f77b8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-focus-over-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-focus-over-fbg.gif new file mode 100644 index 0000000..e11bf81 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-over-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-over-fbg.gif new file mode 100644 index 0000000..e11bf81 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-right-over-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-active-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-active-fbg.gif new file mode 100644 index 0000000..7ab3e2a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-active-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-focus-active-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-focus-active-fbg.gif new file mode 100644 index 0000000..7ab3e2a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-focus-over-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-focus-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-over-fbg.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tab/tab-default-top-over-fbg.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-default-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-default-corners.gif new file mode 100644 index 0000000..d335a16 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-default-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-default-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-default-sides.gif new file mode 100644 index 0000000..b935f3d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-default-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-form-invalid-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-form-invalid-corners.gif new file mode 100644 index 0000000..d335a16 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-form-invalid-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-form-invalid-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-form-invalid-sides.gif new file mode 100644 index 0000000..b935f3d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tip/tip-form-invalid-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-more-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-more-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-more.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-more.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-bottom.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-bottom.png new file mode 100644 index 0000000..6741161 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-right.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-right.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-top.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-top.png new file mode 100644 index 0000000..2a26ba9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/default-scroll-top.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-more-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-more-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-more.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-more.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-scroll-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-scroll-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-scroll-right.png b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/toolbar/footer-scroll-right.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tools/tool-sprites-dark.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tools/tool-sprites-dark.png new file mode 100644 index 0000000..474088b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tools/tool-sprites-dark.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tools/tool-sprites.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tools/tool-sprites.png new file mode 100644 index 0000000..17fbc0f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tools/tool-sprites.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/arrows-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/arrows-rtl.png new file mode 100644 index 0000000..4aae887 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/arrows-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/arrows.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/arrows.png new file mode 100644 index 0000000..de10dd6 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/arrows.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-above.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-above.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-above.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-add.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-add.gif new file mode 100644 index 0000000..b22cd14 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-add.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-add.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-add.png new file mode 100644 index 0000000..c9d24fd Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-add.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-append.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-append.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-append.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-below.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-below.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-below.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-between.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-between.gif new file mode 100644 index 0000000..f5a042d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-between.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-between.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-between.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-between.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-no.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-no.gif new file mode 100644 index 0000000..9d9c6a9 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-no.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-no.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-no.png new file mode 100644 index 0000000..bb89cfc Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-no.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-over.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-over.gif new file mode 100644 index 0000000..2e514e7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-over.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-over.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-over.png new file mode 100644 index 0000000..70d1807 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-over.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-under.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-under.gif new file mode 100644 index 0000000..8535ef4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-under.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-under.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-under.png new file mode 100644 index 0000000..3ba23b3 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-under.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-yes.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-yes.gif new file mode 100644 index 0000000..8aacb30 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-yes.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-yes.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-yes.png new file mode 100644 index 0000000..83d0dbc Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/drop-yes.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-minus-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-minus-rtl.png new file mode 100644 index 0000000..2ffe7b2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-minus-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-minus.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-minus.png new file mode 100644 index 0000000..b39a71d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-minus.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-plus-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-plus-rtl.png new file mode 100644 index 0000000..bea9892 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-plus-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-plus.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-plus.png new file mode 100644 index 0000000..630438f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-plus.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-rtl.png new file mode 100644 index 0000000..1d0821b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end.png new file mode 100644 index 0000000..2eb0ed0 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-end.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-line-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-line-rtl.png new file mode 100644 index 0000000..e26b768 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-line-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-line.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-line.png new file mode 100644 index 0000000..ac37424 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-line.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus-nl-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus-nl-rtl.png new file mode 100644 index 0000000..1008a54 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus-nl-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus-nl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus-nl.png new file mode 100644 index 0000000..f2a805d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus-nl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus-rtl.png new file mode 100644 index 0000000..cefb704 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus.png new file mode 100644 index 0000000..a256b48 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-minus.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus-nl-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus-nl-rtl.png new file mode 100644 index 0000000..e1e6ece Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus-nl-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus-nl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus-nl.png new file mode 100644 index 0000000..3a401ea Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus-nl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus-rtl.png new file mode 100644 index 0000000..487f27a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus.png new file mode 100644 index 0000000..03e202a Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-plus.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-rtl.png new file mode 100644 index 0000000..166e163 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow.png new file mode 100644 index 0000000..4bf9ae5 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/elbow.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder-open-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder-open-rtl.png new file mode 100644 index 0000000..bb896d8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder-open-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder-open.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder-open.png new file mode 100644 index 0000000..50397da Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder-open.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder-rtl.png new file mode 100644 index 0000000..3b17672 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder.png new file mode 100644 index 0000000..4b02054 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/folder.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/leaf-rtl.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/leaf-rtl.png new file mode 100644 index 0000000..b2e6f6e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/leaf-rtl.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/leaf.png b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/leaf.png new file mode 100644 index 0000000..6acb635 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/leaf.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/tree/loading.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/loading.gif new file mode 100644 index 0000000..81b0f12 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/tree/loading.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/1.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/1.png new file mode 100644 index 0000000..4e47a7d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/1.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/10.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/10.png new file mode 100644 index 0000000..176e5ab Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/10.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/11.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/11.png new file mode 100644 index 0000000..6e90ca7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/11.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/12.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/12.png new file mode 100644 index 0000000..a40bca4 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/12.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/13.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/13.png new file mode 100644 index 0000000..c82e352 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/13.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/14.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/14.png new file mode 100644 index 0000000..3391304 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/14.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/15.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/15.png new file mode 100644 index 0000000..84abd3f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/15.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/16.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/16.png new file mode 100644 index 0000000..c096bbd Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/16.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/17.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/17.png new file mode 100644 index 0000000..cd6528d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/17.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/18.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/18.png new file mode 100644 index 0000000..aeaa2f2 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/18.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/19.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/19.png new file mode 100644 index 0000000..a005a4e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/19.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/1_.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/1_.png new file mode 100644 index 0000000..cfcdf16 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/1_.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/2.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/2.png new file mode 100644 index 0000000..af0e6e3 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/2.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/20.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/20.png new file mode 100644 index 0000000..3cab579 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/20.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/2_.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/2_.png new file mode 100644 index 0000000..4b8ceda Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/2_.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/3.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/3.png new file mode 100644 index 0000000..9f540d8 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/3.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/3_.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/3_.png new file mode 100644 index 0000000..56884eb Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/3_.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/4.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/4.png new file mode 100644 index 0000000..502e684 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/4.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/4_.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/4_.png new file mode 100644 index 0000000..10e7ef5 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/4_.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/5.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/5.png new file mode 100644 index 0000000..840ef0b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/5.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/6.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/6.png new file mode 100644 index 0000000..a7bd658 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/6.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/7.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/7.png new file mode 100644 index 0000000..b9d0a0e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/7.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/8.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/8.png new file mode 100644 index 0000000..124a919 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/8.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/9.png b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/9.png new file mode 100644 index 0000000..9e2fb6f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/9.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/mitul.jpg b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/mitul.jpg new file mode 100644 index 0000000..3de1fa7 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/mitul.jpg differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/mitul1.jpg b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/mitul1.jpg new file mode 100644 index 0000000..4444022 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/user-profile/mitul1.jpg differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-bottom.png b/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-bottom.png new file mode 100644 index 0000000..241209e Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-bottom.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-left.png b/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-left.png new file mode 100644 index 0000000..1c40b78 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-left.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-right.png b/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-right.png new file mode 100644 index 0000000..505c329 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-right.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-top.png b/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-top.png new file mode 100644 index 0000000..4a378a3 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/util/splitter/mini-top.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-bottom-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-bottom-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-bottom-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-bottom-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-bottom-sides.gif new file mode 100644 index 0000000..8e9495b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-bottom-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-bottom-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-bottom-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-bottom-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-bottom-sides.gif new file mode 100644 index 0000000..8e9495b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-left-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-left-corners-rtl.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-left-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-left-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-left-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-left-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-left-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-left-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-right-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-right-corners-rtl.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-right-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-right-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-right-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-right-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-right-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-right-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-top-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-top-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-top-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-top-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-top-sides.gif new file mode 100644 index 0000000..8e9495b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-collapsed-top-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-left-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-left-corners-rtl.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-left-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-left-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-left-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-left-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-left-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-left-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-right-corners-rtl.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-right-corners-rtl.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-right-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-right-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-right-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-right-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-right-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-right-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-top-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-top-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-top-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-top-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-top-sides.gif new file mode 100644 index 0000000..8e9495b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window-header/window-header-default-top-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/fade-blue.png b/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/fade-blue.png new file mode 100644 index 0000000..4dbf08b Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/fade-blue.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/fader.png b/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/fader.png new file mode 100644 index 0000000..be8c27f Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/fader.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/icon16_error.png b/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/icon16_error.png new file mode 100644 index 0000000..5f168d3 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/icon16_error.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/icon16_info.png b/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/icon16_info.png new file mode 100644 index 0000000..6c6b32d Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window/toast/icon16_info.png differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window/window-default-corners.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window/window-default-corners.gif new file mode 100644 index 0000000..ef71321 Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window/window-default-corners.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/images/window/window-default-sides.gif b/src/main/webapp/resources/css/adminDashboardCSS/images/window/window-default-sides.gif new file mode 100644 index 0000000..648394c Binary files /dev/null and b/src/main/webapp/resources/css/adminDashboardCSS/images/window/window-default-sides.gif differ diff --git a/src/main/webapp/resources/css/adminDashboardCSS/try.css b/src/main/webapp/resources/css/adminDashboardCSS/try.css new file mode 100644 index 0000000..b596a7b --- /dev/null +++ b/src/main/webapp/resources/css/adminDashboardCSS/try.css @@ -0,0 +1,140 @@ +.calendar { + background-color: white; + border: 1px solid #e1e1e1; +} + +.calendar__day { + border-right: 1px solid #e1e1e1; + border-top: 1px solid #e1e1e1; +} + +.calendar__day:last-child { + border-right: 0; +} + +/* Calendar Detail Chart CSS start */ +@keyframes expand { + 0% { + width: 5%; + background-color: #f9bcca00; + } +} + +h6 { + margin: 0; + font-size: 0.9em; + color: #4b4b4b; +} +.cal-chart { + overflow: hidden; + width: 100%; + animation: expand 0.1s ease forwards; +} +.inc { + border-radius: 9px; + overflow: hidden; + box-shadow: inset 0px 15px 15px -15px #949494, inset 0px -15px 15px -15px #343434; + animation: expand 2s ease forwards; +} +.cal-block { + display: block; + height: 20px; + color: #fff; + font-size: 0.75em; + float: left; + background-color: #334d5c; + position: relative; + overflow: hidden; + opacity: 1; + transition: opacity, 0.3s ease; + cursor: pointer; +} +.item1 { + background-color: #34ca49c2; +} +.item2 { + background-color: #efc94cbd; +} +.item3 { + background-color: #e27b3fb7; +} +.item4 { + background-color: #df5a49b4; +} +.item5 { + background-color: #962d3eb9; +} +.cal-block:hover { + opacity: 0.65; +} +.meeting_text { + padding-left: 20px; + font-size: 12; +} +.fitting_color { + color: #DB4455; +} +.delivery_color { + color: #8CC051; +} +.others_color { + color: #4B89DC; +} + +value { + display: block; + line-height: 1em; + position: absolute; + top: 50%; + left: 50%; + transform: translate(-50%); +} + +/* Calendar Total Chart CSS start */ +.progress2 { + background: rgba(232, 230, 230, 0.25); + box-shadow: inset 0px 0px 2px 0.5px rgba(168, 168, 168, 0.85); + padding: 3px; + border-radius: 10px; + height: 26px; +} + +.progress-moved .progress-bar2 { + background-color: rgb(156, 19, 51); + animation: progressAnimation 3s; + color: white; + font-size: 16px; +} + +@keyframes progressAnimation { + 0% { + width: 5%; + background-color: #f9bcca; + } +} + +/* Category checkbox */ +.category-checkbox { + display: inline-block; + width: 14px; + height: 14px; + line-height: 14px; + margin-right: 8px; + border-radius: 8px; + border: solid 0.5px; +} + +/* Message Box image */ +.img-width-height { + max-width: 300px; + max-height: 200px; +} + +/* Container Title CSS */ +.container-title { + font-weight: bold; + font-size: 20px; + font-family: "Source Sans Pro", sans-serif; + margin-left: 15px; + color: white; +} diff --git a/src/main/webapp/resources/css/icons-silk.css b/src/main/webapp/resources/css/icons-silk.css new file mode 100644 index 0000000..38418e8 --- /dev/null +++ b/src/main/webapp/resources/css/icons-silk.css @@ -0,0 +1,1005 @@ +/* + * this css is for the free "silk" icon library + * http://www.famfamfam.com + */ +.silk-accept { background-image: url(../images/icons-silk/accept.png) !important; background-repeat: no-repeat; } +.silk-add { background-image: url(../images/icons-silk/add.png) !important; background-repeat: no-repeat; } +.silk-anchor { background-image: url(../images/icons-silk/anchor.png) !important; background-repeat: no-repeat; } +.silk-application { background-image: url(../images/icons-silk/application.png) !important; background-repeat: no-repeat; } +.silk-application-add { background-image: url(../images/icons-silk/application_add.png) !important; background-repeat: no-repeat; } +.silk-application-cascade { background-image: url(../images/icons-silk/application_cascade.png) !important; background-repeat: no-repeat; } +.silk-application-delete { background-image: url(../images/icons-silk/application_delete.png) !important; background-repeat: no-repeat; } +.silk-application-double { background-image: url(../images/icons-silk/application_double.png) !important; background-repeat: no-repeat; } +.silk-application-edit { background-image: url(../images/icons-silk/application_edit.png) !important; background-repeat: no-repeat; } +.silk-application-error { background-image: url(../images/icons-silk/application_error.png) !important; background-repeat: no-repeat; } +.silk-application-form { background-image: url(../images/icons-silk/application_form.png) !important; background-repeat: no-repeat; } +.silk-application-form-add { background-image: url(../images/icons-silk/application_form_add.png) !important; background-repeat: no-repeat; } +.silk-application-form-delete { background-image: url(../images/icons-silk/application_form_delete.png) !important; background-repeat: no-repeat; } +.silk-application-form-edit { background-image: url(../images/icons-silk/application_form_edit.png) !important; background-repeat: no-repeat; } +.silk-application-form-magnify { background-image: url(../images/icons-silk/application_form_magnify.png) !important; background-repeat: no-repeat; } +.silk-application-get { background-image: url(../images/icons-silk/application_get.png) !important; background-repeat: no-repeat; } +.silk-application-go { background-image: url(../images/icons-silk/application_go.png) !important; background-repeat: no-repeat; } +.silk-application-home { background-image: url(../images/icons-silk/application_home.png) !important; background-repeat: no-repeat; } +.silk-application-key { background-image: url(../images/icons-silk/application_key.png) !important; background-repeat: no-repeat; } +.silk-application-lightning { background-image: url(../images/icons-silk/application_lightning.png) !important; background-repeat: no-repeat; } +.silk-application-link { background-image: url(../images/icons-silk/application_link.png) !important; background-repeat: no-repeat; } +.silk-application-osx { background-image: url(../images/icons-silk/application_osx.png) !important; background-repeat: no-repeat; } +.silk-application-osx-terminal { background-image: url(../images/icons-silk/application_osx_terminal.png) !important; background-repeat: no-repeat; } +.silk-application-put { background-image: url(../images/icons-silk/application_put.png) !important; background-repeat: no-repeat; } +.silk-application-side-boxes { background-image: url(../images/icons-silk/application_side_boxes.png) !important; background-repeat: no-repeat; } +.silk-application-side-contract { background-image: url(../images/icons-silk/application_side_contract.png) !important; background-repeat: no-repeat; } +.silk-application-side-expand { background-image: url(../images/icons-silk/application_side_expand.png) !important; background-repeat: no-repeat; } +.silk-application-side-list { background-image: url(../images/icons-silk/application_side_list.png) !important; background-repeat: no-repeat; } +.silk-application-side-tree { background-image: url(../images/icons-silk/application_side_tree.png) !important; background-repeat: no-repeat; } +.silk-application-split { background-image: url(../images/icons-silk/application_split.png) !important; background-repeat: no-repeat; } +.silk-application-tile-horizontal { background-image: url(../images/icons-silk/application_tile_horizontal.png) !important; background-repeat: no-repeat; } +.silk-application-tile-vertical { background-image: url(../images/icons-silk/application_tile_vertical.png) !important; background-repeat: no-repeat; } +.silk-application-view-columns { background-image: url(../images/icons-silk/application_view_columns.png) !important; background-repeat: no-repeat; } +.silk-application-view-detail { background-image: url(../images/icons-silk/application_view_detail.png) !important; background-repeat: no-repeat; } +.silk-application-view-gallery { background-image: url(../images/icons-silk/application_view_gallery.png) !important; background-repeat: no-repeat; } +.silk-application-view-icons { background-image: url(../images/icons-silk/application_view_icons.png) !important; background-repeat: no-repeat; } +.silk-application-view-list { background-image: url(../images/icons-silk/application_view_list.png) !important; background-repeat: no-repeat; } +.silk-application-view-tile { background-image: url(../images/icons-silk/application_view_tile.png) !important; background-repeat: no-repeat; } +.silk-application-xp { background-image: url(../images/icons-silk/application_xp.png) !important; background-repeat: no-repeat; } +.silk-application-xp-terminal { background-image: url(../images/icons-silk/application_xp_terminal.png) !important; background-repeat: no-repeat; } +.silk-arrow-branch { background-image: url(../images/icons-silk/arrow_branch.png) !important; background-repeat: no-repeat; } +.silk-arrow-divide { background-image: url(../images/icons-silk/arrow_divide.png) !important; background-repeat: no-repeat; } +.silk-arrow-down { background-image: url(../images/icons-silk/arrow_down.png) !important; background-repeat: no-repeat; } +.silk-arrow-in { background-image: url(../images/icons-silk/arrow_in.png) !important; background-repeat: no-repeat; } +.silk-arrow-inout { background-image: url(../images/icons-silk/arrow_inout.png) !important; background-repeat: no-repeat; } +.silk-arrow-join { background-image: url(../images/icons-silk/arrow_join.png) !important; background-repeat: no-repeat; } +.silk-arrow-left { background-image: url(../images/icons-silk/arrow_left.png) !important; background-repeat: no-repeat; } +.silk-arrow-merge { background-image: url(../images/icons-silk/arrow_merge.png) !important; background-repeat: no-repeat; } +.silk-arrow-out { background-image: url(../images/icons-silk/arrow_out.png) !important; background-repeat: no-repeat; } +.silk-arrow-redo { background-image: url(../images/icons-silk/arrow_redo.png) !important; background-repeat: no-repeat; } +.silk-arrow-refresh { background-image: url(../images/icons-silk/arrow_refresh.png) !important; background-repeat: no-repeat; } +.silk-arrow-refresh-small { background-image: url(../images/icons-silk/arrow_refresh_small.png) !important; background-repeat: no-repeat; } +.silk-arrow-right { background-image: url(../images/icons-silk/arrow_right.png) !important; background-repeat: no-repeat; } +.silk-arrow-rotate-anticlockwise { background-image: url(../images/icons-silk/arrow_rotate_anticlockwise.png) !important; background-repeat: no-repeat; } +.silk-arrow-rotate-clockwise { background-image: url(../images/icons-silk/arrow_rotate_clockwise.png) !important; background-repeat: no-repeat; } +.silk-arrow-switch { background-image: url(../images/icons-silk/arrow_switch.png) !important; background-repeat: no-repeat; } +.silk-arrow-turn-left { background-image: url(../images/icons-silk/arrow_turn_left.png) !important; background-repeat: no-repeat; } +.silk-arrow-turn-right { background-image: url(../images/icons-silk/arrow_turn_right.png) !important; background-repeat: no-repeat; } +.silk-arrow-undo { background-image: url(../images/icons-silk/arrow_undo.png) !important; background-repeat: no-repeat; } +.silk-arrow-up { background-image: url(../images/icons-silk/arrow_up.png) !important; background-repeat: no-repeat; } +.silk-asterisk-orange { background-image: url(../images/icons-silk/asterisk_orange.png) !important; background-repeat: no-repeat; } +.silk-asterisk-yellow { background-image: url(../images/icons-silk/asterisk_yellow.png) !important; background-repeat: no-repeat; } +.silk-attach { background-image: url(../images/icons-silk/attach.png) !important; background-repeat: no-repeat; } +.silk-award-star-add { background-image: url(../images/icons-silk/award_star_add.png) !important; background-repeat: no-repeat; } +.silk-award-star-bronze-1 { background-image: url(../images/icons-silk/award_star_bronze_1.png) !important; background-repeat: no-repeat; } +.silk-award-star-bronze-2 { background-image: url(../images/icons-silk/award_star_bronze_2.png) !important; background-repeat: no-repeat; } +.silk-award-star-bronze-3 { background-image: url(../images/icons-silk/award_star_bronze_3.png) !important; background-repeat: no-repeat; } +.silk-award-star-delete { background-image: url(../images/icons-silk/award_star_delete.png) !important; background-repeat: no-repeat; } +.silk-award-star-gold-1 { background-image: url(../images/icons-silk/award_star_gold_1.png) !important; background-repeat: no-repeat; } +.silk-award-star-gold-2 { background-image: url(../images/icons-silk/award_star_gold_2.png) !important; background-repeat: no-repeat; } +.silk-award-star-gold-3 { background-image: url(../images/icons-silk/award_star_gold_3.png) !important; background-repeat: no-repeat; } +.silk-award-star-silver-1 { background-image: url(../images/icons-silk/award_star_silver_1.png) !important; background-repeat: no-repeat; } +.silk-award-star-silver-2 { background-image: url(../images/icons-silk/award_star_silver_2.png) !important; background-repeat: no-repeat; } +.silk-award-star-silver-3 { background-image: url(../images/icons-silk/award_star_silver_3.png) !important; background-repeat: no-repeat; } +.silk-basket { background-image: url(../images/icons-silk/basket.png) !important; background-repeat: no-repeat; } +.silk-basket-add { background-image: url(../images/icons-silk/basket_add.png) !important; background-repeat: no-repeat; } +.silk-basket-delete { background-image: url(../images/icons-silk/basket_delete.png) !important; background-repeat: no-repeat; } +.silk-basket-edit { background-image: url(../images/icons-silk/basket_edit.png) !important; background-repeat: no-repeat; } +.silk-basket-error { background-image: url(../images/icons-silk/basket_error.png) !important; background-repeat: no-repeat; } +.silk-basket-go { background-image: url(../images/icons-silk/basket_go.png) !important; background-repeat: no-repeat; } +.silk-basket-put { background-image: url(../images/icons-silk/basket_put.png) !important; background-repeat: no-repeat; } +.silk-basket-remove { background-image: url(../images/icons-silk/basket_remove.png) !important; background-repeat: no-repeat; } +.silk-bell { background-image: url(../images/icons-silk/bell.png) !important; background-repeat: no-repeat; } +.silk-bell-add { background-image: url(../images/icons-silk/bell_add.png) !important; background-repeat: no-repeat; } +.silk-bell-delete { background-image: url(../images/icons-silk/bell_delete.png) !important; background-repeat: no-repeat; } +.silk-bell-error { background-image: url(../images/icons-silk/bell_error.png) !important; background-repeat: no-repeat; } +.silk-bell-go { background-image: url(../images/icons-silk/bell_go.png) !important; background-repeat: no-repeat; } +.silk-bell-link { background-image: url(../images/icons-silk/bell_link.png) !important; background-repeat: no-repeat; } +.silk-bin { background-image: url(../images/icons-silk/bin.png) !important; background-repeat: no-repeat; } +.silk-bin-closed { background-image: url(../images/icons-silk/bin_closed.png) !important; background-repeat: no-repeat; } +.silk-bin-empty { background-image: url(../images/icons-silk/bin_empty.png) !important; background-repeat: no-repeat; } +.silk-bomb { background-image: url(../images/icons-silk/bomb.png) !important; background-repeat: no-repeat; } +.silk-book { background-image: url(../images/icons-silk/book.png) !important; background-repeat: no-repeat; } +.silk-book-add { background-image: url(../images/icons-silk/book_add.png) !important; background-repeat: no-repeat; } +.silk-book-addresses { background-image: url(../images/icons-silk/book_addresses.png) !important; background-repeat: no-repeat; } +.silk-book-delete { background-image: url(../images/icons-silk/book_delete.png) !important; background-repeat: no-repeat; } +.silk-book-edit { background-image: url(../images/icons-silk/book_edit.png) !important; background-repeat: no-repeat; } +.silk-book-error { background-image: url(../images/icons-silk/book_error.png) !important; background-repeat: no-repeat; } +.silk-book-go { background-image: url(../images/icons-silk/book_go.png) !important; background-repeat: no-repeat; } +.silk-book-key { background-image: url(../images/icons-silk/book_key.png) !important; background-repeat: no-repeat; } +.silk-book-link { background-image: url(../images/icons-silk/book_link.png) !important; background-repeat: no-repeat; } +.silk-book-next { background-image: url(../images/icons-silk/book_next.png) !important; background-repeat: no-repeat; } +.silk-book-open { background-image: url(../images/icons-silk/book_open.png) !important; background-repeat: no-repeat; } +.silk-book-previous { background-image: url(../images/icons-silk/book_previous.png) !important; background-repeat: no-repeat; } +.silk-box { background-image: url(../images/icons-silk/box.png) !important; background-repeat: no-repeat; } +.silk-brick { background-image: url(../images/icons-silk/brick.png) !important; background-repeat: no-repeat; } +.silk-brick-add { background-image: url(../images/icons-silk/brick_add.png) !important; background-repeat: no-repeat; } +.silk-brick-delete { background-image: url(../images/icons-silk/brick_delete.png) !important; background-repeat: no-repeat; } +.silk-brick-edit { background-image: url(../images/icons-silk/brick_edit.png) !important; background-repeat: no-repeat; } +.silk-brick-error { background-image: url(../images/icons-silk/brick_error.png) !important; background-repeat: no-repeat; } +.silk-brick-go { background-image: url(../images/icons-silk/brick_go.png) !important; background-repeat: no-repeat; } +.silk-brick-link { background-image: url(../images/icons-silk/brick_link.png) !important; background-repeat: no-repeat; } +.silk-bricks { background-image: url(../images/icons-silk/bricks.png) !important; background-repeat: no-repeat; } +.silk-briefcase { background-image: url(../images/icons-silk/briefcase.png) !important; background-repeat: no-repeat; } +.silk-bug { background-image: url(../images/icons-silk/bug.png) !important; background-repeat: no-repeat; } +.silk-bug-add { background-image: url(../images/icons-silk/bug_add.png) !important; background-repeat: no-repeat; } +.silk-bug-delete { background-image: url(../images/icons-silk/bug_delete.png) !important; background-repeat: no-repeat; } +.silk-bug-edit { background-image: url(../images/icons-silk/bug_edit.png) !important; background-repeat: no-repeat; } +.silk-bug-error { background-image: url(../images/icons-silk/bug_error.png) !important; background-repeat: no-repeat; } +.silk-bug-go { background-image: url(../images/icons-silk/bug_go.png) !important; background-repeat: no-repeat; } +.silk-bug-link { background-image: url(../images/icons-silk/bug_link.png) !important; background-repeat: no-repeat; } +.silk-building { background-image: url(../images/icons-silk/building.png) !important; background-repeat: no-repeat; } +.silk-building-add { background-image: url(../images/icons-silk/building_add.png) !important; background-repeat: no-repeat; } +.silk-building-delete { background-image: url(../images/icons-silk/building_delete.png) !important; background-repeat: no-repeat; } +.silk-building-edit { background-image: url(../images/icons-silk/building_edit.png) !important; background-repeat: no-repeat; } +.silk-building-error { background-image: url(../images/icons-silk/building_error.png) !important; background-repeat: no-repeat; } +.silk-building-go { background-image: url(../images/icons-silk/building_go.png) !important; background-repeat: no-repeat; } +.silk-building-key { background-image: url(../images/icons-silk/building_key.png) !important; background-repeat: no-repeat; } +.silk-building-link { background-image: url(../images/icons-silk/building_link.png) !important; background-repeat: no-repeat; } +.silk-bullet-add { background-image: url(../images/icons-silk/bullet_add.png) !important; background-repeat: no-repeat; } +.silk-bullet-arrow-bottom { background-image: url(../images/icons-silk/bullet_arrow_bottom.png) !important; background-repeat: no-repeat; } +.silk-bullet-arrow-down { background-image: url(../images/icons-silk/bullet_arrow_down.png) !important; background-repeat: no-repeat; } +.silk-bullet-arrow-top { background-image: url(../images/icons-silk/bullet_arrow_top.png) !important; background-repeat: no-repeat; } +.silk-bullet-arrow-up { background-image: url(../images/icons-silk/bullet_arrow_up.png) !important; background-repeat: no-repeat; } +.silk-bullet-black { background-image: url(../images/icons-silk/bullet_black.png) !important; background-repeat: no-repeat; } +.silk-bullet-blue { background-image: url(../images/icons-silk/bullet_blue.png) !important; background-repeat: no-repeat; } +.silk-bullet-delete { background-image: url(../images/icons-silk/bullet_delete.png) !important; background-repeat: no-repeat; } +.silk-bullet-disk { background-image: url(../images/icons-silk/bullet_disk.png) !important; background-repeat: no-repeat; } +.silk-bullet-error { background-image: url(../images/icons-silk/bullet_error.png) !important; background-repeat: no-repeat; } +.silk-bullet-feed { background-image: url(../images/icons-silk/bullet_feed.png) !important; background-repeat: no-repeat; } +.silk-bullet-go { background-image: url(../images/icons-silk/bullet_go.png) !important; background-repeat: no-repeat; } +.silk-bullet-green { background-image: url(../images/icons-silk/bullet_green.png) !important; background-repeat: no-repeat; } +.silk-bullet-key { background-image: url(../images/icons-silk/bullet_key.png) !important; background-repeat: no-repeat; } +.silk-bullet-orange { background-image: url(../images/icons-silk/bullet_orange.png) !important; background-repeat: no-repeat; } +.silk-bullet-picture { background-image: url(../images/icons-silk/bullet_picture.png) !important; background-repeat: no-repeat; } +.silk-bullet-pink { background-image: url(../images/icons-silk/bullet_pink.png) !important; background-repeat: no-repeat; } +.silk-bullet-purple { background-image: url(../images/icons-silk/bullet_purple.png) !important; background-repeat: no-repeat; } +.silk-bullet-red { background-image: url(../images/icons-silk/bullet_red.png) !important; background-repeat: no-repeat; } +.silk-bullet-star { background-image: url(../images/icons-silk/bullet_star.png) !important; background-repeat: no-repeat; } +.silk-bullet-toggle-minus { background-image: url(../images/icons-silk/bullet_toggle_minus.png) !important; background-repeat: no-repeat; } +.silk-bullet-toggle-plus { background-image: url(../images/icons-silk/bullet_toggle_plus.png) !important; background-repeat: no-repeat; } +.silk-bullet-white { background-image: url(../images/icons-silk/bullet_white.png) !important; background-repeat: no-repeat; } +.silk-bullet-wrench { background-image: url(../images/icons-silk/bullet_wrench.png) !important; background-repeat: no-repeat; } +.silk-bullet-yellow { background-image: url(../images/icons-silk/bullet_yellow.png) !important; background-repeat: no-repeat; } +.silk-cake { background-image: url(../images/icons-silk/cake.png) !important; background-repeat: no-repeat; } +.silk-calculator { background-image: url(../images/icons-silk/calculator.png) !important; background-repeat: no-repeat; } +.silk-calculator-add { background-image: url(../images/icons-silk/calculator_add.png) !important; background-repeat: no-repeat; } +.silk-calculator-delete { background-image: url(../images/icons-silk/calculator_delete.png) !important; background-repeat: no-repeat; } +.silk-calculator-edit { background-image: url(../images/icons-silk/calculator_edit.png) !important; background-repeat: no-repeat; } +.silk-calculator-error { background-image: url(../images/icons-silk/calculator_error.png) !important; background-repeat: no-repeat; } +.silk-calculator-link { background-image: url(../images/icons-silk/calculator_link.png) !important; background-repeat: no-repeat; } +.silk-calendar { background-image: url(../images/icons-silk/calendar.png) !important; background-repeat: no-repeat; } +.silk-calendar-add { background-image: url(../images/icons-silk/calendar_add.png) !important; background-repeat: no-repeat; } +.silk-calendar-delete { background-image: url(../images/icons-silk/calendar_delete.png) !important; background-repeat: no-repeat; } +.silk-calendar-edit { background-image: url(../images/icons-silk/calendar_edit.png) !important; background-repeat: no-repeat; } +.silk-calendar-link { background-image: url(../images/icons-silk/calendar_link.png) !important; background-repeat: no-repeat; } +.silk-calendar-view-day { background-image: url(../images/icons-silk/calendar_view_day.png) !important; background-repeat: no-repeat; } +.silk-calendar-view-month { background-image: url(../images/icons-silk/calendar_view_month.png) !important; background-repeat: no-repeat; } +.silk-calendar-view-week { background-image: url(../images/icons-silk/calendar_view_week.png) !important; background-repeat: no-repeat; } +.silk-camera { background-image: url(../images/icons-silk/camera.png) !important; background-repeat: no-repeat; } +.silk-camera-add { background-image: url(../images/icons-silk/camera_add.png) !important; background-repeat: no-repeat; } +.silk-camera-delete { background-image: url(../images/icons-silk/camera_delete.png) !important; background-repeat: no-repeat; } +.silk-camera-edit { background-image: url(../images/icons-silk/camera_edit.png) !important; background-repeat: no-repeat; } +.silk-camera-error { background-image: url(../images/icons-silk/camera_error.png) !important; background-repeat: no-repeat; } +.silk-camera-go { background-image: url(../images/icons-silk/camera_go.png) !important; background-repeat: no-repeat; } +.silk-camera-link { background-image: url(../images/icons-silk/camera_link.png) !important; background-repeat: no-repeat; } +.silk-camera-small { background-image: url(../images/icons-silk/camera_small.png) !important; background-repeat: no-repeat; } +.silk-cancel { background-image: url(../images/icons-silk/cancel.png) !important; background-repeat: no-repeat; } +.silk-car { background-image: url(../images/icons-silk/car.png) !important; background-repeat: no-repeat; } +.silk-car-add { background-image: url(../images/icons-silk/car_add.png) !important; background-repeat: no-repeat; } +.silk-car-delete { background-image: url(../images/icons-silk/car_delete.png) !important; background-repeat: no-repeat; } +.silk-cart { background-image: url(../images/icons-silk/cart.png) !important; background-repeat: no-repeat; } +.silk-cart-add { background-image: url(../images/icons-silk/cart_add.png) !important; background-repeat: no-repeat; } +.silk-cart-delete { background-image: url(../images/icons-silk/cart_delete.png) !important; background-repeat: no-repeat; } +.silk-cart-edit { background-image: url(../images/icons-silk/cart_edit.png) !important; background-repeat: no-repeat; } +.silk-cart-error { background-image: url(../images/icons-silk/cart_error.png) !important; background-repeat: no-repeat; } +.silk-cart-go { background-image: url(../images/icons-silk/cart_go.png) !important; background-repeat: no-repeat; } +.silk-cart-put { background-image: url(../images/icons-silk/cart_put.png) !important; background-repeat: no-repeat; } +.silk-cart-remove { background-image: url(../images/icons-silk/cart_remove.png) !important; background-repeat: no-repeat; } +.silk-cd { background-image: url(../images/icons-silk/cd.png) !important; background-repeat: no-repeat; } +.silk-cd-add { background-image: url(../images/icons-silk/cd_add.png) !important; background-repeat: no-repeat; } +.silk-cd-burn { background-image: url(../images/icons-silk/cd_burn.png) !important; background-repeat: no-repeat; } +.silk-cd-delete { background-image: url(../images/icons-silk/cd_delete.png) !important; background-repeat: no-repeat; } +.silk-cd-edit { background-image: url(../images/icons-silk/cd_edit.png) !important; background-repeat: no-repeat; } +.silk-cd-eject { background-image: url(../images/icons-silk/cd_eject.png) !important; background-repeat: no-repeat; } +.silk-cd-go { background-image: url(../images/icons-silk/cd_go.png) !important; background-repeat: no-repeat; } +.silk-chart-bar { background-image: url(../images/icons-silk/chart_bar.png) !important; background-repeat: no-repeat; } +.silk-chart-bar-add { background-image: url(../images/icons-silk/chart_bar_add.png) !important; background-repeat: no-repeat; } +.silk-chart-bar-delete { background-image: url(../images/icons-silk/chart_bar_delete.png) !important; background-repeat: no-repeat; } +.silk-chart-bar-edit { background-image: url(../images/icons-silk/chart_bar_edit.png) !important; background-repeat: no-repeat; } +.silk-chart-bar-error { background-image: url(../images/icons-silk/chart_bar_error.png) !important; background-repeat: no-repeat; } +.silk-chart-bar-link { background-image: url(../images/icons-silk/chart_bar_link.png) !important; background-repeat: no-repeat; } +.silk-chart-curve { background-image: url(../images/icons-silk/chart_curve.png) !important; background-repeat: no-repeat; } +.silk-chart-curve-add { background-image: url(../images/icons-silk/chart_curve_add.png) !important; background-repeat: no-repeat; } +.silk-chart-curve-delete { background-image: url(../images/icons-silk/chart_curve_delete.png) !important; background-repeat: no-repeat; } +.silk-chart-curve-edit { background-image: url(../images/icons-silk/chart_curve_edit.png) !important; background-repeat: no-repeat; } +.silk-chart-curve-error { background-image: url(../images/icons-silk/chart_curve_error.png) !important; background-repeat: no-repeat; } +.silk-chart-curve-go { background-image: url(../images/icons-silk/chart_curve_go.png) !important; background-repeat: no-repeat; } +.silk-chart-curve-link { background-image: url(../images/icons-silk/chart_curve_link.png) !important; background-repeat: no-repeat; } +.silk-chart-line { background-image: url(../images/icons-silk/chart_line.png) !important; background-repeat: no-repeat; } +.silk-chart-line-add { background-image: url(../images/icons-silk/chart_line_add.png) !important; background-repeat: no-repeat; } +.silk-chart-line-delete { background-image: url(../images/icons-silk/chart_line_delete.png) !important; background-repeat: no-repeat; } +.silk-chart-line-edit { background-image: url(../images/icons-silk/chart_line_edit.png) !important; background-repeat: no-repeat; } +.silk-chart-line-error { background-image: url(../images/icons-silk/chart_line_error.png) !important; background-repeat: no-repeat; } +.silk-chart-line-link { background-image: url(../images/icons-silk/chart_line_link.png) !important; background-repeat: no-repeat; } +.silk-chart-organisation { background-image: url(../images/icons-silk/chart_organisation.png) !important; background-repeat: no-repeat; } +.silk-chart-organisation-add { background-image: url(../images/icons-silk/chart_organisation_add.png) !important; background-repeat: no-repeat; } +.silk-chart-organisation-delete { background-image: url(../images/icons-silk/chart_organisation_delete.png) !important; background-repeat: no-repeat; } +.silk-chart-pie { background-image: url(../images/icons-silk/chart_pie.png) !important; background-repeat: no-repeat; } +.silk-chart-pie-add { background-image: url(../images/icons-silk/chart_pie_add.png) !important; background-repeat: no-repeat; } +.silk-chart-pie-delete { background-image: url(../images/icons-silk/chart_pie_delete.png) !important; background-repeat: no-repeat; } +.silk-chart-pie-edit { background-image: url(../images/icons-silk/chart_pie_edit.png) !important; background-repeat: no-repeat; } +.silk-chart-pie-error { background-image: url(../images/icons-silk/chart_pie_error.png) !important; background-repeat: no-repeat; } +.silk-chart-pie-link { background-image: url(../images/icons-silk/chart_pie_link.png) !important; background-repeat: no-repeat; } +.silk-clock { background-image: url(../images/icons-silk/clock.png) !important; background-repeat: no-repeat; } +.silk-clock-add { background-image: url(../images/icons-silk/clock_add.png) !important; background-repeat: no-repeat; } +.silk-clock-delete { background-image: url(../images/icons-silk/clock_delete.png) !important; background-repeat: no-repeat; } +.silk-clock-edit { background-image: url(../images/icons-silk/clock_edit.png) !important; background-repeat: no-repeat; } +.silk-clock-error { background-image: url(../images/icons-silk/clock_error.png) !important; background-repeat: no-repeat; } +.silk-clock-go { background-image: url(../images/icons-silk/clock_go.png) !important; background-repeat: no-repeat; } +.silk-clock-link { background-image: url(../images/icons-silk/clock_link.png) !important; background-repeat: no-repeat; } +.silk-clock-pause { background-image: url(../images/icons-silk/clock_pause.png) !important; background-repeat: no-repeat; } +.silk-clock-play { background-image: url(../images/icons-silk/clock_play.png) !important; background-repeat: no-repeat; } +.silk-clock-red { background-image: url(../images/icons-silk/clock_red.png) !important; background-repeat: no-repeat; } +.silk-clock-stop { background-image: url(../images/icons-silk/clock_stop.png) !important; background-repeat: no-repeat; } +.silk-cog { background-image: url(../images/icons-silk/cog.png) !important; background-repeat: no-repeat; } +.silk-cog-add { background-image: url(../images/icons-silk/cog_add.png) !important; background-repeat: no-repeat; } +.silk-cog-delete { background-image: url(../images/icons-silk/cog_delete.png) !important; background-repeat: no-repeat; } +.silk-cog-edit { background-image: url(../images/icons-silk/cog_edit.png) !important; background-repeat: no-repeat; } +.silk-cog-error { background-image: url(../images/icons-silk/cog_error.png) !important; background-repeat: no-repeat; } +.silk-cog-go { background-image: url(../images/icons-silk/cog_go.png) !important; background-repeat: no-repeat; } +.silk-coins { background-image: url(../images/icons-silk/coins.png) !important; background-repeat: no-repeat; } +.silk-coins-add { background-image: url(../images/icons-silk/coins_add.png) !important; background-repeat: no-repeat; } +.silk-coins-delete { background-image: url(../images/icons-silk/coins_delete.png) !important; background-repeat: no-repeat; } +.silk-color-swatch { background-image: url(../images/icons-silk/color_swatch.png) !important; background-repeat: no-repeat; } +.silk-color-wheel { background-image: url(../images/icons-silk/color_wheel.png) !important; background-repeat: no-repeat; } +.silk-comment { background-image: url(../images/icons-silk/comment.png) !important; background-repeat: no-repeat; } +.silk-comment-add { background-image: url(../images/icons-silk/comment_add.png) !important; background-repeat: no-repeat; } +.silk-comment-delete { background-image: url(../images/icons-silk/comment_delete.png) !important; background-repeat: no-repeat; } +.silk-comment-edit { background-image: url(../images/icons-silk/comment_edit.png) !important; background-repeat: no-repeat; } +.silk-comments { background-image: url(../images/icons-silk/comments.png) !important; background-repeat: no-repeat; } +.silk-comments-add { background-image: url(../images/icons-silk/comments_add.png) !important; background-repeat: no-repeat; } +.silk-comments-delete { background-image: url(../images/icons-silk/comments_delete.png) !important; background-repeat: no-repeat; } +.silk-compress { background-image: url(../images/icons-silk/compress.png) !important; background-repeat: no-repeat; } +.silk-computer { background-image: url(../images/icons-silk/computer.png) !important; background-repeat: no-repeat; } +.silk-computer-add { background-image: url(../images/icons-silk/computer_add.png) !important; background-repeat: no-repeat; } +.silk-computer-delete { background-image: url(../images/icons-silk/computer_delete.png) !important; background-repeat: no-repeat; } +.silk-computer-edit { background-image: url(../images/icons-silk/computer_edit.png) !important; background-repeat: no-repeat; } +.silk-computer-error { background-image: url(../images/icons-silk/computer_error.png) !important; background-repeat: no-repeat; } +.silk-computer-go { background-image: url(../images/icons-silk/computer_go.png) !important; background-repeat: no-repeat; } +.silk-computer-key { background-image: url(../images/icons-silk/computer_key.png) !important; background-repeat: no-repeat; } +.silk-computer-link { background-image: url(../images/icons-silk/computer_link.png) !important; background-repeat: no-repeat; } +.silk-connect { background-image: url(../images/icons-silk/connect.png) !important; background-repeat: no-repeat; } +.silk-contrast { background-image: url(../images/icons-silk/contrast.png) !important; background-repeat: no-repeat; } +.silk-contrast-decrease { background-image: url(../images/icons-silk/contrast_decrease.png) !important; background-repeat: no-repeat; } +.silk-contrast-high { background-image: url(../images/icons-silk/contrast_high.png) !important; background-repeat: no-repeat; } +.silk-contrast-increase { background-image: url(../images/icons-silk/contrast_increase.png) !important; background-repeat: no-repeat; } +.silk-contrast-low { background-image: url(../images/icons-silk/contrast_low.png) !important; background-repeat: no-repeat; } +.silk-control-eject { background-image: url(../images/icons-silk/control_eject.png) !important; background-repeat: no-repeat; } +.silk-control-eject-blue { background-image: url(../images/icons-silk/control_eject_blue.png) !important; background-repeat: no-repeat; } +.silk-control-end { background-image: url(../images/icons-silk/control_end.png) !important; background-repeat: no-repeat; } +.silk-control-end-blue { background-image: url(../images/icons-silk/control_end_blue.png) !important; background-repeat: no-repeat; } +.silk-control-equalizer { background-image: url(../images/icons-silk/control_equalizer.png) !important; background-repeat: no-repeat; } +.silk-control-equalizer-blue { background-image: url(../images/icons-silk/control_equalizer_blue.png) !important; background-repeat: no-repeat; } +.silk-control-fastforward { background-image: url(../images/icons-silk/control_fastforward.png) !important; background-repeat: no-repeat; } +.silk-control-fastforward-blue { background-image: url(../images/icons-silk/control_fastforward_blue.png) !important; background-repeat: no-repeat; } +.silk-control-pause { background-image: url(../images/icons-silk/control_pause.png) !important; background-repeat: no-repeat; } +.silk-control-pause-blue { background-image: url(../images/icons-silk/control_pause_blue.png) !important; background-repeat: no-repeat; } +.silk-control-play { background-image: url(../images/icons-silk/control_play.png) !important; background-repeat: no-repeat; } +.silk-control-play-blue { background-image: url(../images/icons-silk/control_play_blue.png) !important; background-repeat: no-repeat; } +.silk-control-repeat { background-image: url(../images/icons-silk/control_repeat.png) !important; background-repeat: no-repeat; } +.silk-control-repeat-blue { background-image: url(../images/icons-silk/control_repeat_blue.png) !important; background-repeat: no-repeat; } +.silk-control-rewind { background-image: url(../images/icons-silk/control_rewind.png) !important; background-repeat: no-repeat; } +.silk-control-rewind-blue { background-image: url(../images/icons-silk/control_rewind_blue.png) !important; background-repeat: no-repeat; } +.silk-control-start { background-image: url(../images/icons-silk/control_start.png) !important; background-repeat: no-repeat; } +.silk-control-start-blue { background-image: url(../images/icons-silk/control_start_blue.png) !important; background-repeat: no-repeat; } +.silk-control-stop { background-image: url(../images/icons-silk/control_stop.png) !important; background-repeat: no-repeat; } +.silk-control-stop-blue { background-image: url(../images/icons-silk/control_stop_blue.png) !important; background-repeat: no-repeat; } +.silk-controller { background-image: url(../images/icons-silk/controller.png) !important; background-repeat: no-repeat; } +.silk-controller-add { background-image: url(../images/icons-silk/controller_add.png) !important; background-repeat: no-repeat; } +.silk-controller-delete { background-image: url(../images/icons-silk/controller_delete.png) !important; background-repeat: no-repeat; } +.silk-controller-error { background-image: url(../images/icons-silk/controller_error.png) !important; background-repeat: no-repeat; } +.silk-creditcards { background-image: url(../images/icons-silk/creditcards.png) !important; background-repeat: no-repeat; } +.silk-cross { background-image: url(../images/icons-silk/cross.png) !important; background-repeat: no-repeat; } +.silk-css { background-image: url(../images/icons-silk/css.png) !important; background-repeat: no-repeat; } +.silk-css-add { background-image: url(../images/icons-silk/css_add.png) !important; background-repeat: no-repeat; } +.silk-css-delete { background-image: url(../images/icons-silk/css_delete.png) !important; background-repeat: no-repeat; } +.silk-css-go { background-image: url(../images/icons-silk/css_go.png) !important; background-repeat: no-repeat; } +.silk-css-valid { background-image: url(../images/icons-silk/css_valid.png) !important; background-repeat: no-repeat; } +.silk-cup { background-image: url(../images/icons-silk/cup.png) !important; background-repeat: no-repeat; } +.silk-cup-add { background-image: url(../images/icons-silk/cup_add.png) !important; background-repeat: no-repeat; } +.silk-cup-delete { background-image: url(../images/icons-silk/cup_delete.png) !important; background-repeat: no-repeat; } +.silk-cup-edit { background-image: url(../images/icons-silk/cup_edit.png) !important; background-repeat: no-repeat; } +.silk-cup-error { background-image: url(../images/icons-silk/cup_error.png) !important; background-repeat: no-repeat; } +.silk-cup-go { background-image: url(../images/icons-silk/cup_go.png) !important; background-repeat: no-repeat; } +.silk-cup-key { background-image: url(../images/icons-silk/cup_key.png) !important; background-repeat: no-repeat; } +.silk-cup-link { background-image: url(../images/icons-silk/cup_link.png) !important; background-repeat: no-repeat; } +.silk-cursor { background-image: url(../images/icons-silk/cursor.png) !important; background-repeat: no-repeat; } +.silk-cut { background-image: url(../images/icons-silk/cut.png) !important; background-repeat: no-repeat; } +.silk-cut-red { background-image: url(../images/icons-silk/cut_red.png) !important; background-repeat: no-repeat; } +.silk-database { background-image: url(../images/icons-silk/database.png) !important; background-repeat: no-repeat; } +.silk-database-add { background-image: url(../images/icons-silk/database_add.png) !important; background-repeat: no-repeat; } +.silk-database-connect { background-image: url(../images/icons-silk/database_connect.png) !important; background-repeat: no-repeat; } +.silk-database-delete { background-image: url(../images/icons-silk/database_delete.png) !important; background-repeat: no-repeat; } +.silk-database-edit { background-image: url(../images/icons-silk/database_edit.png) !important; background-repeat: no-repeat; } +.silk-database-error { background-image: url(../images/icons-silk/database_error.png) !important; background-repeat: no-repeat; } +.silk-database-gear { background-image: url(../images/icons-silk/database_gear.png) !important; background-repeat: no-repeat; } +.silk-database-go { background-image: url(../images/icons-silk/database_go.png) !important; background-repeat: no-repeat; } +.silk-database-key { background-image: url(../images/icons-silk/database_key.png) !important; background-repeat: no-repeat; } +.silk-database-lightning { background-image: url(../images/icons-silk/database_lightning.png) !important; background-repeat: no-repeat; } +.silk-database-link { background-image: url(../images/icons-silk/database_link.png) !important; background-repeat: no-repeat; } +.silk-database-refresh { background-image: url(../images/icons-silk/database_refresh.png) !important; background-repeat: no-repeat; } +.silk-database-save { background-image: url(../images/icons-silk/database_save.png) !important; background-repeat: no-repeat; } +.silk-database-table { background-image: url(../images/icons-silk/database_table.png) !important; background-repeat: no-repeat; } +.silk-date { background-image: url(../images/icons-silk/date.png) !important; background-repeat: no-repeat; } +.silk-date-add { background-image: url(../images/icons-silk/date_add.png) !important; background-repeat: no-repeat; } +.silk-date-delete { background-image: url(../images/icons-silk/date_delete.png) !important; background-repeat: no-repeat; } +.silk-date-edit { background-image: url(../images/icons-silk/date_edit.png) !important; background-repeat: no-repeat; } +.silk-date-error { background-image: url(../images/icons-silk/date_error.png) !important; background-repeat: no-repeat; } +.silk-date-go { background-image: url(../images/icons-silk/date_go.png) !important; background-repeat: no-repeat; } +.silk-date-link { background-image: url(../images/icons-silk/date_link.png) !important; background-repeat: no-repeat; } +.silk-date-magnify { background-image: url(../images/icons-silk/date_magnify.png) !important; background-repeat: no-repeat; } +.silk-date-next { background-image: url(../images/icons-silk/date_next.png) !important; background-repeat: no-repeat; } +.silk-date-previous { background-image: url(../images/icons-silk/date_previous.png) !important; background-repeat: no-repeat; } +.silk-delete { background-image: url(../images/icons-silk/delete.png) !important; background-repeat: no-repeat; } +.silk-disconnect { background-image: url(../images/icons-silk/disconnect.png) !important; background-repeat: no-repeat; } +.silk-disk { background-image: url(../images/icons-silk/disk.png) !important; background-repeat: no-repeat; } +.silk-disk-multiple { background-image: url(../images/icons-silk/disk_multiple.png) !important; background-repeat: no-repeat; } +.silk-door { background-image: url(../images/icons-silk/door.png) !important; background-repeat: no-repeat; } +.silk-door-in { background-image: url(../images/icons-silk/door_in.png) !important; background-repeat: no-repeat; } +.silk-door-open { background-image: url(../images/icons-silk/door_open.png) !important; background-repeat: no-repeat; } +.silk-door-out { background-image: url(../images/icons-silk/door_out.png) !important; background-repeat: no-repeat; } +.silk-drink { background-image: url(../images/icons-silk/drink.png) !important; background-repeat: no-repeat; } +.silk-drink-empty { background-image: url(../images/icons-silk/drink_empty.png) !important; background-repeat: no-repeat; } +.silk-drive { background-image: url(../images/icons-silk/drive.png) !important; background-repeat: no-repeat; } +.silk-drive-add { background-image: url(../images/icons-silk/drive_add.png) !important; background-repeat: no-repeat; } +.silk-drive-burn { background-image: url(../images/icons-silk/drive_burn.png) !important; background-repeat: no-repeat; } +.silk-drive-cd { background-image: url(../images/icons-silk/drive_cd.png) !important; background-repeat: no-repeat; } +.silk-drive-cd-empty { background-image: url(../images/icons-silk/drive_cd_empty.png) !important; background-repeat: no-repeat; } +.silk-drive-delete { background-image: url(../images/icons-silk/drive_delete.png) !important; background-repeat: no-repeat; } +.silk-drive-disk { background-image: url(../images/icons-silk/drive_disk.png) !important; background-repeat: no-repeat; } +.silk-drive-edit { background-image: url(../images/icons-silk/drive_edit.png) !important; background-repeat: no-repeat; } +.silk-drive-error { background-image: url(../images/icons-silk/drive_error.png) !important; background-repeat: no-repeat; } +.silk-drive-go { background-image: url(../images/icons-silk/drive_go.png) !important; background-repeat: no-repeat; } +.silk-drive-key { background-image: url(../images/icons-silk/drive_key.png) !important; background-repeat: no-repeat; } +.silk-drive-link { background-image: url(../images/icons-silk/drive_link.png) !important; background-repeat: no-repeat; } +.silk-drive-magnify { background-image: url(../images/icons-silk/drive_magnify.png) !important; background-repeat: no-repeat; } +.silk-drive-network { background-image: url(../images/icons-silk/drive_network.png) !important; background-repeat: no-repeat; } +.silk-drive-rename { background-image: url(../images/icons-silk/drive_rename.png) !important; background-repeat: no-repeat; } +.silk-drive-user { background-image: url(../images/icons-silk/drive_user.png) !important; background-repeat: no-repeat; } +.silk-drive-web { background-image: url(../images/icons-silk/drive_web.png) !important; background-repeat: no-repeat; } +.silk-dvd { background-image: url(../images/icons-silk/dvd.png) !important; background-repeat: no-repeat; } +.silk-dvd-add { background-image: url(../images/icons-silk/dvd_add.png) !important; background-repeat: no-repeat; } +.silk-dvd-delete { background-image: url(../images/icons-silk/dvd_delete.png) !important; background-repeat: no-repeat; } +.silk-dvd-edit { background-image: url(../images/icons-silk/dvd_edit.png) !important; background-repeat: no-repeat; } +.silk-dvd-error { background-image: url(../images/icons-silk/dvd_error.png) !important; background-repeat: no-repeat; } +.silk-dvd-go { background-image: url(../images/icons-silk/dvd_go.png) !important; background-repeat: no-repeat; } +.silk-dvd-key { background-image: url(../images/icons-silk/dvd_key.png) !important; background-repeat: no-repeat; } +.silk-dvd-link { background-image: url(../images/icons-silk/dvd_link.png) !important; background-repeat: no-repeat; } +.silk-email { background-image: url(../images/icons-silk/email.png) !important; background-repeat: no-repeat; } +.silk-email-add { background-image: url(../images/icons-silk/email_add.png) !important; background-repeat: no-repeat; } +.silk-email-attach { background-image: url(../images/icons-silk/email_attach.png) !important; background-repeat: no-repeat; } +.silk-email-delete { background-image: url(../images/icons-silk/email_delete.png) !important; background-repeat: no-repeat; } +.silk-email-edit { background-image: url(../images/icons-silk/email_edit.png) !important; background-repeat: no-repeat; } +.silk-email-error { background-image: url(../images/icons-silk/email_error.png) !important; background-repeat: no-repeat; } +.silk-email-go { background-image: url(../images/icons-silk/email_go.png) !important; background-repeat: no-repeat; } +.silk-email-link { background-image: url(../images/icons-silk/email_link.png) !important; background-repeat: no-repeat; } +.silk-email-open { background-image: url(../images/icons-silk/email_open.png) !important; background-repeat: no-repeat; } +.silk-email-open-image { background-image: url(../images/icons-silk/email_open_image.png) !important; background-repeat: no-repeat; } +.silk-emoticon-evilgrin { background-image: url(../images/icons-silk/emoticon_evilgrin.png) !important; background-repeat: no-repeat; } +.silk-emoticon-grin { background-image: url(../images/icons-silk/emoticon_grin.png) !important; background-repeat: no-repeat; } +.silk-emoticon-happy { background-image: url(../images/icons-silk/emoticon_happy.png) !important; background-repeat: no-repeat; } +.silk-emoticon-smile { background-image: url(../images/icons-silk/emoticon_smile.png) !important; background-repeat: no-repeat; } +.silk-emoticon-surprised { background-image: url(../images/icons-silk/emoticon_surprised.png) !important; background-repeat: no-repeat; } +.silk-emoticon-tongue { background-image: url(../images/icons-silk/emoticon_tongue.png) !important; background-repeat: no-repeat; } +.silk-emoticon-unhappy { background-image: url(../images/icons-silk/emoticon_unhappy.png) !important; background-repeat: no-repeat; } +.silk-emoticon-waii { background-image: url(../images/icons-silk/emoticon_waii.png) !important; background-repeat: no-repeat; } +.silk-emoticon-wink { background-image: url(../images/icons-silk/emoticon_wink.png) !important; background-repeat: no-repeat; } +.silk-error { background-image: url(../images/icons-silk/error.png) !important; background-repeat: no-repeat; } +.silk-error-add { background-image: url(../images/icons-silk/error_add.png) !important; background-repeat: no-repeat; } +.silk-error-delete { background-image: url(../images/icons-silk/error_delete.png) !important; background-repeat: no-repeat; } +.silk-error-go { background-image: url(../images/icons-silk/error_go.png) !important; background-repeat: no-repeat; } +.silk-exclamation { background-image: url(../images/icons-silk/exclamation.png) !important; background-repeat: no-repeat; } +.silk-eye { background-image: url(../images/icons-silk/eye.png) !important; background-repeat: no-repeat; } +.silk-feed { background-image: url(../images/icons-silk/feed.png) !important; background-repeat: no-repeat; } +.silk-feed-add { background-image: url(../images/icons-silk/feed_add.png) !important; background-repeat: no-repeat; } +.silk-feed-delete { background-image: url(../images/icons-silk/feed_delete.png) !important; background-repeat: no-repeat; } +.silk-feed-disk { background-image: url(../images/icons-silk/feed_disk.png) !important; background-repeat: no-repeat; } +.silk-feed-edit { background-image: url(../images/icons-silk/feed_edit.png) !important; background-repeat: no-repeat; } +.silk-feed-error { background-image: url(../images/icons-silk/feed_error.png) !important; background-repeat: no-repeat; } +.silk-feed-go { background-image: url(../images/icons-silk/feed_go.png) !important; background-repeat: no-repeat; } +.silk-feed-key { background-image: url(../images/icons-silk/feed_key.png) !important; background-repeat: no-repeat; } +.silk-feed-link { background-image: url(../images/icons-silk/feed_link.png) !important; background-repeat: no-repeat; } +.silk-feed-magnify { background-image: url(../images/icons-silk/feed_magnify.png) !important; background-repeat: no-repeat; } +.silk-female { background-image: url(../images/icons-silk/female.png) !important; background-repeat: no-repeat; } +.silk-film { background-image: url(../images/icons-silk/film.png) !important; background-repeat: no-repeat; } +.silk-film-add { background-image: url(../images/icons-silk/film_add.png) !important; background-repeat: no-repeat; } +.silk-film-delete { background-image: url(../images/icons-silk/film_delete.png) !important; background-repeat: no-repeat; } +.silk-film-edit { background-image: url(../images/icons-silk/film_edit.png) !important; background-repeat: no-repeat; } +.silk-film-error { background-image: url(../images/icons-silk/film_error.png) !important; background-repeat: no-repeat; } +.silk-film-go { background-image: url(../images/icons-silk/film_go.png) !important; background-repeat: no-repeat; } +.silk-film-key { background-image: url(../images/icons-silk/film_key.png) !important; background-repeat: no-repeat; } +.silk-film-link { background-image: url(../images/icons-silk/film_link.png) !important; background-repeat: no-repeat; } +.silk-film-save { background-image: url(../images/icons-silk/film_save.png) !important; background-repeat: no-repeat; } +.silk-find { background-image: url(../images/icons-silk/find.png) !important; background-repeat: no-repeat; } +.silk-flag-blue { background-image: url(../images/icons-silk/flag_blue.png) !important; background-repeat: no-repeat; } +.silk-flag-green { background-image: url(../images/icons-silk/flag_green.png) !important; background-repeat: no-repeat; } +.silk-flag-orange { background-image: url(../images/icons-silk/flag_orange.png) !important; background-repeat: no-repeat; } +.silk-flag-pink { background-image: url(../images/icons-silk/flag_pink.png) !important; background-repeat: no-repeat; } +.silk-flag-purple { background-image: url(../images/icons-silk/flag_purple.png) !important; background-repeat: no-repeat; } +.silk-flag-red { background-image: url(../images/icons-silk/flag_red.png) !important; background-repeat: no-repeat; } +.silk-flag-yellow { background-image: url(../images/icons-silk/flag_yellow.png) !important; background-repeat: no-repeat; } +.silk-folder { background-image: url(../images/icons-silk/folder.png) !important; background-repeat: no-repeat; } +.silk-folder-add { background-image: url(../images/icons-silk/folder_add.png) !important; background-repeat: no-repeat; } +.silk-folder-bell { background-image: url(../images/icons-silk/folder_bell.png) !important; background-repeat: no-repeat; } +.silk-folder-brick { background-image: url(../images/icons-silk/folder_brick.png) !important; background-repeat: no-repeat; } +.silk-folder-bug { background-image: url(../images/icons-silk/folder_bug.png) !important; background-repeat: no-repeat; } +.silk-folder-camera { background-image: url(../images/icons-silk/folder_camera.png) !important; background-repeat: no-repeat; } +.silk-folder-database { background-image: url(../images/icons-silk/folder_database.png) !important; background-repeat: no-repeat; } +.silk-folder-delete { background-image: url(../images/icons-silk/folder_delete.png) !important; background-repeat: no-repeat; } +.silk-folder-edit { background-image: url(../images/icons-silk/folder_edit.png) !important; background-repeat: no-repeat; } +.silk-folder-error { background-image: url(../images/icons-silk/folder_error.png) !important; background-repeat: no-repeat; } +.silk-folder-explore { background-image: url(../images/icons-silk/folder_explore.png) !important; background-repeat: no-repeat; } +.silk-folder-feed { background-image: url(../images/icons-silk/folder_feed.png) !important; background-repeat: no-repeat; } +.silk-folder-find { background-image: url(../images/icons-silk/folder_find.png) !important; background-repeat: no-repeat; } +.silk-folder-go { background-image: url(../images/icons-silk/folder_go.png) !important; background-repeat: no-repeat; } +.silk-folder-heart { background-image: url(../images/icons-silk/folder_heart.png) !important; background-repeat: no-repeat; } +.silk-folder-image { background-image: url(../images/icons-silk/folder_image.png) !important; background-repeat: no-repeat; } +.silk-folder-key { background-image: url(../images/icons-silk/folder_key.png) !important; background-repeat: no-repeat; } +.silk-folder-lightbulb { background-image: url(../images/icons-silk/folder_lightbulb.png) !important; background-repeat: no-repeat; } +.silk-folder-link { background-image: url(../images/icons-silk/folder_link.png) !important; background-repeat: no-repeat; } +.silk-folder-magnify { background-image: url(../images/icons-silk/folder_magnify.png) !important; background-repeat: no-repeat; } +.silk-folder-page { background-image: url(../images/icons-silk/folder_page.png) !important; background-repeat: no-repeat; } +.silk-folder-page-white { background-image: url(../images/icons-silk/folder_page_white.png) !important; background-repeat: no-repeat; } +.silk-folder-palette { background-image: url(../images/icons-silk/folder_palette.png) !important; background-repeat: no-repeat; } +.silk-folder-picture { background-image: url(../images/icons-silk/folder_picture.png) !important; background-repeat: no-repeat; } +.silk-folder-star { background-image: url(../images/icons-silk/folder_star.png) !important; background-repeat: no-repeat; } +.silk-folder-table { background-image: url(../images/icons-silk/folder_table.png) !important; background-repeat: no-repeat; } +.silk-folder-user { background-image: url(../images/icons-silk/folder_user.png) !important; background-repeat: no-repeat; } +.silk-folder-wrench { background-image: url(../images/icons-silk/folder_wrench.png) !important; background-repeat: no-repeat; } +.silk-font { background-image: url(../images/icons-silk/font.png) !important; background-repeat: no-repeat; } +.silk-font-add { background-image: url(../images/icons-silk/font_add.png) !important; background-repeat: no-repeat; } +.silk-font-delete { background-image: url(../images/icons-silk/font_delete.png) !important; background-repeat: no-repeat; } +.silk-font-go { background-image: url(../images/icons-silk/font_go.png) !important; background-repeat: no-repeat; } +.silk-group { background-image: url(../images/icons-silk/group.png) !important; background-repeat: no-repeat; } +.silk-group-add { background-image: url(../images/icons-silk/group_add.png) !important; background-repeat: no-repeat; } +.silk-group-delete { background-image: url(../images/icons-silk/group_delete.png) !important; background-repeat: no-repeat; } +.silk-group-edit { background-image: url(../images/icons-silk/group_edit.png) !important; background-repeat: no-repeat; } +.silk-group-error { background-image: url(../images/icons-silk/group_error.png) !important; background-repeat: no-repeat; } +.silk-group-gear { background-image: url(../images/icons-silk/group_gear.png) !important; background-repeat: no-repeat; } +.silk-group-go { background-image: url(../images/icons-silk/group_go.png) !important; background-repeat: no-repeat; } +.silk-group-key { background-image: url(../images/icons-silk/group_key.png) !important; background-repeat: no-repeat; } +.silk-group-link { background-image: url(../images/icons-silk/group_link.png) !important; background-repeat: no-repeat; } +.silk-heart { background-image: url(../images/icons-silk/heart.png) !important; background-repeat: no-repeat; } +.silk-heart-add { background-image: url(../images/icons-silk/heart_add.png) !important; background-repeat: no-repeat; } +.silk-heart-delete { background-image: url(../images/icons-silk/heart_delete.png) !important; background-repeat: no-repeat; } +.silk-help { background-image: url(../images/icons-silk/help.png) !important; background-repeat: no-repeat; } +.silk-hourglass { background-image: url(../images/icons-silk/hourglass.png) !important; background-repeat: no-repeat; } +.silk-hourglass-add { background-image: url(../images/icons-silk/hourglass_add.png) !important; background-repeat: no-repeat; } +.silk-hourglass-delete { background-image: url(../images/icons-silk/hourglass_delete.png) !important; background-repeat: no-repeat; } +.silk-hourglass-go { background-image: url(../images/icons-silk/hourglass_go.png) !important; background-repeat: no-repeat; } +.silk-hourglass-link { background-image: url(../images/icons-silk/hourglass_link.png) !important; background-repeat: no-repeat; } +.silk-house { background-image: url(../images/icons-silk/house.png) !important; background-repeat: no-repeat; } +.silk-house-go { background-image: url(../images/icons-silk/house_go.png) !important; background-repeat: no-repeat; } +.silk-house-link { background-image: url(../images/icons-silk/house_link.png) !important; background-repeat: no-repeat; } +.silk-html { background-image: url(../images/icons-silk/html.png) !important; background-repeat: no-repeat; } +.silk-html-add { background-image: url(../images/icons-silk/html_add.png) !important; background-repeat: no-repeat; } +.silk-html-delete { background-image: url(../images/icons-silk/html_delete.png) !important; background-repeat: no-repeat; } +.silk-html-go { background-image: url(../images/icons-silk/html_go.png) !important; background-repeat: no-repeat; } +.silk-html-valid { background-image: url(../images/icons-silk/html_valid.png) !important; background-repeat: no-repeat; } +.silk-image { background-image: url(../images/icons-silk/image.png) !important; background-repeat: no-repeat; } +.silk-image-add { background-image: url(../images/icons-silk/image_add.png) !important; background-repeat: no-repeat; } +.silk-image-delete { background-image: url(../images/icons-silk/image_delete.png) !important; background-repeat: no-repeat; } +.silk-image-edit { background-image: url(../images/icons-silk/image_edit.png) !important; background-repeat: no-repeat; } +.silk-image-link { background-image: url(../images/icons-silk/image_link.png) !important; background-repeat: no-repeat; } +.silk-images { background-image: url(../images/icons-silk/images.png) !important; background-repeat: no-repeat; } +.silk-information { background-image: url(../images/icons-silk/information.png) !important; background-repeat: no-repeat; } +.silk-ipod { background-image: url(../images/icons-silk/ipod.png) !important; background-repeat: no-repeat; } +.silk-ipod-cast { background-image: url(../images/icons-silk/ipod_cast.png) !important; background-repeat: no-repeat; } +.silk-ipod-cast-add { background-image: url(../images/icons-silk/ipod_cast_add.png) !important; background-repeat: no-repeat; } +.silk-ipod-cast-delete { background-image: url(../images/icons-silk/ipod_cast_delete.png) !important; background-repeat: no-repeat; } +.silk-ipod-sound { background-image: url(../images/icons-silk/ipod_sound.png) !important; background-repeat: no-repeat; } +.silk-joystick { background-image: url(../images/icons-silk/joystick.png) !important; background-repeat: no-repeat; } +.silk-joystick-add { background-image: url(../images/icons-silk/joystick_add.png) !important; background-repeat: no-repeat; } +.silk-joystick-delete { background-image: url(../images/icons-silk/joystick_delete.png) !important; background-repeat: no-repeat; } +.silk-joystick-error { background-image: url(../images/icons-silk/joystick_error.png) !important; background-repeat: no-repeat; } +.silk-key { background-image: url(../images/icons-silk/key.png) !important; background-repeat: no-repeat; } +.silk-key-add { background-image: url(../images/icons-silk/key_add.png) !important; background-repeat: no-repeat; } +.silk-key-delete { background-image: url(../images/icons-silk/key_delete.png) !important; background-repeat: no-repeat; } +.silk-key-go { background-image: url(../images/icons-silk/key_go.png) !important; background-repeat: no-repeat; } +.silk-keyboard { background-image: url(../images/icons-silk/keyboard.png) !important; background-repeat: no-repeat; } +.silk-keyboard-add { background-image: url(../images/icons-silk/keyboard_add.png) !important; background-repeat: no-repeat; } +.silk-keyboard-delete { background-image: url(../images/icons-silk/keyboard_delete.png) !important; background-repeat: no-repeat; } +.silk-keyboard-magnify { background-image: url(../images/icons-silk/keyboard_magnify.png) !important; background-repeat: no-repeat; } +.silk-layers { background-image: url(../images/icons-silk/layers.png) !important; background-repeat: no-repeat; } +.silk-layout { background-image: url(../images/icons-silk/layout.png) !important; background-repeat: no-repeat; } +.silk-layout-add { background-image: url(../images/icons-silk/layout_add.png) !important; background-repeat: no-repeat; } +.silk-layout-content { background-image: url(../images/icons-silk/layout_content.png) !important; background-repeat: no-repeat; } +.silk-layout-delete { background-image: url(../images/icons-silk/layout_delete.png) !important; background-repeat: no-repeat; } +.silk-layout-edit { background-image: url(../images/icons-silk/layout_edit.png) !important; background-repeat: no-repeat; } +.silk-layout-error { background-image: url(../images/icons-silk/layout_error.png) !important; background-repeat: no-repeat; } +.silk-layout-header { background-image: url(../images/icons-silk/layout_header.png) !important; background-repeat: no-repeat; } +.silk-layout-link { background-image: url(../images/icons-silk/layout_link.png) !important; background-repeat: no-repeat; } +.silk-layout-sidebar { background-image: url(../images/icons-silk/layout_sidebar.png) !important; background-repeat: no-repeat; } +.silk-lightbulb { background-image: url(../images/icons-silk/lightbulb.png) !important; background-repeat: no-repeat; } +.silk-lightbulb-add { background-image: url(../images/icons-silk/lightbulb_add.png) !important; background-repeat: no-repeat; } +.silk-lightbulb-delete { background-image: url(../images/icons-silk/lightbulb_delete.png) !important; background-repeat: no-repeat; } +.silk-lightbulb-off { background-image: url(../images/icons-silk/lightbulb_off.png) !important; background-repeat: no-repeat; } +.silk-lightning { background-image: url(../images/icons-silk/lightning.png) !important; background-repeat: no-repeat; } +.silk-lightning-add { background-image: url(../images/icons-silk/lightning_add.png) !important; background-repeat: no-repeat; } +.silk-lightning-delete { background-image: url(../images/icons-silk/lightning_delete.png) !important; background-repeat: no-repeat; } +.silk-lightning-go { background-image: url(../images/icons-silk/lightning_go.png) !important; background-repeat: no-repeat; } +.silk-link { background-image: url(../images/icons-silk/link.png) !important; background-repeat: no-repeat; } +.silk-link-add { background-image: url(../images/icons-silk/link_add.png) !important; background-repeat: no-repeat; } +.silk-link-break { background-image: url(../images/icons-silk/link_break.png) !important; background-repeat: no-repeat; } +.silk-link-delete { background-image: url(../images/icons-silk/link_delete.png) !important; background-repeat: no-repeat; } +.silk-link-edit { background-image: url(../images/icons-silk/link_edit.png) !important; background-repeat: no-repeat; } +.silk-link-error { background-image: url(../images/icons-silk/link_error.png) !important; background-repeat: no-repeat; } +.silk-link-go { background-image: url(../images/icons-silk/link_go.png) !important; background-repeat: no-repeat; } +.silk-lock { background-image: url(../images/icons-silk/lock.png) !important; background-repeat: no-repeat; } +.silk-lock-add { background-image: url(../images/icons-silk/lock_add.png) !important; background-repeat: no-repeat; } +.silk-lock-break { background-image: url(../images/icons-silk/lock_break.png) !important; background-repeat: no-repeat; } +.silk-lock-delete { background-image: url(../images/icons-silk/lock_delete.png) !important; background-repeat: no-repeat; } +.silk-lock-edit { background-image: url(../images/icons-silk/lock_edit.png) !important; background-repeat: no-repeat; } +.silk-lock-go { background-image: url(../images/icons-silk/lock_go.png) !important; background-repeat: no-repeat; } +.silk-lock-open { background-image: url(../images/icons-silk/lock_open.png) !important; background-repeat: no-repeat; } +.silk-lorry { background-image: url(../images/icons-silk/lorry.png) !important; background-repeat: no-repeat; } +.silk-lorry-add { background-image: url(../images/icons-silk/lorry_add.png) !important; background-repeat: no-repeat; } +.silk-lorry-delete { background-image: url(../images/icons-silk/lorry_delete.png) !important; background-repeat: no-repeat; } +.silk-lorry-error { background-image: url(../images/icons-silk/lorry_error.png) !important; background-repeat: no-repeat; } +.silk-lorry-flatbed { background-image: url(../images/icons-silk/lorry_flatbed.png) !important; background-repeat: no-repeat; } +.silk-lorry-go { background-image: url(../images/icons-silk/lorry_go.png) !important; background-repeat: no-repeat; } +.silk-lorry-link { background-image: url(../images/icons-silk/lorry_link.png) !important; background-repeat: no-repeat; } +.silk-magifier-zoom-out { background-image: url(../images/icons-silk/magifier_zoom_out.png) !important; background-repeat: no-repeat; } +.silk-magnifier { background-image: url(../images/icons-silk/magnifier.png) !important; background-repeat: no-repeat; } +.silk-magnifier-zoom-in { background-image: url(../images/icons-silk/magnifier_zoom_in.png) !important; background-repeat: no-repeat; } +.silk-male { background-image: url(../images/icons-silk/male.png) !important; background-repeat: no-repeat; } +.silk-map { background-image: url(../images/icons-silk/map.png) !important; background-repeat: no-repeat; } +.silk-map-add { background-image: url(../images/icons-silk/map_add.png) !important; background-repeat: no-repeat; } +.silk-map-delete { background-image: url(../images/icons-silk/map_delete.png) !important; background-repeat: no-repeat; } +.silk-map-edit { background-image: url(../images/icons-silk/map_edit.png) !important; background-repeat: no-repeat; } +.silk-map-go { background-image: url(../images/icons-silk/map_go.png) !important; background-repeat: no-repeat; } +.silk-map-magnify { background-image: url(../images/icons-silk/map_magnify.png) !important; background-repeat: no-repeat; } +.silk-medal-bronze-1 { background-image: url(../images/icons-silk/medal_bronze_1.png) !important; background-repeat: no-repeat; } +.silk-medal-bronze-2 { background-image: url(../images/icons-silk/medal_bronze_2.png) !important; background-repeat: no-repeat; } +.silk-medal-bronze-3 { background-image: url(../images/icons-silk/medal_bronze_3.png) !important; background-repeat: no-repeat; } +.silk-medal-bronze-add { background-image: url(../images/icons-silk/medal_bronze_add.png) !important; background-repeat: no-repeat; } +.silk-medal-bronze-delete { background-image: url(../images/icons-silk/medal_bronze_delete.png) !important; background-repeat: no-repeat; } +.silk-medal-gold-1 { background-image: url(../images/icons-silk/medal_gold_1.png) !important; background-repeat: no-repeat; } +.silk-medal-gold-2 { background-image: url(../images/icons-silk/medal_gold_2.png) !important; background-repeat: no-repeat; } +.silk-medal-gold-3 { background-image: url(../images/icons-silk/medal_gold_3.png) !important; background-repeat: no-repeat; } +.silk-medal-gold-add { background-image: url(../images/icons-silk/medal_gold_add.png) !important; background-repeat: no-repeat; } +.silk-medal-gold-delete { background-image: url(../images/icons-silk/medal_gold_delete.png) !important; background-repeat: no-repeat; } +.silk-medal-silver-1 { background-image: url(../images/icons-silk/medal_silver_1.png) !important; background-repeat: no-repeat; } +.silk-medal-silver-2 { background-image: url(../images/icons-silk/medal_silver_2.png) !important; background-repeat: no-repeat; } +.silk-medal-silver-3 { background-image: url(../images/icons-silk/medal_silver_3.png) !important; background-repeat: no-repeat; } +.silk-medal-silver-add { background-image: url(../images/icons-silk/medal_silver_add.png) !important; background-repeat: no-repeat; } +.silk-medal-silver-delete { background-image: url(../images/icons-silk/medal_silver_delete.png) !important; background-repeat: no-repeat; } +.silk-money { background-image: url(../images/icons-silk/money.png) !important; background-repeat: no-repeat; } +.silk-money-add { background-image: url(../images/icons-silk/money_add.png) !important; background-repeat: no-repeat; } +.silk-money-delete { background-image: url(../images/icons-silk/money_delete.png) !important; background-repeat: no-repeat; } +.silk-money-dollar { background-image: url(../images/icons-silk/money_dollar.png) !important; background-repeat: no-repeat; } +.silk-money-euro { background-image: url(../images/icons-silk/money_euro.png) !important; background-repeat: no-repeat; } +.silk-money-pound { background-image: url(../images/icons-silk/money_pound.png) !important; background-repeat: no-repeat; } +.silk-money-yen { background-image: url(../images/icons-silk/money_yen.png) !important; background-repeat: no-repeat; } +.silk-monitor { background-image: url(../images/icons-silk/monitor.png) !important; background-repeat: no-repeat; } +.silk-monitor-add { background-image: url(../images/icons-silk/monitor_add.png) !important; background-repeat: no-repeat; } +.silk-monitor-delete { background-image: url(../images/icons-silk/monitor_delete.png) !important; background-repeat: no-repeat; } +.silk-monitor-edit { background-image: url(../images/icons-silk/monitor_edit.png) !important; background-repeat: no-repeat; } +.silk-monitor-error { background-image: url(../images/icons-silk/monitor_error.png) !important; background-repeat: no-repeat; } +.silk-monitor-go { background-image: url(../images/icons-silk/monitor_go.png) !important; background-repeat: no-repeat; } +.silk-monitor-lightning { background-image: url(../images/icons-silk/monitor_lightning.png) !important; background-repeat: no-repeat; } +.silk-monitor-link { background-image: url(../images/icons-silk/monitor_link.png) !important; background-repeat: no-repeat; } +.silk-mouse { background-image: url(../images/icons-silk/mouse.png) !important; background-repeat: no-repeat; } +.silk-mouse-add { background-image: url(../images/icons-silk/mouse_add.png) !important; background-repeat: no-repeat; } +.silk-mouse-delete { background-image: url(../images/icons-silk/mouse_delete.png) !important; background-repeat: no-repeat; } +.silk-mouse-error { background-image: url(../images/icons-silk/mouse_error.png) !important; background-repeat: no-repeat; } +.silk-music { background-image: url(../images/icons-silk/music.png) !important; background-repeat: no-repeat; } +.silk-new { background-image: url(../images/icons-silk/new.png) !important; background-repeat: no-repeat; } +.silk-newspaper { background-image: url(../images/icons-silk/newspaper.png) !important; background-repeat: no-repeat; } +.silk-newspaper-add { background-image: url(../images/icons-silk/newspaper_add.png) !important; background-repeat: no-repeat; } +.silk-newspaper-delete { background-image: url(../images/icons-silk/newspaper_delete.png) !important; background-repeat: no-repeat; } +.silk-newspaper-go { background-image: url(../images/icons-silk/newspaper_go.png) !important; background-repeat: no-repeat; } +.silk-newspaper-link { background-image: url(../images/icons-silk/newspaper_link.png) !important; background-repeat: no-repeat; } +.silk-note { background-image: url(../images/icons-silk/note.png) !important; background-repeat: no-repeat; } +.silk-note-add { background-image: url(../images/icons-silk/note_add.png) !important; background-repeat: no-repeat; } +.silk-note-delete { background-image: url(../images/icons-silk/note_delete.png) !important; background-repeat: no-repeat; } +.silk-note-edit { background-image: url(../images/icons-silk/note_edit.png) !important; background-repeat: no-repeat; } +.silk-note-error { background-image: url(../images/icons-silk/note_error.png) !important; background-repeat: no-repeat; } +.silk-note-go { background-image: url(../images/icons-silk/note_go.png) !important; background-repeat: no-repeat; } +.silk-overlays { background-image: url(../images/icons-silk/overlays.png) !important; background-repeat: no-repeat; } +.silk-package { background-image: url(../images/icons-silk/package.png) !important; background-repeat: no-repeat; } +.silk-package-add { background-image: url(../images/icons-silk/package_add.png) !important; background-repeat: no-repeat; } +.silk-package-delete { background-image: url(../images/icons-silk/package_delete.png) !important; background-repeat: no-repeat; } +.silk-package-go { background-image: url(../images/icons-silk/package_go.png) !important; background-repeat: no-repeat; } +.silk-package-green { background-image: url(../images/icons-silk/package_green.png) !important; background-repeat: no-repeat; } +.silk-package-link { background-image: url(../images/icons-silk/package_link.png) !important; background-repeat: no-repeat; } +.silk-page { background-image: url(../images/icons-silk/page.png) !important; background-repeat: no-repeat; } +.silk-page-add { background-image: url(../images/icons-silk/page_add.png) !important; background-repeat: no-repeat; } +.silk-page-attach { background-image: url(../images/icons-silk/page_attach.png) !important; background-repeat: no-repeat; } +.silk-page-code { background-image: url(../images/icons-silk/page_code.png) !important; background-repeat: no-repeat; } +.silk-page-copy { background-image: url(../images/icons-silk/page_copy.png) !important; background-repeat: no-repeat; } +.silk-page-delete { background-image: url(../images/icons-silk/page_delete.png) !important; background-repeat: no-repeat; } +.silk-page-edit { background-image: url(../images/icons-silk/page_edit.png) !important; background-repeat: no-repeat; } +.silk-page-error { background-image: url(../images/icons-silk/page_error.png) !important; background-repeat: no-repeat; } +.silk-page-excel { background-image: url(../images/icons-silk/page_excel.png) !important; background-repeat: no-repeat; } +.silk-page-find { background-image: url(../images/icons-silk/page_find.png) !important; background-repeat: no-repeat; } +.silk-page-gear { background-image: url(../images/icons-silk/page_gear.png) !important; background-repeat: no-repeat; } +.silk-page-go { background-image: url(../images/icons-silk/page_go.png) !important; background-repeat: no-repeat; } +.silk-page-green { background-image: url(../images/icons-silk/page_green.png) !important; background-repeat: no-repeat; } +.silk-page-key { background-image: url(../images/icons-silk/page_key.png) !important; background-repeat: no-repeat; } +.silk-page-lightning { background-image: url(../images/icons-silk/page_lightning.png) !important; background-repeat: no-repeat; } +.silk-page-link { background-image: url(../images/icons-silk/page_link.png) !important; background-repeat: no-repeat; } +.silk-page-paintbrush { background-image: url(../images/icons-silk/page_paintbrush.png) !important; background-repeat: no-repeat; } +.silk-page-paste { background-image: url(../images/icons-silk/page_paste.png) !important; background-repeat: no-repeat; } +.silk-page-red { background-image: url(../images/icons-silk/page_red.png) !important; background-repeat: no-repeat; } +.silk-page-refresh { background-image: url(../images/icons-silk/page_refresh.png) !important; background-repeat: no-repeat; } +.silk-page-save { background-image: url(../images/icons-silk/page_save.png) !important; background-repeat: no-repeat; } +.silk-page-white { background-image: url(../images/icons-silk/page_white.png) !important; background-repeat: no-repeat; } +.silk-page-white-acrobat { background-image: url(../images/icons-silk/page_white_acrobat.png) !important; background-repeat: no-repeat; } +.silk-page-white-actionscript { background-image: url(../images/icons-silk/page_white_actionscript.png) !important; background-repeat: no-repeat; } +.silk-page-white-add { background-image: url(../images/icons-silk/page_white_add.png) !important; background-repeat: no-repeat; } +.silk-page-white-c { background-image: url(../images/icons-silk/page_white_c.png) !important; background-repeat: no-repeat; } +.silk-page-white-camera { background-image: url(../images/icons-silk/page_white_camera.png) !important; background-repeat: no-repeat; } +.silk-page-white-cd { background-image: url(../images/icons-silk/page_white_cd.png) !important; background-repeat: no-repeat; } +.silk-page-white-code { background-image: url(../images/icons-silk/page_white_code.png) !important; background-repeat: no-repeat; } +.silk-page-white-code-red { background-image: url(../images/icons-silk/page_white_code_red.png) !important; background-repeat: no-repeat; } +.silk-page-white-coldfusion { background-image: url(../images/icons-silk/page_white_coldfusion.png) !important; background-repeat: no-repeat; } +.silk-page-white-compressed { background-image: url(../images/icons-silk/page_white_compressed.png) !important; background-repeat: no-repeat; } +.silk-page-white-copy { background-image: url(../images/icons-silk/page_white_copy.png) !important; background-repeat: no-repeat; } +.silk-page-white-cplusplus { background-image: url(../images/icons-silk/page_white_cplusplus.png) !important; background-repeat: no-repeat; } +.silk-page-white-csharp { background-image: url(../images/icons-silk/page_white_csharp.png) !important; background-repeat: no-repeat; } +.silk-page-white-cup { background-image: url(../images/icons-silk/page_white_cup.png) !important; background-repeat: no-repeat; } +.silk-page-white-database { background-image: url(../images/icons-silk/page_white_database.png) !important; background-repeat: no-repeat; } +.silk-page-white-delete { background-image: url(../images/icons-silk/page_white_delete.png) !important; background-repeat: no-repeat; } +.silk-page-white-dvd { background-image: url(../images/icons-silk/page_white_dvd.png) !important; background-repeat: no-repeat; } +.silk-page-white-edit { background-image: url(../images/icons-silk/page_white_edit.png) !important; background-repeat: no-repeat; } +.silk-page-white-error { background-image: url(../images/icons-silk/page_white_error.png) !important; background-repeat: no-repeat; } +.silk-page-white-excel { background-image: url(../images/icons-silk/page_white_excel.png) !important; background-repeat: no-repeat; } +.silk-page-white-find { background-image: url(../images/icons-silk/page_white_find.png) !important; background-repeat: no-repeat; } +.silk-page-white-flash { background-image: url(../images/icons-silk/page_white_flash.png) !important; background-repeat: no-repeat; } +.silk-page-white-freehand { background-image: url(../images/icons-silk/page_white_freehand.png) !important; background-repeat: no-repeat; } +.silk-page-white-gear { background-image: url(../images/icons-silk/page_white_gear.png) !important; background-repeat: no-repeat; } +.silk-page-white-get { background-image: url(../images/icons-silk/page_white_get.png) !important; background-repeat: no-repeat; } +.silk-page-white-go { background-image: url(../images/icons-silk/page_white_go.png) !important; background-repeat: no-repeat; } +.silk-page-white-h { background-image: url(../images/icons-silk/page_white_h.png) !important; background-repeat: no-repeat; } +.silk-page-white-horizontal { background-image: url(../images/icons-silk/page_white_horizontal.png) !important; background-repeat: no-repeat; } +.silk-page-white-key { background-image: url(../images/icons-silk/page_white_key.png) !important; background-repeat: no-repeat; } +.silk-page-white-lightning { background-image: url(../images/icons-silk/page_white_lightning.png) !important; background-repeat: no-repeat; } +.silk-page-white-link { background-image: url(../images/icons-silk/page_white_link.png) !important; background-repeat: no-repeat; } +.silk-page-white-magnify { background-image: url(../images/icons-silk/page_white_magnify.png) !important; background-repeat: no-repeat; } +.silk-page-white-medal { background-image: url(../images/icons-silk/page_white_medal.png) !important; background-repeat: no-repeat; } +.silk-page-white-office { background-image: url(../images/icons-silk/page_white_office.png) !important; background-repeat: no-repeat; } +.silk-page-white-paint { background-image: url(../images/icons-silk/page_white_paint.png) !important; background-repeat: no-repeat; } +.silk-page-white-paintbrush { background-image: url(../images/icons-silk/page_white_paintbrush.png) !important; background-repeat: no-repeat; } +.silk-page-white-paste { background-image: url(../images/icons-silk/page_white_paste.png) !important; background-repeat: no-repeat; } +.silk-page-white-php { background-image: url(../images/icons-silk/page_white_php.png) !important; background-repeat: no-repeat; } +.silk-page-white-picture { background-image: url(../images/icons-silk/page_white_picture.png) !important; background-repeat: no-repeat; } +.silk-page-white-powerpoint { background-image: url(../images/icons-silk/page_white_powerpoint.png) !important; background-repeat: no-repeat; } +.silk-page-white-put { background-image: url(../images/icons-silk/page_white_put.png) !important; background-repeat: no-repeat; } +.silk-page-white-ruby { background-image: url(../images/icons-silk/page_white_ruby.png) !important; background-repeat: no-repeat; } +.silk-page-white-stack { background-image: url(../images/icons-silk/page_white_stack.png) !important; background-repeat: no-repeat; } +.silk-page-white-star { background-image: url(../images/icons-silk/page_white_star.png) !important; background-repeat: no-repeat; } +.silk-page-white-swoosh { background-image: url(../images/icons-silk/page_white_swoosh.png) !important; background-repeat: no-repeat; } +.silk-page-white-text { background-image: url(../images/icons-silk/page_white_text.png) !important; background-repeat: no-repeat; } +.silk-page-white-text-width { background-image: url(../images/icons-silk/page_white_text_width.png) !important; background-repeat: no-repeat; } +.silk-page-white-tux { background-image: url(../images/icons-silk/page_white_tux.png) !important; background-repeat: no-repeat; } +.silk-page-white-vector { background-image: url(../images/icons-silk/page_white_vector.png) !important; background-repeat: no-repeat; } +.silk-page-white-visualstudio { background-image: url(../images/icons-silk/page_white_visualstudio.png) !important; background-repeat: no-repeat; } +.silk-page-white-width { background-image: url(../images/icons-silk/page_white_width.png) !important; background-repeat: no-repeat; } +.silk-page-white-word { background-image: url(../images/icons-silk/page_white_word.png) !important; background-repeat: no-repeat; } +.silk-page-white-world { background-image: url(../images/icons-silk/page_white_world.png) !important; background-repeat: no-repeat; } +.silk-page-white-wrench { background-image: url(../images/icons-silk/page_white_wrench.png) !important; background-repeat: no-repeat; } +.silk-page-white-zip { background-image: url(../images/icons-silk/page_white_zip.png) !important; background-repeat: no-repeat; } +.silk-page-word { background-image: url(../images/icons-silk/page_word.png) !important; background-repeat: no-repeat; } +.silk-page-world { background-image: url(../images/icons-silk/page_world.png) !important; background-repeat: no-repeat; } +.silk-paintbrush { background-image: url(../images/icons-silk/paintbrush.png) !important; background-repeat: no-repeat; } +.silk-paintcan { background-image: url(../images/icons-silk/paintcan.png) !important; background-repeat: no-repeat; } +.silk-palette { background-image: url(../images/icons-silk/palette.png) !important; background-repeat: no-repeat; } +.silk-paste-plain { background-image: url(../images/icons-silk/paste_plain.png) !important; background-repeat: no-repeat; } +.silk-paste-word { background-image: url(../images/icons-silk/paste_word.png) !important; background-repeat: no-repeat; } +.silk-pencil { background-image: url(../images/icons-silk/pencil.png) !important; background-repeat: no-repeat; } +.silk-pencil-add { background-image: url(../images/icons-silk/pencil_add.png) !important; background-repeat: no-repeat; } +.silk-pencil-delete { background-image: url(../images/icons-silk/pencil_delete.png) !important; background-repeat: no-repeat; } +.silk-pencil-go { background-image: url(../images/icons-silk/pencil_go.png) !important; background-repeat: no-repeat; } +.silk-phone { background-image: url(../images/icons-silk/phone.png) !important; background-repeat: no-repeat; } +.silk-phone-add { background-image: url(../images/icons-silk/phone_add.png) !important; background-repeat: no-repeat; } +.silk-phone-delete { background-image: url(../images/icons-silk/phone_delete.png) !important; background-repeat: no-repeat; } +.silk-phone-sound { background-image: url(../images/icons-silk/phone_sound.png) !important; background-repeat: no-repeat; } +.silk-photo { background-image: url(../images/icons-silk/photo.png) !important; background-repeat: no-repeat; } +.silk-photo-add { background-image: url(../images/icons-silk/photo_add.png) !important; background-repeat: no-repeat; } +.silk-photo-delete { background-image: url(../images/icons-silk/photo_delete.png) !important; background-repeat: no-repeat; } +.silk-photo-link { background-image: url(../images/icons-silk/photo_link.png) !important; background-repeat: no-repeat; } +.silk-photos { background-image: url(../images/icons-silk/photos.png) !important; background-repeat: no-repeat; } +.silk-picture { background-image: url(../images/icons-silk/picture.png) !important; background-repeat: no-repeat; } +.silk-picture-add { background-image: url(../images/icons-silk/picture_add.png) !important; background-repeat: no-repeat; } +.silk-picture-delete { background-image: url(../images/icons-silk/picture_delete.png) !important; background-repeat: no-repeat; } +.silk-picture-edit { background-image: url(../images/icons-silk/picture_edit.png) !important; background-repeat: no-repeat; } +.silk-picture-empty { background-image: url(../images/icons-silk/picture_empty.png) !important; background-repeat: no-repeat; } +.silk-picture-error { background-image: url(../images/icons-silk/picture_error.png) !important; background-repeat: no-repeat; } +.silk-picture-go { background-image: url(../images/icons-silk/picture_go.png) !important; background-repeat: no-repeat; } +.silk-picture-key { background-image: url(../images/icons-silk/picture_key.png) !important; background-repeat: no-repeat; } +.silk-picture-link { background-image: url(../images/icons-silk/picture_link.png) !important; background-repeat: no-repeat; } +.silk-picture-save { background-image: url(../images/icons-silk/picture_save.png) !important; background-repeat: no-repeat; } +.silk-pictures { background-image: url(../images/icons-silk/pictures.png) !important; background-repeat: no-repeat; } +.silk-pilcrow { background-image: url(../images/icons-silk/pilcrow.png) !important; background-repeat: no-repeat; } +.silk-pill { background-image: url(../images/icons-silk/pill.png) !important; background-repeat: no-repeat; } +.silk-pill-add { background-image: url(../images/icons-silk/pill_add.png) !important; background-repeat: no-repeat; } +.silk-pill-delete { background-image: url(../images/icons-silk/pill_delete.png) !important; background-repeat: no-repeat; } +.silk-pill-go { background-image: url(../images/icons-silk/pill_go.png) !important; background-repeat: no-repeat; } +.silk-plugin { background-image: url(../images/icons-silk/plugin.png) !important; background-repeat: no-repeat; } +.silk-plugin-add { background-image: url(../images/icons-silk/plugin_add.png) !important; background-repeat: no-repeat; } +.silk-plugin-delete { background-image: url(../images/icons-silk/plugin_delete.png) !important; background-repeat: no-repeat; } +.silk-plugin-disabled { background-image: url(../images/icons-silk/plugin_disabled.png) !important; background-repeat: no-repeat; } +.silk-plugin-edit { background-image: url(../images/icons-silk/plugin_edit.png) !important; background-repeat: no-repeat; } +.silk-plugin-error { background-image: url(../images/icons-silk/plugin_error.png) !important; background-repeat: no-repeat; } +.silk-plugin-go { background-image: url(../images/icons-silk/plugin_go.png) !important; background-repeat: no-repeat; } +.silk-plugin-link { background-image: url(../images/icons-silk/plugin_link.png) !important; background-repeat: no-repeat; } +.silk-printer { background-image: url(../images/icons-silk/printer.png) !important; background-repeat: no-repeat; } +.silk-printer-add { background-image: url(../images/icons-silk/printer_add.png) !important; background-repeat: no-repeat; } +.silk-printer-delete { background-image: url(../images/icons-silk/printer_delete.png) !important; background-repeat: no-repeat; } +.silk-printer-empty { background-image: url(../images/icons-silk/printer_empty.png) !important; background-repeat: no-repeat; } +.silk-printer-error { background-image: url(../images/icons-silk/printer_error.png) !important; background-repeat: no-repeat; } +.silk-rainbow { background-image: url(../images/icons-silk/rainbow.png) !important; background-repeat: no-repeat; } +.silk-report { background-image: url(../images/icons-silk/report.png) !important; background-repeat: no-repeat; } +.silk-report-add { background-image: url(../images/icons-silk/report_add.png) !important; background-repeat: no-repeat; } +.silk-report-delete { background-image: url(../images/icons-silk/report_delete.png) !important; background-repeat: no-repeat; } +.silk-report-disk { background-image: url(../images/icons-silk/report_disk.png) !important; background-repeat: no-repeat; } +.silk-report-edit { background-image: url(../images/icons-silk/report_edit.png) !important; background-repeat: no-repeat; } +.silk-report-go { background-image: url(../images/icons-silk/report_go.png) !important; background-repeat: no-repeat; } +.silk-report-key { background-image: url(../images/icons-silk/report_key.png) !important; background-repeat: no-repeat; } +.silk-report-link { background-image: url(../images/icons-silk/report_link.png) !important; background-repeat: no-repeat; } +.silk-report-magnify { background-image: url(../images/icons-silk/report_magnify.png) !important; background-repeat: no-repeat; } +.silk-report-picture { background-image: url(../images/icons-silk/report_picture.png) !important; background-repeat: no-repeat; } +.silk-report-user { background-image: url(../images/icons-silk/report_user.png) !important; background-repeat: no-repeat; } +.silk-report-word { background-image: url(../images/icons-silk/report_word.png) !important; background-repeat: no-repeat; } +.silk-resultset-first { background-image: url(../images/icons-silk/resultset_first.png) !important; background-repeat: no-repeat; } +.silk-resultset-last { background-image: url(../images/icons-silk/resultset_last.png) !important; background-repeat: no-repeat; } +.silk-resultset-next { background-image: url(../images/icons-silk/resultset_next.png) !important; background-repeat: no-repeat; } +.silk-resultset-previous { background-image: url(../images/icons-silk/resultset_previous.png) !important; background-repeat: no-repeat; } +.silk-rosette { background-image: url(../images/icons-silk/rosette.png) !important; background-repeat: no-repeat; } +.silk-rss { background-image: url(../images/icons-silk/rss.png) !important; background-repeat: no-repeat; } +.silk-rss-add { background-image: url(../images/icons-silk/rss_add.png) !important; background-repeat: no-repeat; } +.silk-rss-delete { background-image: url(../images/icons-silk/rss_delete.png) !important; background-repeat: no-repeat; } +.silk-rss-go { background-image: url(../images/icons-silk/rss_go.png) !important; background-repeat: no-repeat; } +.silk-rss-valid { background-image: url(../images/icons-silk/rss_valid.png) !important; background-repeat: no-repeat; } +.silk-ruby { background-image: url(../images/icons-silk/ruby.png) !important; background-repeat: no-repeat; } +.silk-ruby-add { background-image: url(../images/icons-silk/ruby_add.png) !important; background-repeat: no-repeat; } +.silk-ruby-delete { background-image: url(../images/icons-silk/ruby_delete.png) !important; background-repeat: no-repeat; } +.silk-ruby-gear { background-image: url(../images/icons-silk/ruby_gear.png) !important; background-repeat: no-repeat; } +.silk-ruby-get { background-image: url(../images/icons-silk/ruby_get.png) !important; background-repeat: no-repeat; } +.silk-ruby-go { background-image: url(../images/icons-silk/ruby_go.png) !important; background-repeat: no-repeat; } +.silk-ruby-key { background-image: url(../images/icons-silk/ruby_key.png) !important; background-repeat: no-repeat; } +.silk-ruby-link { background-image: url(../images/icons-silk/ruby_link.png) !important; background-repeat: no-repeat; } +.silk-ruby-put { background-image: url(../images/icons-silk/ruby_put.png) !important; background-repeat: no-repeat; } +.silk-script { background-image: url(../images/icons-silk/script.png) !important; background-repeat: no-repeat; } +.silk-script-add { background-image: url(../images/icons-silk/script_add.png) !important; background-repeat: no-repeat; } +.silk-script-code { background-image: url(../images/icons-silk/script_code.png) !important; background-repeat: no-repeat; } +.silk-script-code-red { background-image: url(../images/icons-silk/script_code_red.png) !important; background-repeat: no-repeat; } +.silk-script-delete { background-image: url(../images/icons-silk/script_delete.png) !important; background-repeat: no-repeat; } +.silk-script-edit { background-image: url(../images/icons-silk/script_edit.png) !important; background-repeat: no-repeat; } +.silk-script-error { background-image: url(../images/icons-silk/script_error.png) !important; background-repeat: no-repeat; } +.silk-script-gear { background-image: url(../images/icons-silk/script_gear.png) !important; background-repeat: no-repeat; } +.silk-script-go { background-image: url(../images/icons-silk/script_go.png) !important; background-repeat: no-repeat; } +.silk-script-key { background-image: url(../images/icons-silk/script_key.png) !important; background-repeat: no-repeat; } +.silk-script-lightning { background-image: url(../images/icons-silk/script_lightning.png) !important; background-repeat: no-repeat; } +.silk-script-link { background-image: url(../images/icons-silk/script_link.png) !important; background-repeat: no-repeat; } +.silk-script-palette { background-image: url(../images/icons-silk/script_palette.png) !important; background-repeat: no-repeat; } +.silk-script-save { background-image: url(../images/icons-silk/script_save.png) !important; background-repeat: no-repeat; } +.silk-server { background-image: url(../images/icons-silk/server.png) !important; background-repeat: no-repeat; } +.silk-server-add { background-image: url(../images/icons-silk/server_add.png) !important; background-repeat: no-repeat; } +.silk-server-chart { background-image: url(../images/icons-silk/server_chart.png) !important; background-repeat: no-repeat; } +.silk-server-compressed { background-image: url(../images/icons-silk/server_compressed.png) !important; background-repeat: no-repeat; } +.silk-server-connect { background-image: url(../images/icons-silk/server_connect.png) !important; background-repeat: no-repeat; } +.silk-server-database { background-image: url(../images/icons-silk/server_database.png) !important; background-repeat: no-repeat; } +.silk-server-delete { background-image: url(../images/icons-silk/server_delete.png) !important; background-repeat: no-repeat; } +.silk-server-edit { background-image: url(../images/icons-silk/server_edit.png) !important; background-repeat: no-repeat; } +.silk-server-error { background-image: url(../images/icons-silk/server_error.png) !important; background-repeat: no-repeat; } +.silk-server-go { background-image: url(../images/icons-silk/server_go.png) !important; background-repeat: no-repeat; } +.silk-server-key { background-image: url(../images/icons-silk/server_key.png) !important; background-repeat: no-repeat; } +.silk-server-lightning { background-image: url(../images/icons-silk/server_lightning.png) !important; background-repeat: no-repeat; } +.silk-server-link { background-image: url(../images/icons-silk/server_link.png) !important; background-repeat: no-repeat; } +.silk-server-uncompressed { background-image: url(../images/icons-silk/server_uncompressed.png) !important; background-repeat: no-repeat; } +.silk-shading { background-image: url(../images/icons-silk/shading.png) !important; background-repeat: no-repeat; } +.silk-shape-align-bottom { background-image: url(../images/icons-silk/shape_align_bottom.png) !important; background-repeat: no-repeat; } +.silk-shape-align-center { background-image: url(../images/icons-silk/shape_align_center.png) !important; background-repeat: no-repeat; } +.silk-shape-align-left { background-image: url(../images/icons-silk/shape_align_left.png) !important; background-repeat: no-repeat; } +.silk-shape-align-middle { background-image: url(../images/icons-silk/shape_align_middle.png) !important; background-repeat: no-repeat; } +.silk-shape-align-right { background-image: url(../images/icons-silk/shape_align_right.png) !important; background-repeat: no-repeat; } +.silk-shape-align-top { background-image: url(../images/icons-silk/shape_align_top.png) !important; background-repeat: no-repeat; } +.silk-shape-flip-horizontal { background-image: url(../images/icons-silk/shape_flip_horizontal.png) !important; background-repeat: no-repeat; } +.silk-shape-flip-vertical { background-image: url(../images/icons-silk/shape_flip_vertical.png) !important; background-repeat: no-repeat; } +.silk-shape-group { background-image: url(../images/icons-silk/shape_group.png) !important; background-repeat: no-repeat; } +.silk-shape-handles { background-image: url(../images/icons-silk/shape_handles.png) !important; background-repeat: no-repeat; } +.silk-shape-move-back { background-image: url(../images/icons-silk/shape_move_back.png) !important; background-repeat: no-repeat; } +.silk-shape-move-backwards { background-image: url(../images/icons-silk/shape_move_backwards.png) !important; background-repeat: no-repeat; } +.silk-shape-move-forwards { background-image: url(../images/icons-silk/shape_move_forwards.png) !important; background-repeat: no-repeat; } +.silk-shape-move-front { background-image: url(../images/icons-silk/shape_move_front.png) !important; background-repeat: no-repeat; } +.silk-shape-rotate-anticlockwise { background-image: url(../images/icons-silk/shape_rotate_anticlockwise.png) !important; background-repeat: no-repeat; } +.silk-shape-rotate-clockwise { background-image: url(../images/icons-silk/shape_rotate_clockwise.png) !important; background-repeat: no-repeat; } +.silk-shape-square { background-image: url(../images/icons-silk/shape_square.png) !important; background-repeat: no-repeat; } +.silk-shape-square-add { background-image: url(../images/icons-silk/shape_square_add.png) !important; background-repeat: no-repeat; } +.silk-shape-square-delete { background-image: url(../images/icons-silk/shape_square_delete.png) !important; background-repeat: no-repeat; } +.silk-shape-square-edit { background-image: url(../images/icons-silk/shape_square_edit.png) !important; background-repeat: no-repeat; } +.silk-shape-square-error { background-image: url(../images/icons-silk/shape_square_error.png) !important; background-repeat: no-repeat; } +.silk-shape-square-go { background-image: url(../images/icons-silk/shape_square_go.png) !important; background-repeat: no-repeat; } +.silk-shape-square-key { background-image: url(../images/icons-silk/shape_square_key.png) !important; background-repeat: no-repeat; } +.silk-shape-square-link { background-image: url(../images/icons-silk/shape_square_link.png) !important; background-repeat: no-repeat; } +.silk-shape-ungroup { background-image: url(../images/icons-silk/shape_ungroup.png) !important; background-repeat: no-repeat; } +.silk-shield { background-image: url(../images/icons-silk/shield.png) !important; background-repeat: no-repeat; } +.silk-shield-add { background-image: url(../images/icons-silk/shield_add.png) !important; background-repeat: no-repeat; } +.silk-shield-delete { background-image: url(../images/icons-silk/shield_delete.png) !important; background-repeat: no-repeat; } +.silk-shield-go { background-image: url(../images/icons-silk/shield_go.png) !important; background-repeat: no-repeat; } +.silk-sitemap { background-image: url(../images/icons-silk/sitemap.png) !important; background-repeat: no-repeat; } +.silk-sitemap-color { background-image: url(../images/icons-silk/sitemap_color.png) !important; background-repeat: no-repeat; } +.silk-sound { background-image: url(../images/icons-silk/sound.png) !important; background-repeat: no-repeat; } +.silk-sound-add { background-image: url(../images/icons-silk/sound_add.png) !important; background-repeat: no-repeat; } +.silk-sound-delete { background-image: url(../images/icons-silk/sound_delete.png) !important; background-repeat: no-repeat; } +.silk-sound-low { background-image: url(../images/icons-silk/sound_low.png) !important; background-repeat: no-repeat; } +.silk-sound-mute { background-image: url(../images/icons-silk/sound_mute.png) !important; background-repeat: no-repeat; } +.silk-sound-none { background-image: url(../images/icons-silk/sound_none.png) !important; background-repeat: no-repeat; } +.silk-spellcheck { background-image: url(../images/icons-silk/spellcheck.png) !important; background-repeat: no-repeat; } +.silk-sport-8ball { background-image: url(../images/icons-silk/sport_8ball.png) !important; background-repeat: no-repeat; } +.silk-sport-basketball { background-image: url(../images/icons-silk/sport_basketball.png) !important; background-repeat: no-repeat; } +.silk-sport-football { background-image: url(../images/icons-silk/sport_football.png) !important; background-repeat: no-repeat; } +.silk-sport-golf { background-image: url(../images/icons-silk/sport_golf.png) !important; background-repeat: no-repeat; } +.silk-sport-raquet { background-image: url(../images/icons-silk/sport_raquet.png) !important; background-repeat: no-repeat; } +.silk-sport-shuttlecock { background-image: url(../images/icons-silk/sport_shuttlecock.png) !important; background-repeat: no-repeat; } +.silk-sport-soccer { background-image: url(../images/icons-silk/sport_soccer.png) !important; background-repeat: no-repeat; } +.silk-sport-tennis { background-image: url(../images/icons-silk/sport_tennis.png) !important; background-repeat: no-repeat; } +.silk-star { background-image: url(../images/icons-silk/star.png) !important; background-repeat: no-repeat; } +.silk-star-empty { background-image: url(../images/icons-silk/star_empty.png) !important; background-repeat: no-repeat; } +.silk-status-away { background-image: url(../images/icons-silk/status_away.png) !important; background-repeat: no-repeat; } +.silk-status-busy { background-image: url(../images/icons-silk/status_busy.png) !important; background-repeat: no-repeat; } +.silk-status-offline { background-image: url(../images/icons-silk/status_offline.png) !important; background-repeat: no-repeat; } +.silk-status-online { background-image: url(../images/icons-silk/status_online.png) !important; background-repeat: no-repeat; } +.silk-stop { background-image: url(../images/icons-silk/stop.png) !important; background-repeat: no-repeat; } +.silk-style { background-image: url(../images/icons-silk/style.png) !important; background-repeat: no-repeat; } +.silk-style-add { background-image: url(../images/icons-silk/style_add.png) !important; background-repeat: no-repeat; } +.silk-style-delete { background-image: url(../images/icons-silk/style_delete.png) !important; background-repeat: no-repeat; } +.silk-style-edit { background-image: url(../images/icons-silk/style_edit.png) !important; background-repeat: no-repeat; } +.silk-style-go { background-image: url(../images/icons-silk/style_go.png) !important; background-repeat: no-repeat; } +.silk-sum { background-image: url(../images/icons-silk/sum.png) !important; background-repeat: no-repeat; } +.silk-tab { background-image: url(../images/icons-silk/tab.png) !important; background-repeat: no-repeat; } +.silk-tab-add { background-image: url(../images/icons-silk/tab_add.png) !important; background-repeat: no-repeat; } +.silk-tab-delete { background-image: url(../images/icons-silk/tab_delete.png) !important; background-repeat: no-repeat; } +.silk-tab-edit { background-image: url(../images/icons-silk/tab_edit.png) !important; background-repeat: no-repeat; } +.silk-tab-go { background-image: url(../images/icons-silk/tab_go.png) !important; background-repeat: no-repeat; } +.silk-table { background-image: url(../images/icons-silk/table.png) !important; background-repeat: no-repeat; } +.silk-table-add { background-image: url(../images/icons-silk/table_add.png) !important; background-repeat: no-repeat; } +.silk-table-delete { background-image: url(../images/icons-silk/table_delete.png) !important; background-repeat: no-repeat; } +.silk-table-edit { background-image: url(../images/icons-silk/table_edit.png) !important; background-repeat: no-repeat; } +.silk-table-error { background-image: url(../images/icons-silk/table_error.png) !important; background-repeat: no-repeat; } +.silk-table-gear { background-image: url(../images/icons-silk/table_gear.png) !important; background-repeat: no-repeat; } +.silk-table-go { background-image: url(../images/icons-silk/table_go.png) !important; background-repeat: no-repeat; } +.silk-table-key { background-image: url(../images/icons-silk/table_key.png) !important; background-repeat: no-repeat; } +.silk-table-lightning { background-image: url(../images/icons-silk/table_lightning.png) !important; background-repeat: no-repeat; } +.silk-table-link { background-image: url(../images/icons-silk/table_link.png) !important; background-repeat: no-repeat; } +.silk-table-multiple { background-image: url(../images/icons-silk/table_multiple.png) !important; background-repeat: no-repeat; } +.silk-table-refresh { background-image: url(../images/icons-silk/table_refresh.png) !important; background-repeat: no-repeat; } +.silk-table-relationship { background-image: url(../images/icons-silk/table_relationship.png) !important; background-repeat: no-repeat; } +.silk-table-row-delete { background-image: url(../images/icons-silk/table_row_delete.png) !important; background-repeat: no-repeat; } +.silk-table-row-insert { background-image: url(../images/icons-silk/table_row_insert.png) !important; background-repeat: no-repeat; } +.silk-table-save { background-image: url(../images/icons-silk/table_save.png) !important; background-repeat: no-repeat; } +.silk-table-sort { background-image: url(../images/icons-silk/table_sort.png) !important; background-repeat: no-repeat; } +.silk-tag { background-image: url(../images/icons-silk/tag.png) !important; background-repeat: no-repeat; } +.silk-tag-blue { background-image: url(../images/icons-silk/tag_blue.png) !important; background-repeat: no-repeat; } +.silk-tag-blue-add { background-image: url(../images/icons-silk/tag_blue_add.png) !important; background-repeat: no-repeat; } +.silk-tag-blue-delete { background-image: url(../images/icons-silk/tag_blue_delete.png) !important; background-repeat: no-repeat; } +.silk-tag-blue-edit { background-image: url(../images/icons-silk/tag_blue_edit.png) !important; background-repeat: no-repeat; } +.silk-tag-green { background-image: url(../images/icons-silk/tag_green.png) !important; background-repeat: no-repeat; } +.silk-tag-orange { background-image: url(../images/icons-silk/tag_orange.png) !important; background-repeat: no-repeat; } +.silk-tag-pink { background-image: url(../images/icons-silk/tag_pink.png) !important; background-repeat: no-repeat; } +.silk-tag-purple { background-image: url(../images/icons-silk/tag_purple.png) !important; background-repeat: no-repeat; } +.silk-tag-red { background-image: url(../images/icons-silk/tag_red.png) !important; background-repeat: no-repeat; } +.silk-tag-yellow { background-image: url(../images/icons-silk/tag_yellow.png) !important; background-repeat: no-repeat; } +.silk-telephone { background-image: url(../images/icons-silk/telephone.png) !important; background-repeat: no-repeat; } +.silk-telephone-add { background-image: url(../images/icons-silk/telephone_add.png) !important; background-repeat: no-repeat; } +.silk-telephone-delete { background-image: url(../images/icons-silk/telephone_delete.png) !important; background-repeat: no-repeat; } +.silk-telephone-edit { background-image: url(../images/icons-silk/telephone_edit.png) !important; background-repeat: no-repeat; } +.silk-telephone-error { background-image: url(../images/icons-silk/telephone_error.png) !important; background-repeat: no-repeat; } +.silk-telephone-go { background-image: url(../images/icons-silk/telephone_go.png) !important; background-repeat: no-repeat; } +.silk-telephone-key { background-image: url(../images/icons-silk/telephone_key.png) !important; background-repeat: no-repeat; } +.silk-telephone-link { background-image: url(../images/icons-silk/telephone_link.png) !important; background-repeat: no-repeat; } +.silk-television { background-image: url(../images/icons-silk/television.png) !important; background-repeat: no-repeat; } +.silk-television-add { background-image: url(../images/icons-silk/television_add.png) !important; background-repeat: no-repeat; } +.silk-television-delete { background-image: url(../images/icons-silk/television_delete.png) !important; background-repeat: no-repeat; } +.silk-text-align-center { background-image: url(../images/icons-silk/text_align_center.png) !important; background-repeat: no-repeat; } +.silk-text-align-justify { background-image: url(../images/icons-silk/text_align_justify.png) !important; background-repeat: no-repeat; } +.silk-text-align-left { background-image: url(../images/icons-silk/text_align_left.png) !important; background-repeat: no-repeat; } +.silk-text-align-right { background-image: url(../images/icons-silk/text_align_right.png) !important; background-repeat: no-repeat; } +.silk-text-allcaps { background-image: url(../images/icons-silk/text_allcaps.png) !important; background-repeat: no-repeat; } +.silk-text-bold { background-image: url(../images/icons-silk/text_bold.png) !important; background-repeat: no-repeat; } +.silk-text-columns { background-image: url(../images/icons-silk/text_columns.png) !important; background-repeat: no-repeat; } +.silk-text-dropcaps { background-image: url(../images/icons-silk/text_dropcaps.png) !important; background-repeat: no-repeat; } +.silk-text-heading-1 { background-image: url(../images/icons-silk/text_heading_1.png) !important; background-repeat: no-repeat; } +.silk-text-heading-2 { background-image: url(../images/icons-silk/text_heading_2.png) !important; background-repeat: no-repeat; } +.silk-text-heading-3 { background-image: url(../images/icons-silk/text_heading_3.png) !important; background-repeat: no-repeat; } +.silk-text-heading-4 { background-image: url(../images/icons-silk/text_heading_4.png) !important; background-repeat: no-repeat; } +.silk-text-heading-5 { background-image: url(../images/icons-silk/text_heading_5.png) !important; background-repeat: no-repeat; } +.silk-text-heading-6 { background-image: url(../images/icons-silk/text_heading_6.png) !important; background-repeat: no-repeat; } +.silk-text-horizontalrule { background-image: url(../images/icons-silk/text_horizontalrule.png) !important; background-repeat: no-repeat; } +.silk-text-indent { background-image: url(../images/icons-silk/text_indent.png) !important; background-repeat: no-repeat; } +.silk-text-indent-remove { background-image: url(../images/icons-silk/text_indent_remove.png) !important; background-repeat: no-repeat; } +.silk-text-italic { background-image: url(../images/icons-silk/text_italic.png) !important; background-repeat: no-repeat; } +.silk-text-kerning { background-image: url(../images/icons-silk/text_kerning.png) !important; background-repeat: no-repeat; } +.silk-text-letter-omega { background-image: url(../images/icons-silk/text_letter_omega.png) !important; background-repeat: no-repeat; } +.silk-text-letterspacing { background-image: url(../images/icons-silk/text_letterspacing.png) !important; background-repeat: no-repeat; } +.silk-text-linespacing { background-image: url(../images/icons-silk/text_linespacing.png) !important; background-repeat: no-repeat; } +.silk-text-list-bullets { background-image: url(../images/icons-silk/text_list_bullets.png) !important; background-repeat: no-repeat; } +.silk-text-list-numbers { background-image: url(../images/icons-silk/text_list_numbers.png) !important; background-repeat: no-repeat; } +.silk-text-lowercase { background-image: url(../images/icons-silk/text_lowercase.png) !important; background-repeat: no-repeat; } +.silk-text-padding-bottom { background-image: url(../images/icons-silk/text_padding_bottom.png) !important; background-repeat: no-repeat; } +.silk-text-padding-left { background-image: url(../images/icons-silk/text_padding_left.png) !important; background-repeat: no-repeat; } +.silk-text-padding-right { background-image: url(../images/icons-silk/text_padding_right.png) !important; background-repeat: no-repeat; } +.silk-text-padding-top { background-image: url(../images/icons-silk/text_padding_top.png) !important; background-repeat: no-repeat; } +.silk-text-replace { background-image: url(../images/icons-silk/text_replace.png) !important; background-repeat: no-repeat; } +.silk-text-signature { background-image: url(../images/icons-silk/text_signature.png) !important; background-repeat: no-repeat; } +.silk-text-smallcaps { background-image: url(../images/icons-silk/text_smallcaps.png) !important; background-repeat: no-repeat; } +.silk-text-strikethrough { background-image: url(../images/icons-silk/text_strikethrough.png) !important; background-repeat: no-repeat; } +.silk-text-subscript { background-image: url(../images/icons-silk/text_subscript.png) !important; background-repeat: no-repeat; } +.silk-text-superscript { background-image: url(../images/icons-silk/text_superscript.png) !important; background-repeat: no-repeat; } +.silk-text-underline { background-image: url(../images/icons-silk/text_underline.png) !important; background-repeat: no-repeat; } +.silk-text-uppercase { background-image: url(../images/icons-silk/text_uppercase.png) !important; background-repeat: no-repeat; } +.silk-textfield { background-image: url(../images/icons-silk/textfield.png) !important; background-repeat: no-repeat; } +.silk-textfield-add { background-image: url(../images/icons-silk/textfield_add.png) !important; background-repeat: no-repeat; } +.silk-textfield-delete { background-image: url(../images/icons-silk/textfield_delete.png) !important; background-repeat: no-repeat; } +.silk-textfield-key { background-image: url(../images/icons-silk/textfield_key.png) !important; background-repeat: no-repeat; } +.silk-textfield-rename { background-image: url(../images/icons-silk/textfield_rename.png) !important; background-repeat: no-repeat; } +.silk-thumb-down { background-image: url(../images/icons-silk/thumb_down.png) !important; background-repeat: no-repeat; } +.silk-thumb-up { background-image: url(../images/icons-silk/thumb_up.png) !important; background-repeat: no-repeat; } +.silk-tick { background-image: url(../images/icons-silk/tick.png) !important; background-repeat: no-repeat; } +.silk-time { background-image: url(../images/icons-silk/time.png) !important; background-repeat: no-repeat; } +.silk-time-add { background-image: url(../images/icons-silk/time_add.png) !important; background-repeat: no-repeat; } +.silk-time-delete { background-image: url(../images/icons-silk/time_delete.png) !important; background-repeat: no-repeat; } +.silk-time-go { background-image: url(../images/icons-silk/time_go.png) !important; background-repeat: no-repeat; } +.silk-timeline-marker { background-image: url(../images/icons-silk/timeline_marker.png) !important; background-repeat: no-repeat; } +.silk-transmit { background-image: url(../images/icons-silk/transmit.png) !important; background-repeat: no-repeat; } +.silk-transmit-add { background-image: url(../images/icons-silk/transmit_add.png) !important; background-repeat: no-repeat; } +.silk-transmit-blue { background-image: url(../images/icons-silk/transmit_blue.png) !important; background-repeat: no-repeat; } +.silk-transmit-delete { background-image: url(../images/icons-silk/transmit_delete.png) !important; background-repeat: no-repeat; } +.silk-transmit-edit { background-image: url(../images/icons-silk/transmit_edit.png) !important; background-repeat: no-repeat; } +.silk-transmit-error { background-image: url(../images/icons-silk/transmit_error.png) !important; background-repeat: no-repeat; } +.silk-transmit-go { background-image: url(../images/icons-silk/transmit_go.png) !important; background-repeat: no-repeat; } +.silk-tux { background-image: url(../images/icons-silk/tux.png) !important; background-repeat: no-repeat; } +.silk-user { background-image: url(../images/icons-silk/user.png) !important; background-repeat: no-repeat; } +.silk-user-add { background-image: url(../images/icons-silk/user_add.png) !important; background-repeat: no-repeat; } +.silk-user-comment { background-image: url(../images/icons-silk/user_comment.png) !important; background-repeat: no-repeat; } +.silk-user-delete { background-image: url(../images/icons-silk/user_delete.png) !important; background-repeat: no-repeat; } +.silk-user-edit { background-image: url(../images/icons-silk/user_edit.png) !important; background-repeat: no-repeat; } +.silk-user-female { background-image: url(../images/icons-silk/user_female.png) !important; background-repeat: no-repeat; } +.silk-user-go { background-image: url(../images/icons-silk/user_go.png) !important; background-repeat: no-repeat; } +.silk-user-gray { background-image: url(../images/icons-silk/user_gray.png) !important; background-repeat: no-repeat; } +.silk-user-green { background-image: url(../images/icons-silk/user_green.png) !important; background-repeat: no-repeat; } +.silk-user-orange { background-image: url(../images/icons-silk/user_orange.png) !important; background-repeat: no-repeat; } +.silk-user-red { background-image: url(../images/icons-silk/user_red.png) !important; background-repeat: no-repeat; } +.silk-user-suit { background-image: url(../images/icons-silk/user_suit.png) !important; background-repeat: no-repeat; } +.silk-vcard { background-image: url(../images/icons-silk/vcard.png) !important; background-repeat: no-repeat; } +.silk-vcard-add { background-image: url(../images/icons-silk/vcard_add.png) !important; background-repeat: no-repeat; } +.silk-vcard-delete { background-image: url(../images/icons-silk/vcard_delete.png) !important; background-repeat: no-repeat; } +.silk-vcard-edit { background-image: url(../images/icons-silk/vcard_edit.png) !important; background-repeat: no-repeat; } +.silk-vector { background-image: url(../images/icons-silk/vector.png) !important; background-repeat: no-repeat; } +.silk-vector-add { background-image: url(../images/icons-silk/vector_add.png) !important; background-repeat: no-repeat; } +.silk-vector-delete { background-image: url(../images/icons-silk/vector_delete.png) !important; background-repeat: no-repeat; } +.silk-wand { background-image: url(../images/icons-silk/wand.png) !important; background-repeat: no-repeat; } +.silk-weather-clouds { background-image: url(../images/icons-silk/weather_clouds.png) !important; background-repeat: no-repeat; } +.silk-weather-cloudy { background-image: url(../images/icons-silk/weather_cloudy.png) !important; background-repeat: no-repeat; } +.silk-weather-lightning { background-image: url(../images/icons-silk/weather_lightning.png) !important; background-repeat: no-repeat; } +.silk-weather-rain { background-image: url(../images/icons-silk/weather_rain.png) !important; background-repeat: no-repeat; } +.silk-weather-snow { background-image: url(../images/icons-silk/weather_snow.png) !important; background-repeat: no-repeat; } +.silk-weather-sun { background-image: url(../images/icons-silk/weather_sun.png) !important; background-repeat: no-repeat; } +.silk-webcam { background-image: url(../images/icons-silk/webcam.png) !important; background-repeat: no-repeat; } +.silk-webcam-add { background-image: url(../images/icons-silk/webcam_add.png) !important; background-repeat: no-repeat; } +.silk-webcam-delete { background-image: url(../images/icons-silk/webcam_delete.png) !important; background-repeat: no-repeat; } +.silk-webcam-error { background-image: url(../images/icons-silk/webcam_error.png) !important; background-repeat: no-repeat; } +.silk-world { background-image: url(../images/icons-silk/world.png) !important; background-repeat: no-repeat; } +.silk-world-add { background-image: url(../images/icons-silk/world_add.png) !important; background-repeat: no-repeat; } +.silk-world-delete { background-image: url(../images/icons-silk/world_delete.png) !important; background-repeat: no-repeat; } +.silk-world-edit { background-image: url(../images/icons-silk/world_edit.png) !important; background-repeat: no-repeat; } +.silk-world-go { background-image: url(../images/icons-silk/world_go.png) !important; background-repeat: no-repeat; } +.silk-world-link { background-image: url(../images/icons-silk/world_link.png) !important; background-repeat: no-repeat; } +.silk-wrench { background-image: url(../images/icons-silk/wrench.png) !important; background-repeat: no-repeat; } +.silk-wrench-orange { background-image: url(../images/icons-silk/wrench_orange.png) !important; background-repeat: no-repeat; } +.silk-xhtml { background-image: url(../images/icons-silk/xhtml.png) !important; background-repeat: no-repeat; } +.silk-xhtml-add { background-image: url(../images/icons-silk/xhtml_add.png) !important; background-repeat: no-repeat; } +.silk-xhtml-delete { background-image: url(../images/icons-silk/xhtml_delete.png) !important; background-repeat: no-repeat; } +.silk-xhtml-go { background-image: url(../images/icons-silk/xhtml_go.png) !important; background-repeat: no-repeat; } +.silk-xhtml-valid { background-image: url(../images/icons-silk/xhtml_valid.png) !important; background-repeat: no-repeat; } +.silk-zoom { background-image: url(../images/icons-silk/zoom.png) !important; background-repeat: no-repeat; } +.silk-zoom-in { background-image: url(../images/icons-silk/zoom_in.png) !important; background-repeat: no-repeat; } +.silk-zoom-out { background-image: url(../images/icons-silk/zoom_out.png) !important; background-repeat: no-repeat; } diff --git a/src/main/webapp/resources/css/icons.css b/src/main/webapp/resources/css/icons.css new file mode 100644 index 0000000..c7b5eb6 --- /dev/null +++ b/src/main/webapp/resources/css/icons.css @@ -0,0 +1,18 @@ +.icon-download { background-image: url(../images/icons/download.png) !important; background-repeat: no-repeat; background-size: contain; } +.icon-upload { background-image: url(../images/icons/upload.png) !important; background-repeat: no-repeat; background-size: contain; } +.icon-pdf { background-image: url(../images/icons/pdf.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-word { background-image: url(../images/icons/word.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-excel { background-image: url(../images/icons/excel.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-save { background-image: url(../images/icons/save.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-checkmark { background-image: url(../images/icons/checkmark.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-earlyrelease { background-image: url(../images/icons/earlyrelease.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-library { background-image: url(../images/icons/library.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-schedule { background-image: url(../images/icons/schedule.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-flag { background-image: url(../images/icons/flag.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-timer { background-image: url(../images/icons/timer.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-generate { background-image: url(../images/icons/generate.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-logout { background-image: url(../images/icons/logout.png) !important; background-repeat: no-repeat; background-size: contain;} +.icon-table-multiple{ background-image: url(../images/icons/table_multiple.png) !important; height: 24px !important; width: 24px !important;} +.icon-table-add{ background-image: url(../images/icons/table_add.png) !important; height: 24px !important; width: 24px !important;} +.icon-images{ background-image: url(../images/icons/images.png) !important; height: 24px !important; width: 24px !important;} +.icon-edit{ background-image: url(../images/icons/edit.png) !important; height: 24px !important; width: 24px !important;} diff --git a/src/main/webapp/resources/css/main.css b/src/main/webapp/resources/css/main.css new file mode 100644 index 0000000..2532fa7 --- /dev/null +++ b/src/main/webapp/resources/css/main.css @@ -0,0 +1,79 @@ +.editableCell { + background-color: #fffbd0 !important; +} + +.textAlignRight { + text-align: right !important; +} + +.textAlignCenter { + text-align: center !important; +} + +.silk-cross-large { + background-image: url(../images/icons-silk/cross.png) !important; + background-repeat: no-repeat; + background-size: 25px 25px; + width: 25px; + height: 25px; +} +.silk-arrow-right-large { + background-image: url(../images/icons-silk/arrow_right.png) !important; + background-repeat: no-repeat; + background-size: 25px 25px; + width: 25px; + height: 25px; +} + +.x-table-layout td { + vertical-align: top; +} + +.x-action-col-icon { + margin-right: 8px; +} + +.custom-label { + background-color: #e7e7e7; + color: black; + padding: 8px; + font-family: Arial; + border-radius: 7px; +} + +.selection-disabled .x-selmodel-column { + visibility: hidden; +} + +.editable-column .x-column-header-inner{ + background: #fdf5d7; +} + +.change-status-column .x-column-header-inner{ + background:#9cc96b; +} + +.tbms-base-button { + background-color: #4CAF50; + border: none; + color: white; + padding: 8px 12px; + text-align: center; + text-decoration: none; + display: inline-block; + font-size: 14px; + margin: 4px 2px; + transition-duration: 0.4s; + cursor: pointer; + float: right; + } + +.tbms-button { + background-color: #5d8c97; + color: white; +} + +.tbms-button:hover { + background-color: #3d5d64; + color: white; +} diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/Readme.md b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/Readme.md new file mode 100644 index 0000000..e618474 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/Readme.md @@ -0,0 +1,3 @@ +# theme-neptune/resources + +This folder contains static resources (typically an `"images"` folder as well). diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow-open-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow-open-rtl.png new file mode 100644 index 0000000..d9968ae Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow-open-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow-open.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow-open.png new file mode 100644 index 0000000..04b1132 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow-open.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow-rtl.png new file mode 100644 index 0000000..90f717b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow.png new file mode 100644 index 0000000..51d2861 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-open-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-open-rtl.png new file mode 100644 index 0000000..a8801df Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-open-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-open.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-open.png new file mode 100644 index 0000000..19a6673 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-open.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-over-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-over-rtl.png new file mode 100644 index 0000000..db04b9d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-over-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-over.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-over.png new file mode 100644 index 0000000..5106cdf Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-over.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-rtl.png new file mode 100644 index 0000000..658194b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow.png new file mode 100644 index 0000000..d3d375c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/breadcrumb/default-split-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-corners.gif new file mode 100644 index 0000000..7f6a166 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-notitle-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-notitle-corners.gif new file mode 100644 index 0000000..7f6a166 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-notitle-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-notitle-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-notitle-sides.gif new file mode 100644 index 0000000..7e1a05f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-notitle-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-sides.gif new file mode 100644 index 0000000..1ddf279 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn-group/btn-group-default-framed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-corners.gif new file mode 100644 index 0000000..a7cb52a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-disabled-corners.gif new file mode 100644 index 0000000..60fd58e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-disabled-fbg.gif new file mode 100644 index 0000000..155ec57 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-disabled-sides.gif new file mode 100644 index 0000000..24acd43 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-fbg.gif new file mode 100644 index 0000000..566f794 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-corners.gif new file mode 100644 index 0000000..f3e031c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-fbg.gif new file mode 100644 index 0000000..566f794 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-over-corners.gif new file mode 100644 index 0000000..dc3f16a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-over-fbg.gif new file mode 100644 index 0000000..566f794 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-over-sides.gif new file mode 100644 index 0000000..169e259 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-pressed-corners.gif new file mode 100644 index 0000000..d1b24b5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-pressed-fbg.gif new file mode 100644 index 0000000..a274ca5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-pressed-sides.gif new file mode 100644 index 0000000..7a3e78e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-sides.gif new file mode 100644 index 0000000..56fac0a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-over-corners.gif new file mode 100644 index 0000000..1edb4c0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-over-fbg.gif new file mode 100644 index 0000000..6d6ada8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-over-sides.gif new file mode 100644 index 0000000..c5474d4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-pressed-corners.gif new file mode 100644 index 0000000..38519b9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-pressed-fbg.gif new file mode 100644 index 0000000..a274ca5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-pressed-sides.gif new file mode 100644 index 0000000..5865de8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-sides.gif new file mode 100644 index 0000000..9dc0780 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-large-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-corners.gif new file mode 100644 index 0000000..308020b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-disabled-corners.gif new file mode 100644 index 0000000..8a6fa9d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-disabled-fbg.gif new file mode 100644 index 0000000..0e31b18 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-disabled-sides.gif new file mode 100644 index 0000000..c7e4bc3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-fbg.gif new file mode 100644 index 0000000..7cdabfa Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-corners.gif new file mode 100644 index 0000000..9c66fb0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-fbg.gif new file mode 100644 index 0000000..7cdabfa Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-over-corners.gif new file mode 100644 index 0000000..168acfd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-over-fbg.gif new file mode 100644 index 0000000..7cdabfa Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-over-sides.gif new file mode 100644 index 0000000..cca8b8d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-pressed-corners.gif new file mode 100644 index 0000000..fdef27e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-pressed-fbg.gif new file mode 100644 index 0000000..dd9c2e1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-pressed-sides.gif new file mode 100644 index 0000000..0549074 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-sides.gif new file mode 100644 index 0000000..72c1faa Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-over-corners.gif new file mode 100644 index 0000000..0139959 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-over-fbg.gif new file mode 100644 index 0000000..4f078a0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-over-sides.gif new file mode 100644 index 0000000..d845ef2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-pressed-corners.gif new file mode 100644 index 0000000..da18e19 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-pressed-fbg.gif new file mode 100644 index 0000000..dd9c2e1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-pressed-sides.gif new file mode 100644 index 0000000..45fd420 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-sides.gif new file mode 100644 index 0000000..f6555b9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-medium-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-corners.gif new file mode 100644 index 0000000..308020b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-disabled-corners.gif new file mode 100644 index 0000000..8a6fa9d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-disabled-fbg.gif new file mode 100644 index 0000000..c9e2a1f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-disabled-sides.gif new file mode 100644 index 0000000..5e9a2b2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-fbg.gif new file mode 100644 index 0000000..0fab50b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-corners.gif new file mode 100644 index 0000000..9c66fb0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-fbg.gif new file mode 100644 index 0000000..0fab50b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-over-corners.gif new file mode 100644 index 0000000..168acfd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-over-fbg.gif new file mode 100644 index 0000000..0fab50b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-over-sides.gif new file mode 100644 index 0000000..02aadd5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-pressed-corners.gif new file mode 100644 index 0000000..26467dd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-pressed-fbg.gif new file mode 100644 index 0000000..26cb8a1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-pressed-sides.gif new file mode 100644 index 0000000..3e8a3b3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-sides.gif new file mode 100644 index 0000000..9bb8bf8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-over-corners.gif new file mode 100644 index 0000000..0139959 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-over-fbg.gif new file mode 100644 index 0000000..9f43a4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-over-sides.gif new file mode 100644 index 0000000..2c31699 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-pressed-corners.gif new file mode 100644 index 0000000..40a816c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-pressed-fbg.gif new file mode 100644 index 0000000..26cb8a1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-pressed-sides.gif new file mode 100644 index 0000000..9151b21 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-sides.gif new file mode 100644 index 0000000..54716fc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-small-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-corners.gif new file mode 100644 index 0000000..e138e5a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-disabled-corners.gif new file mode 100644 index 0000000..33abe5a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-disabled-fbg.gif new file mode 100644 index 0000000..543e5ec Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-disabled-sides.gif new file mode 100644 index 0000000..aec8db6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-fbg.gif new file mode 100644 index 0000000..f4d58e4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-corners.gif new file mode 100644 index 0000000..6e9c724 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-fbg.gif new file mode 100644 index 0000000..f4d58e4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-over-corners.gif new file mode 100644 index 0000000..3b4ff7c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-over-fbg.gif new file mode 100644 index 0000000..f4d58e4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-over-sides.gif new file mode 100644 index 0000000..33ba5b8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-pressed-corners.gif new file mode 100644 index 0000000..c40ace0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-pressed-fbg.gif new file mode 100644 index 0000000..209f235 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-pressed-sides.gif new file mode 100644 index 0000000..b44d913 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-sides.gif new file mode 100644 index 0000000..1ec77a3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-over-corners.gif new file mode 100644 index 0000000..7fe70c9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-over-fbg.gif new file mode 100644 index 0000000..54f38f0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-over-sides.gif new file mode 100644 index 0000000..1b72758 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-pressed-corners.gif new file mode 100644 index 0000000..a10fca5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-pressed-fbg.gif new file mode 100644 index 0000000..209f235 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-pressed-sides.gif new file mode 100644 index 0000000..1721c22 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-sides.gif new file mode 100644 index 0000000..6d0efd9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-large-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-corners.gif new file mode 100644 index 0000000..533f915 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-disabled-corners.gif new file mode 100644 index 0000000..b16da7f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-disabled-fbg.gif new file mode 100644 index 0000000..4798700 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-disabled-sides.gif new file mode 100644 index 0000000..39353dd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-fbg.gif new file mode 100644 index 0000000..44450d8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-corners.gif new file mode 100644 index 0000000..a1ac809 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-fbg.gif new file mode 100644 index 0000000..44450d8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-over-corners.gif new file mode 100644 index 0000000..1b187b6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-over-fbg.gif new file mode 100644 index 0000000..44450d8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-over-sides.gif new file mode 100644 index 0000000..4dcfe8a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif new file mode 100644 index 0000000..e8dd1d3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-pressed-fbg.gif new file mode 100644 index 0000000..6ed4cf9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif new file mode 100644 index 0000000..b4486b5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-sides.gif new file mode 100644 index 0000000..92921cc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-over-corners.gif new file mode 100644 index 0000000..a077186 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-over-fbg.gif new file mode 100644 index 0000000..2656821 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-over-sides.gif new file mode 100644 index 0000000..78d14e0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-pressed-corners.gif new file mode 100644 index 0000000..bab4074 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-pressed-fbg.gif new file mode 100644 index 0000000..6ed4cf9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-pressed-sides.gif new file mode 100644 index 0000000..9a5aa30 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-sides.gif new file mode 100644 index 0000000..f0df3c5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-medium-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-corners.gif new file mode 100644 index 0000000..533f915 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-disabled-corners.gif new file mode 100644 index 0000000..b16da7f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-disabled-fbg.gif new file mode 100644 index 0000000..b0d0d64 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-disabled-sides.gif new file mode 100644 index 0000000..5992c2f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-fbg.gif new file mode 100644 index 0000000..7c0b0be Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-corners.gif new file mode 100644 index 0000000..a1ac809 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-fbg.gif new file mode 100644 index 0000000..7c0b0be Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-over-corners.gif new file mode 100644 index 0000000..1b187b6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-over-fbg.gif new file mode 100644 index 0000000..7c0b0be Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-over-sides.gif new file mode 100644 index 0000000..a7de889 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-pressed-corners.gif new file mode 100644 index 0000000..e8dd1d3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-pressed-fbg.gif new file mode 100644 index 0000000..f2a7049 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-pressed-sides.gif new file mode 100644 index 0000000..06e5435 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-sides.gif new file mode 100644 index 0000000..8940e9c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-over-corners.gif new file mode 100644 index 0000000..a077186 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-over-fbg.gif new file mode 100644 index 0000000..1884d52 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-over-sides.gif new file mode 100644 index 0000000..0524d4d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-pressed-corners.gif new file mode 100644 index 0000000..bab4074 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-pressed-fbg.gif new file mode 100644 index 0000000..f2a7049 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-pressed-sides.gif new file mode 100644 index 0000000..d58887e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-sides.gif new file mode 100644 index 0000000..87b3ca4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-default-toolbar-small-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-over-corners.gif new file mode 100644 index 0000000..8fdc18b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-over-sides.gif new file mode 100644 index 0000000..5e9c4e0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif new file mode 100644 index 0000000..c40ace0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-pressed-fbg.gif new file mode 100644 index 0000000..209f235 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif new file mode 100644 index 0000000..b44d913 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-over-corners.gif new file mode 100644 index 0000000..7fe70c9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-over-fbg.gif new file mode 100644 index 0000000..54f38f0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-over-sides.gif new file mode 100644 index 0000000..1b72758 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-pressed-corners.gif new file mode 100644 index 0000000..a10fca5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-pressed-fbg.gif new file mode 100644 index 0000000..209f235 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-pressed-sides.gif new file mode 100644 index 0000000..1721c22 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-large-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-over-corners.gif new file mode 100644 index 0000000..8fdc18b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-over-sides.gif new file mode 100644 index 0000000..5e9c4e0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif new file mode 100644 index 0000000..e8dd1d3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-fbg.gif new file mode 100644 index 0000000..6ed4cf9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif new file mode 100644 index 0000000..b4486b5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-over-corners.gif new file mode 100644 index 0000000..a077186 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-over-fbg.gif new file mode 100644 index 0000000..2656821 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-over-sides.gif new file mode 100644 index 0000000..78d14e0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-pressed-corners.gif new file mode 100644 index 0000000..bab4074 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-pressed-fbg.gif new file mode 100644 index 0000000..6ed4cf9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-pressed-sides.gif new file mode 100644 index 0000000..9a5aa30 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-medium-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-over-corners.gif new file mode 100644 index 0000000..8fdc18b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-over-sides.gif new file mode 100644 index 0000000..5e9c4e0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif new file mode 100644 index 0000000..e8dd1d3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-pressed-fbg.gif new file mode 100644 index 0000000..f2a7049 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif new file mode 100644 index 0000000..06e5435 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-over-corners.gif new file mode 100644 index 0000000..a077186 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-over-fbg.gif new file mode 100644 index 0000000..1884d52 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-over-sides.gif new file mode 100644 index 0000000..0524d4d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-pressed-corners.gif new file mode 100644 index 0000000..bab4074 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-pressed-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-pressed-fbg.gif new file mode 100644 index 0000000..f2a7049 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-pressed-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-pressed-sides.gif new file mode 100644 index 0000000..d58887e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/btn/btn-plain-toolbar-small-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-arrow-rtl.png new file mode 100644 index 0000000..76beeab Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-arrow.png new file mode 100644 index 0000000..32674e4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..79677a4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow-b.png new file mode 100644 index 0000000..9f3928a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow-rtl.png new file mode 100644 index 0000000..7985050 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow.png new file mode 100644 index 0000000..06ad27b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-large-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-arrow-rtl.png new file mode 100644 index 0000000..d54d3a0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-arrow.png new file mode 100644 index 0000000..e565db4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..f2fb53b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow-b.png new file mode 100644 index 0000000..ee39ae2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow-rtl.png new file mode 100644 index 0000000..fb11140 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow.png new file mode 100644 index 0000000..c1d1875 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-arrow-rtl.png new file mode 100644 index 0000000..3538445 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-arrow.png new file mode 100644 index 0000000..17a9beb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..2f8b2e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow-b.png new file mode 100644 index 0000000..afd13fb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow-rtl.png new file mode 100644 index 0000000..f59b792 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow.png new file mode 100644 index 0000000..eaffbdc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-arrow-rtl.png new file mode 100644 index 0000000..d8f0151 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-arrow.png new file mode 100644 index 0000000..31fc36e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..379d2d9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow-b.png new file mode 100644 index 0000000..dcfe8ea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow-rtl.png new file mode 100644 index 0000000..612a6b1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow.png new file mode 100644 index 0000000..731b207 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-large-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-arrow-rtl.png new file mode 100644 index 0000000..1648e51 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-arrow.png new file mode 100644 index 0000000..65fdd03 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..8d2232b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow-b.png new file mode 100644 index 0000000..2489479 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow-rtl.png new file mode 100644 index 0000000..c81c5f2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow.png new file mode 100644 index 0000000..0a6857a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-arrow-rtl.png new file mode 100644 index 0000000..8919138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-arrow.png new file mode 100644 index 0000000..b56c2a6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..1142351 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow-b.png new file mode 100644 index 0000000..bb1b08e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow-rtl.png new file mode 100644 index 0000000..9e9e16b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow.png new file mode 100644 index 0000000..9a72857 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/default-toolbar-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-arrow-rtl.png new file mode 100644 index 0000000..3d68e7e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-arrow.png new file mode 100644 index 0000000..17a9beb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-s-arrow-b.png new file mode 100644 index 0000000..afd13fb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-s-arrow-rtl.png new file mode 100644 index 0000000..f59b792 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-s-arrow.png new file mode 100644 index 0000000..eaffbdc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/grid-cell-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-arrow-rtl.png new file mode 100644 index 0000000..d8f0151 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-arrow.png new file mode 100644 index 0000000..31fc36e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..379d2d9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow-b.png new file mode 100644 index 0000000..dcfe8ea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow-rtl.png new file mode 100644 index 0000000..612a6b1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow.png new file mode 100644 index 0000000..731b207 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-large-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-arrow-rtl.png new file mode 100644 index 0000000..1648e51 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-arrow.png new file mode 100644 index 0000000..65fdd03 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..8d2232b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow-b.png new file mode 100644 index 0000000..2489479 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow-rtl.png new file mode 100644 index 0000000..c81c5f2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow.png new file mode 100644 index 0000000..0a6857a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-arrow-rtl.png new file mode 100644 index 0000000..8919138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-arrow.png new file mode 100644 index 0000000..b56c2a6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..1142351 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow-b.png new file mode 100644 index 0000000..bb1b08e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow-rtl.png new file mode 100644 index 0000000..9e9e16b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow.png new file mode 100644 index 0000000..9a72857 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/button/plain-toolbar-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/datepicker/arrow-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/datepicker/arrow-left.png new file mode 100644 index 0000000..fc09f9a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/datepicker/arrow-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/datepicker/arrow-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/datepicker/arrow-right.png new file mode 100644 index 0000000..a22b876 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/datepicker/arrow-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/datepicker/month-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/datepicker/month-arrow.png new file mode 100644 index 0000000..f0b572f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/datepicker/month-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/dd/drop-add.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/dd/drop-add.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/dd/drop-add.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/dd/drop-no.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/dd/drop-no.png new file mode 100644 index 0000000..02e219a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/dd/drop-no.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/dd/drop-yes.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/dd/drop-yes.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/dd/drop-yes.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/editor/tb-sprite.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/editor/tb-sprite.png new file mode 100644 index 0000000..9886118 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/editor/tb-sprite.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/fieldset/collapse-tool.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/fieldset/collapse-tool.png new file mode 100644 index 0000000..97eb83f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/fieldset/collapse-tool.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/checkbox.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/checkbox.png new file mode 100644 index 0000000..fc2709c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/checkbox.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/clear-trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/clear-trigger-rtl.png new file mode 100644 index 0000000..73e1dbe Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/clear-trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/clear-trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/clear-trigger.png new file mode 100644 index 0000000..73e1dbe Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/clear-trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/date-trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/date-trigger-rtl.png new file mode 100644 index 0000000..9489493 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/date-trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/date-trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/date-trigger.png new file mode 100644 index 0000000..9489493 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/date-trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/exclamation.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/exclamation.png new file mode 100644 index 0000000..3e6e3d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/exclamation.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/radio.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/radio.png new file mode 100644 index 0000000..86644bb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/radio.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/search-trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/search-trigger-rtl.png new file mode 100644 index 0000000..15e15f5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/search-trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/search-trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/search-trigger.png new file mode 100644 index 0000000..15e15f5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/search-trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/spinner-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/spinner-rtl.png new file mode 100644 index 0000000..28d140f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/spinner-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/spinner.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/spinner.png new file mode 100644 index 0000000..28d140f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/spinner.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/tag-field-item-close.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/tag-field-item-close.png new file mode 100644 index 0000000..bcb2834 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/tag-field-item-close.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/trigger-rtl.png new file mode 100644 index 0000000..b4e2d5c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/trigger.png new file mode 100644 index 0000000..b4e2d5c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/form/trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif new file mode 100644 index 0000000..b696674 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif new file mode 100644 index 0000000..d50a3c6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif new file mode 100644 index 0000000..c034936 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif new file mode 100644 index 0000000..d50a3c6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/col-move-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/col-move-bottom.png new file mode 100644 index 0000000..9782219 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/col-move-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/col-move-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/col-move-top.png new file mode 100644 index 0000000..6e28535 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/col-move-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/columns.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/columns.png new file mode 100644 index 0000000..70a5c87 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/columns.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dd-insert-arrow-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dd-insert-arrow-left.png new file mode 100644 index 0000000..e8177d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dd-insert-arrow-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dd-insert-arrow-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dd-insert-arrow-right.png new file mode 100644 index 0000000..d610f9d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dd-insert-arrow-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dirty-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dirty-rtl.png new file mode 100644 index 0000000..5f84122 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dirty-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dirty.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dirty.png new file mode 100644 index 0000000..fc06fdd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/dirty.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/drop-no.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/drop-no.png new file mode 100644 index 0000000..02e219a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/drop-no.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/drop-yes.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/drop-yes.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/drop-yes.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/equals.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/equals.png new file mode 100644 index 0000000..c1060ca Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/equals.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/find.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/find.png new file mode 100644 index 0000000..dbfbc16 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/find.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/greater_than.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/greater_than.png new file mode 100644 index 0000000..be41c9a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/greater_than.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/less_than.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/less_than.png new file mode 100644 index 0000000..80aacdd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/filters/less_than.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/group-by.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/group-by.png new file mode 100644 index 0000000..8508ade Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/group-by.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/group-collapse.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/group-collapse.png new file mode 100644 index 0000000..49fcc4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/group-collapse.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/group-expand.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/group-expand.png new file mode 100644 index 0000000..d65a7df Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/group-expand.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hd-pop.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hd-pop.png new file mode 100644 index 0000000..3ad96ef Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hd-pop.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-asc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-asc.png new file mode 100644 index 0000000..a206d35 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-asc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-desc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-desc.png new file mode 100644 index 0000000..55a714e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-desc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-lock.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-lock.png new file mode 100644 index 0000000..b293e10 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-lock.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-unlock.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-unlock.png new file mode 100644 index 0000000..e9e9df5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/hmenu-unlock.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/loading.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/loading.gif new file mode 100644 index 0000000..81b0f12 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/loading.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-first.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-first.png new file mode 100644 index 0000000..7691f32 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-first.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-last.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-last.png new file mode 100644 index 0000000..49b13d7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-last.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-next.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-next.png new file mode 100644 index 0000000..c3e72ba Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-next.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-prev.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-prev.png new file mode 100644 index 0000000..cace90b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/page-prev.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/pick-button.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/pick-button.png new file mode 100644 index 0000000..acaface Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/pick-button.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/refresh.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/refresh.png new file mode 100644 index 0000000..5320ddd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/refresh.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/sort_asc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/sort_asc.png new file mode 100644 index 0000000..a206d35 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/sort_asc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/sort_desc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/sort_desc.png new file mode 100644 index 0000000..55a714e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/grid/sort_desc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/loadmask/loading.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/loadmask/loading.gif new file mode 100644 index 0000000..8471b4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/loadmask/loading.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/magnify.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/magnify.png new file mode 100644 index 0000000..b807c42 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/magnify.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-checked.png new file mode 100644 index 0000000..4f5157d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-group-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-group-checked.png new file mode 100644 index 0000000..a9f0b80 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-group-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menu-parent-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menu-parent-left.png new file mode 100644 index 0000000..d457564 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menu-parent-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menu-parent.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menu-parent.png new file mode 100644 index 0000000..2d2331e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menu-parent.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-checked.png new file mode 100644 index 0000000..4f5157d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-group-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-group-checked.png new file mode 100644 index 0000000..a9f0b80 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-group-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-menu-parent-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-menu-parent-left.png new file mode 100644 index 0000000..9992618 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-menu-parent-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-menu-parent.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-menu-parent.png new file mode 100644 index 0000000..cb3a569 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-menu-parent.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-scroll-bottom.png new file mode 100644 index 0000000..69c61f6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-scroll-top.png new file mode 100644 index 0000000..ca7e3e1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-unchecked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-unchecked.png new file mode 100644 index 0000000..bce8817 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-menubar-unchecked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-scroll-bottom.png new file mode 100644 index 0000000..d89a459 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-scroll-top.png new file mode 100644 index 0000000..bbbf4af Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-unchecked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-unchecked.png new file mode 100644 index 0000000..bce8817 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/menu/default-unchecked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-bottom-corners.gif new file mode 100644 index 0000000..4b1c369 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-bottom-sides.gif new file mode 100644 index 0000000..04ae2be Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif new file mode 100644 index 0000000..5c2013c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif new file mode 100644 index 0000000..04ae2be Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners-rtl.gif new file mode 100644 index 0000000..ff642eb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners.gif new file mode 100644 index 0000000..5c2013c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-left-sides.gif new file mode 100644 index 0000000..d5a75a3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners-rtl.gif new file mode 100644 index 0000000..ff642eb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners.gif new file mode 100644 index 0000000..5c2013c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-right-sides.gif new file mode 100644 index 0000000..d5a75a3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-top-corners.gif new file mode 100644 index 0000000..5c2013c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-top-sides.gif new file mode 100644 index 0000000..04ae2be Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-collapsed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-left-corners-rtl.gif new file mode 100644 index 0000000..6accfd9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-left-corners.gif new file mode 100644 index 0000000..2f2c4e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-left-sides.gif new file mode 100644 index 0000000..d5a75a3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-right-corners-rtl.gif new file mode 100644 index 0000000..ffdae56 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-right-corners.gif new file mode 100644 index 0000000..d4d042b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-right-sides.gif new file mode 100644 index 0000000..d5a75a3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-top-corners.gif new file mode 100644 index 0000000..ee7005f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-top-sides.gif new file mode 100644 index 0000000..04ae2be Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-default-framed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-bottom-corners.gif new file mode 100644 index 0000000..9cdc989 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-bottom-sides.gif new file mode 100644 index 0000000..25f83d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif new file mode 100644 index 0000000..9d2d6e9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif new file mode 100644 index 0000000..25f83d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners-rtl.gif new file mode 100644 index 0000000..3847d54 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners.gif new file mode 100644 index 0000000..9d2d6e9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-left-sides.gif new file mode 100644 index 0000000..ecc4821 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners-rtl.gif new file mode 100644 index 0000000..3847d54 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners.gif new file mode 100644 index 0000000..9d2d6e9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-right-sides.gif new file mode 100644 index 0000000..ecc4821 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-top-corners.gif new file mode 100644 index 0000000..9d2d6e9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-top-sides.gif new file mode 100644 index 0000000..25f83d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-collapsed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-left-corners-rtl.gif new file mode 100644 index 0000000..c2fdd12 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-left-corners.gif new file mode 100644 index 0000000..acafbdd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-left-sides.gif new file mode 100644 index 0000000..ecc4821 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-right-corners-rtl.gif new file mode 100644 index 0000000..f546f8a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-right-corners.gif new file mode 100644 index 0000000..cd5e656 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-right-sides.gif new file mode 100644 index 0000000..ecc4821 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-top-corners.gif new file mode 100644 index 0000000..bba06b3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-top-sides.gif new file mode 100644 index 0000000..25f83d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel-header/panel-header-light-framed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-default-framed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-default-framed-corners.gif new file mode 100644 index 0000000..5c2013c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-default-framed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-default-framed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-default-framed-sides.gif new file mode 100644 index 0000000..d5a75a3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-default-framed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-light-framed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-light-framed-corners.gif new file mode 100644 index 0000000..9d2d6e9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-light-framed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-light-framed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-light-framed-sides.gif new file mode 100644 index 0000000..ecc4821 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/panel/panel-light-framed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-error.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-error.png new file mode 100644 index 0000000..458c098 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-error.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-info.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-info.png new file mode 100644 index 0000000..cbccd11 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-info.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-question.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-question.png new file mode 100644 index 0000000..cac922e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-question.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-warning.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-warning.png new file mode 100644 index 0000000..042ca05 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/shared/icon-warning.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/e-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/e-handle.png new file mode 100644 index 0000000..2fe5cb1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/e-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/ne-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/ne-handle.png new file mode 100644 index 0000000..8d8eb63 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/ne-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/nw-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/nw-handle.png new file mode 100644 index 0000000..9835bea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/nw-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/s-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/s-handle.png new file mode 100644 index 0000000..06f914e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/s-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/se-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/se-handle.png new file mode 100644 index 0000000..5a2c695 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/se-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/sw-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/sw-handle.png new file mode 100644 index 0000000..7f68f40 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/sizer/sw-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-bg.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-bg.png new file mode 100644 index 0000000..1ade292 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-bg.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-thumb.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-thumb.png new file mode 100644 index 0000000..d8a03de Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-thumb.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-v-bg.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-v-bg.png new file mode 100644 index 0000000..c24663e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-v-bg.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-v-thumb.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-v-thumb.png new file mode 100644 index 0000000..d8a03de Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/slider/slider-v-thumb.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-more-left.png new file mode 100644 index 0000000..83b0288 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-more.png new file mode 100644 index 0000000..83b0288 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-bottom.png new file mode 100644 index 0000000..813a4d5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-left.png new file mode 100644 index 0000000..9120ea4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-right.png new file mode 100644 index 0000000..67fd5a4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-top.png new file mode 100644 index 0000000..01ad4ee Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-plain-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-bottom.png new file mode 100644 index 0000000..ffff826 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-left.png new file mode 100644 index 0000000..2c35294 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-right.png new file mode 100644 index 0000000..82dfe01 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-top.png new file mode 100644 index 0000000..b2fabfc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab-bar/default-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-active-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-active-corners.gif new file mode 100644 index 0000000..772d73e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-active-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-active-fbg.gif new file mode 100644 index 0000000..a97f73a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-active-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-active-sides.gif new file mode 100644 index 0000000..25e7096 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-active-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-corners.gif new file mode 100644 index 0000000..d464060 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-disabled-corners.gif new file mode 100644 index 0000000..d464060 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-disabled-fbg.gif new file mode 100644 index 0000000..a0f3621 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-disabled-sides.gif new file mode 100644 index 0000000..38624e0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-active-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-active-corners.gif new file mode 100644 index 0000000..a170574 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-active-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-active-fbg.gif new file mode 100644 index 0000000..a97f73a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-active-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-active-sides.gif new file mode 100644 index 0000000..81331b4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-active-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-corners.gif new file mode 100644 index 0000000..81cf886 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-fbg.gif new file mode 100644 index 0000000..a0f3621 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-over-corners.gif new file mode 100644 index 0000000..38786eb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-over-fbg.gif new file mode 100644 index 0000000..ed6973c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-over-sides.gif new file mode 100644 index 0000000..4c0b366 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-sides.gif new file mode 100644 index 0000000..96e7cc8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-over-corners.gif new file mode 100644 index 0000000..be92916 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-over-fbg.gif new file mode 100644 index 0000000..ed6973c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-over-sides.gif new file mode 100644 index 0000000..ff247d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-sides.gif new file mode 100644 index 0000000..9a930d1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-close.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-close.png new file mode 100644 index 0000000..46cc89f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-close.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-active-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-active-corners.gif new file mode 100644 index 0000000..d32c32e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-active-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-active-fbg.gif new file mode 100644 index 0000000..378ad4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-active-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-active-sides.gif new file mode 100644 index 0000000..92c8579 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-active-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-corners.gif new file mode 100644 index 0000000..cd54f97 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-disabled-corners.gif new file mode 100644 index 0000000..cd54f97 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-disabled-fbg.gif new file mode 100644 index 0000000..a1613bd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-disabled-sides.gif new file mode 100644 index 0000000..9a930d1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-active-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-active-corners.gif new file mode 100644 index 0000000..ea7d155 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-active-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-active-fbg.gif new file mode 100644 index 0000000..378ad4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-active-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-active-sides.gif new file mode 100644 index 0000000..e11a208 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-active-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-corners.gif new file mode 100644 index 0000000..e217b9e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-fbg.gif new file mode 100644 index 0000000..a1613bd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-over-corners.gif new file mode 100644 index 0000000..c5ada20 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-over-fbg.gif new file mode 100644 index 0000000..5f02581 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-over-sides.gif new file mode 100644 index 0000000..4715f08 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-sides.gif new file mode 100644 index 0000000..16a8130 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-over-corners.gif new file mode 100644 index 0000000..1ebfb76 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-over-fbg.gif new file mode 100644 index 0000000..5f02581 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-over-sides.gif new file mode 100644 index 0000000..1e754d5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-sides.gif new file mode 100644 index 0000000..9a930d1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-active-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-active-corners.gif new file mode 100644 index 0000000..53d3460 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-active-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-active-fbg.gif new file mode 100644 index 0000000..378ad4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-active-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-active-sides.gif new file mode 100644 index 0000000..92c8579 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-active-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-corners.gif new file mode 100644 index 0000000..44b7def Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-disabled-corners.gif new file mode 100644 index 0000000..44b7def Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-disabled-fbg.gif new file mode 100644 index 0000000..a1613bd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-disabled-sides.gif new file mode 100644 index 0000000..9a930d1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-active-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-active-corners.gif new file mode 100644 index 0000000..324b647 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-active-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-active-fbg.gif new file mode 100644 index 0000000..378ad4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-active-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-active-sides.gif new file mode 100644 index 0000000..e11a208 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-active-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-corners.gif new file mode 100644 index 0000000..bac5649 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-fbg.gif new file mode 100644 index 0000000..a1613bd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-over-corners.gif new file mode 100644 index 0000000..1b8ebdb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-over-fbg.gif new file mode 100644 index 0000000..5f02581 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-over-sides.gif new file mode 100644 index 0000000..4715f08 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-sides.gif new file mode 100644 index 0000000..16a8130 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-over-corners.gif new file mode 100644 index 0000000..cfddf88 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-over-fbg.gif new file mode 100644 index 0000000..5f02581 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-over-sides.gif new file mode 100644 index 0000000..1e754d5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-sides.gif new file mode 100644 index 0000000..9a930d1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-active-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-active-corners.gif new file mode 100644 index 0000000..27c37ca Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-active-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-active-fbg.gif new file mode 100644 index 0000000..a97f73a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-active-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-active-sides.gif new file mode 100644 index 0000000..25e7096 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-active-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-corners.gif new file mode 100644 index 0000000..9a5ecf1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-disabled-corners.gif new file mode 100644 index 0000000..9a5ecf1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-disabled-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-disabled-fbg.gif new file mode 100644 index 0000000..a0f3621 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-disabled-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-disabled-sides.gif new file mode 100644 index 0000000..38624e0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-active-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-active-corners.gif new file mode 100644 index 0000000..310a463 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-active-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-active-fbg.gif new file mode 100644 index 0000000..a97f73a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-active-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-active-sides.gif new file mode 100644 index 0000000..81331b4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-active-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-corners.gif new file mode 100644 index 0000000..b5f3b71 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-fbg.gif new file mode 100644 index 0000000..a0f3621 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-over-corners.gif new file mode 100644 index 0000000..2175d71 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-over-fbg.gif new file mode 100644 index 0000000..ed6973c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-over-sides.gif new file mode 100644 index 0000000..4c0b366 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-sides.gif new file mode 100644 index 0000000..96e7cc8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-over-corners.gif new file mode 100644 index 0000000..3bd69f1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-over-fbg.gif new file mode 100644 index 0000000..ed6973c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-over-sides.gif new file mode 100644 index 0000000..ff247d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-sides.gif new file mode 100644 index 0000000..9a930d1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tab/tab-default-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-default-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-default-corners.gif new file mode 100644 index 0000000..5930b0c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-default-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-default-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-default-sides.gif new file mode 100644 index 0000000..a8974c6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-default-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-form-invalid-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-form-invalid-corners.gif new file mode 100644 index 0000000..5930b0c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-form-invalid-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-form-invalid-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-form-invalid-sides.gif new file mode 100644 index 0000000..a8974c6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tip/tip-form-invalid-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-bottom.png new file mode 100644 index 0000000..6741161 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-top.png new file mode 100644 index 0000000..2a26ba9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/default-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/toolbar/footer-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tools/tool-sprites-dark.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tools/tool-sprites-dark.png new file mode 100644 index 0000000..474088b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tools/tool-sprites-dark.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tools/tool-sprites.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tools/tool-sprites.png new file mode 100644 index 0000000..17fbc0f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tools/tool-sprites.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/arrows-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/arrows-rtl.png new file mode 100644 index 0000000..4aae887 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/arrows-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/arrows.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/arrows.png new file mode 100644 index 0000000..de10dd6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/arrows.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-above.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-above.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-above.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-add.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-add.gif new file mode 100644 index 0000000..b22cd14 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-add.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-add.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-add.png new file mode 100644 index 0000000..c9d24fd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-add.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-append.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-append.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-append.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-below.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-below.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-below.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-between.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-between.gif new file mode 100644 index 0000000..f5a042d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-between.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-between.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-between.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-between.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-no.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-no.gif new file mode 100644 index 0000000..9d9c6a9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-no.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-no.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-no.png new file mode 100644 index 0000000..bb89cfc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-no.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-over.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-over.gif new file mode 100644 index 0000000..2e514e7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-over.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-over.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-over.png new file mode 100644 index 0000000..70d1807 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-over.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-under.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-under.gif new file mode 100644 index 0000000..8535ef4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-under.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-under.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-under.png new file mode 100644 index 0000000..3ba23b3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-under.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-yes.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-yes.gif new file mode 100644 index 0000000..8aacb30 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-yes.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-yes.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-yes.png new file mode 100644 index 0000000..83d0dbc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/drop-yes.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-minus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-minus-rtl.png new file mode 100644 index 0000000..2ffe7b2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-minus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-minus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-minus.png new file mode 100644 index 0000000..b39a71d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-minus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-plus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-plus-rtl.png new file mode 100644 index 0000000..bea9892 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-plus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-plus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-plus.png new file mode 100644 index 0000000..630438f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-plus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-rtl.png new file mode 100644 index 0000000..1d0821b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end.png new file mode 100644 index 0000000..2eb0ed0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-end.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-line-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-line-rtl.png new file mode 100644 index 0000000..e26b768 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-line-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-line.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-line.png new file mode 100644 index 0000000..ac37424 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-line.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus-nl-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus-nl-rtl.png new file mode 100644 index 0000000..1008a54 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus-nl-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus-nl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus-nl.png new file mode 100644 index 0000000..f2a805d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus-nl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus-rtl.png new file mode 100644 index 0000000..cefb704 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus.png new file mode 100644 index 0000000..a256b48 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-minus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus-nl-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus-nl-rtl.png new file mode 100644 index 0000000..e1e6ece Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus-nl-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus-nl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus-nl.png new file mode 100644 index 0000000..3a401ea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus-nl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus-rtl.png new file mode 100644 index 0000000..487f27a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus.png new file mode 100644 index 0000000..03e202a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-plus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-rtl.png new file mode 100644 index 0000000..166e163 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow.png new file mode 100644 index 0000000..4bf9ae5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/elbow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder-open-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder-open-rtl.png new file mode 100644 index 0000000..bb896d8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder-open-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder-open.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder-open.png new file mode 100644 index 0000000..50397da Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder-open.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder-rtl.png new file mode 100644 index 0000000..3b17672 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder.png new file mode 100644 index 0000000..4b02054 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/folder.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/leaf-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/leaf-rtl.png new file mode 100644 index 0000000..b2e6f6e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/leaf-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/leaf.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/leaf.png new file mode 100644 index 0000000..6acb635 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/leaf.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/loading.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/loading.gif new file mode 100644 index 0000000..81b0f12 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/tree/loading.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-bottom.png new file mode 100644 index 0000000..241209e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-left.png new file mode 100644 index 0000000..1c40b78 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-right.png new file mode 100644 index 0000000..505c329 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-top.png new file mode 100644 index 0000000..4a378a3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/util/splitter/mini-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-bottom-corners.gif new file mode 100644 index 0000000..4ceff70 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-bottom-sides.gif new file mode 100644 index 0000000..3bef182 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-bottom-corners.gif new file mode 100644 index 0000000..b485603 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-bottom-sides.gif new file mode 100644 index 0000000..3bef182 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-left-corners-rtl.gif new file mode 100644 index 0000000..62320d8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-left-corners.gif new file mode 100644 index 0000000..b485603 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-left-sides.gif new file mode 100644 index 0000000..2f6ca43 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-right-corners-rtl.gif new file mode 100644 index 0000000..62320d8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-right-corners.gif new file mode 100644 index 0000000..b485603 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-right-sides.gif new file mode 100644 index 0000000..2f6ca43 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-top-corners.gif new file mode 100644 index 0000000..b485603 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-top-sides.gif new file mode 100644 index 0000000..3bef182 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-collapsed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-left-corners-rtl.gif new file mode 100644 index 0000000..5f5d3fa Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-left-corners.gif new file mode 100644 index 0000000..3097e29 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-left-sides.gif new file mode 100644 index 0000000..2f6ca43 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-right-corners-rtl.gif new file mode 100644 index 0000000..b898967 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-right-corners.gif new file mode 100644 index 0000000..1e257bb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-right-sides.gif new file mode 100644 index 0000000..2f6ca43 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-top-corners.gif new file mode 100644 index 0000000..04ae090 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-top-sides.gif new file mode 100644 index 0000000..3bef182 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window-header/window-header-default-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/fade-blue.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/fade-blue.png new file mode 100644 index 0000000..4dbf08b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/fade-blue.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/fader.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/fader.png new file mode 100644 index 0000000..be8c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/fader.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/icon16_error.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/icon16_error.png new file mode 100644 index 0000000..5f168d3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/icon16_error.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/icon16_info.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/icon16_info.png new file mode 100644 index 0000000..6c6b32d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/toast/icon16_info.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/window-default-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/window-default-corners.gif new file mode 100644 index 0000000..b485603 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/window-default-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/window-default-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/window-default-sides.gif new file mode 100644 index 0000000..2f6ca43 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/images/window/window-default-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-base/Readme.md b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-base/Readme.md new file mode 100644 index 0000000..a0d00c3 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-base/Readme.md @@ -0,0 +1,3 @@ +# theme-base/resources + +This folder contains static resources (typically an `"images"` folder as well). diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all-debug.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all-debug.css new file mode 100644 index 0000000..9b094a4 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all-debug.css @@ -0,0 +1,2 @@ +@import 'theme-neptune-all-debug_1.css'; +@import 'theme-neptune-all-debug_2.css'; diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all-debug_1.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all-debug_1.css new file mode 100644 index 0000000..5d4474c --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all-debug_1.css @@ -0,0 +1,15819 @@ +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:5 */ +.x-size-monitored { + /** + * @class Ext.util.SizeMonitor + */ + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:9 */ +.x-size-monitors { + position: absolute; + left: 0; + top: 0; + width: 100%; + height: 100%; + visibility: hidden; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:18 */ +.x-size-monitors > * { + width: 100%; + height: 100%; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:25 */ +.x-size-monitors.scroll > *.shrink::after { + content: ''; + display: block; + width: 200%; + height: 200%; + min-width: 1px; + min-height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:34 */ +.x-size-monitors.scroll > *.expand::after { + content: ''; + display: block; + width: 100000px; + height: 100000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:44 */ +.x-size-monitors.overflowchanged > *.shrink > * { + width: 100%; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:51 */ +.x-size-monitors.overflowchanged > *.expand > * { + width: 200%; + height: 200%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:59 */ +.x-size-change-detector { + visibility: hidden; + position: absolute; + left: 0; + top: 0; + z-index: -1; + width: 100%; + height: 100%; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:70 */ +.x-size-change-detector > * { + visibility: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:74 */ +.x-size-change-detector-shrink > * { + width: 200%; + height: 200%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:79 */ +.x-size-change-detector-expand > * { + width: 100000px; + height: 100000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:5 */ +@-webkit-keyframes x-paint-monitor-helper { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:6 */ + from { + /** + * @class Ext.util.PaintMonitor + */ + /** + * @class Ext.util.PaintMonitor + */ + zoom: 1; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:9 */ + to { + zoom: 1; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:14 */ +@keyframes x-paint-monitor-helper { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:15 */ + from { + zoom: 1; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:18 */ + to { + zoom: 1; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:23 */ +.x-paint-monitored { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:27 */ +.x-paint-monitor { + width: 0 !important; + height: 0 !important; + visibility: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:32 */ +.x-paint-monitor.cssanimation { + -webkit-animation-duration: 0.0001ms; + -webkit-animation-name: x-paint-monitor-helper; + animation-duration: 0.0001ms; + animation-name: x-paint-monitor-helper; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:39 */ +.x-paint-monitor.overflowchange { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:42 */ +.x-paint-monitor.overflowchange::after { + content: ''; + display: block; + width: 1px !important; + height: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:2 */ +.x-unselectable { + user-select: none; + -o-user-select: none; + -ms-user-select: none; + -moz-user-select: -moz-none; + -webkit-user-select: none; + -webkit-tap-highlight-color: transparent; + -webkit-user-drag: none; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:7 */ +.x-hidden-clip { + position: absolute !important; + clip: rect(0, 0, 0, 0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:12 */ +.x-hidden-display { + display: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:16 */ +.x-hidden-offsets, +.x-hidden { + display: block !important; + visibility: hidden !important; + position: absolute !important; + top: -10000px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:26 */ +.x-hidden-opacity { + opacity: 0 !important; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:31 */ +.x-hidden-visibility { + visibility: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:36 */ +.x-pressed .x-ripple-transition, +.x-pressing .x-ripple-transition { + transition: background-color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1), color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:40 */ +.x-pressed .x-ripple-transition .x-icon-el, +.x-pressed .x-ripple-transition .x-arrow-el, +.x-pressing .x-ripple-transition .x-icon-el, +.x-pressing .x-ripple-transition .x-arrow-el { + transition: background-color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1), color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:45 */ +.x-rippling { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:48 */ +.x-rippling.x-component-confirm .x-ripple { + background-color: green; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:52 */ +.x-rippling.x-component-decline .x-ripple { + background-color: red; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:57 */ +.x-rippling.x-rippling-unbound { + overflow: visible !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:59 */ +.x-rippling.x-rippling-unbound .x-ripple-container { + overflow: visible; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:68 */ +.x-safari .x-rippling:not(.x-rippling-unbound) .x-ripple-container { + -webkit-transform: rotate(0); + -moz-transform: rotate(0); + -ms-transform: rotate(0); + -o-transform: rotate(0); + transform: rotate(0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:72 */ +.x-ripple-container { + overflow: hidden; + position: absolute; + top: 0; + bottom: 0; + left: 0; + right: 0; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:83 */ +.x-ripple-wrapper { + z-index: 1000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:88 */ +.x-button-fab .x-ripple-container, +.x-button-round .x-ripple-container { + border-radius: 10000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:93 */ +.x-splitButton-fab .x-ripple-container, +.x-splitButton-round .x-ripple-container { + border-radius: 10000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:97 */ +.x-ripple { + position: absolute; + border-radius: 50%; + background-color: white; + -webkit-transform: scale(1, 1); + -moz-transform: scale(1, 1); + -ms-transform: scale(1, 1); + -o-transform: scale(1, 1); + transform: scale(1, 1); + opacity: 0.4; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:106 */ +.x-rippling.x-rippling-unbound .x-ripple { + -webkit-animation: x-ripple-unbound-animation 0.3s ease-out forwards; + animation: x-ripple-unbound-animation 0.3s ease-out forwards; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:110 */ +.x-rippling:not(.x-rippling-unbound) .x-ripple { + -webkit-animation: x-ripple-animation 0.35s ease-out forwards; + animation: x-ripple-animation 0.35s ease-out forwards; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/etc/mixins/animation.scss:17 */ +@-webkit-keyframes x-ripple-animation { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:115 */ + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:119 */ + 75% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0.2; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:123 */ + 100% { + -webkit-transform: scale(2.35, 2.35); + -moz-transform: scale(2.35, 2.35); + -ms-transform: scale(2.35, 2.35); + -o-transform: scale(2.35, 2.35); + transform: scale(2.35, 2.35); + opacity: 0; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/etc/mixins/animation.scss:20 */ +@keyframes x-ripple-animation { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:115 */ + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:119 */ + 75% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0.2; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:123 */ + 100% { + -webkit-transform: scale(2.35, 2.35); + -moz-transform: scale(2.35, 2.35); + -ms-transform: scale(2.35, 2.35); + -o-transform: scale(2.35, 2.35); + transform: scale(2.35, 2.35); + opacity: 0; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/etc/mixins/animation.scss:17 */ +@-webkit-keyframes x-ripple-unbound-animation { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:130 */ + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:134 */ + 75% { + -webkit-transform: scale(1.75, 1.75); + -moz-transform: scale(1.75, 1.75); + -ms-transform: scale(1.75, 1.75); + -o-transform: scale(1.75, 1.75); + transform: scale(1.75, 1.75); + opacity: 0.2; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:138 */ + 100% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/etc/mixins/animation.scss:20 */ +@keyframes x-ripple-unbound-animation { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:130 */ + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:134 */ + 75% { + -webkit-transform: scale(1.75, 1.75); + -moz-transform: scale(1.75, 1.75); + -ms-transform: scale(1.75, 1.75); + -o-transform: scale(1.75, 1.75); + transform: scale(1.75, 1.75); + opacity: 0.2; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:138 */ + 100% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/ProgressBase.scss:1 */ +.x-progress { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/ProgressBase.scss:6 */ +.x-progress-bar { + height: 100%; + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/ProgressBase.scss:11 */ +.x-progress-text { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/ProgressBase.scss:15 */ +.x-progress-bar { + overflow: hidden; + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:1 */ +.x-scroller { + -webkit-overflow-scrolling: touch; + overflow-anchor: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:6 */ +.x-scroller-spacer { + position: absolute; + top: 0; + overflow: hidden; + height: 1px; + width: 1px; + font-size: 0; + line-height: 0; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:17 */ +.x-scroller-snappable { + -ms-scroll-snap-type: mandatory; + -webkit-scroll-snap-type: mandatory; + scroll-snap-type: mandatory; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:23 */ +.x-no-scrollbars { + -ms-overflow-style: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:26 */ +.x-no-scrollbars::-webkit-scrollbar { + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/TouchAction.scss:1 */ +.x-touch-action-pan-y { + overflow-x: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/TouchAction.scss:5 */ +.x-touch-action-pan-x { + overflow-y: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/drag/Source.scss:4 */ +.x-drag-body { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/drag/Source.scss:6 */ +.x-drag-body * { + -webkit-user-select: none; + -moz-user-select: none; + user-select: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/drag/Source.scss:11 */ +.x-drag-dragging { + z-index: 1000000!important; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:576 */ +.x-treelist { + background-color: #fff; + background-position: 16px 0%; + overflow: hidden; + padding: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:589 */ +.x-treelist-container, +.x-treelist-root-container { + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:594 */ +.x-treelist-toolstrip { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:599 */ +.x-treelist-micro > .x-treelist-toolstrip { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:602 */ +.x-treelist-micro > .x-treelist-root-container { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:607 */ +.x-treelist-item, +.x-treelist-container, +.x-treelist-root-container { + position: relative; + overflow: hidden; + list-style: none; + padding: 0; + margin: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:617 */ +.x-treelist-item-tool, +.x-treelist-row, +.x-treelist-item-wrap { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:623 */ +.x-treelist-item-icon, +.x-treelist-item-expander { + display: none; + position: absolute; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:630 */ +.x-treelist-item-expander { + right: 0; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:635 */ +.x-treelist-expander-only .x-treelist-item-expandable > * > .x-treelist-item-wrap > * { + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:639 */ +.x-treelist-item-text { + cursor: pointer; + white-space: nowrap; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:645 */ +.x-treelist-item-collapsed > .x-treelist-container { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:649 */ +.x-treelist-item-expandable > * > * > .x-treelist-item-expander, +.x-treelist-item-icon { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:654 */ +.x-treelist-item-floated > * > * > .x-treelist-item-expander, +.x-treelist-item-floated > * > * > .x-treelist-item-icon { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:659 */ +.x-treelist-expander-first .x-treelist-item-expander { + left: 0; + right: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:103 */ +.x-treelist-toolstrip { + background-color: #f8f8f8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:134 */ +.x-treelist-item-selected > .x-treelist-row { + background-color: #c2ddf2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:138 */ +.x-treelist-item-selected > .x-treelist-row-over { + background-color: #c2ddf2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:143 */ +.x-treelist-item-tool { + padding-left: 6px; + padding-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:166 */ +.x-treelist-item-icon:before, +.x-treelist-item-tool:before, +.x-treelist-item-expander { + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:178 */ +.x-treelist-item-icon, +.x-treelist-item-tool, +.x-treelist-item-expander { + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:188 */ +.x-treelist-item-loading .x-treelist-item-icon { + background-image: url(images/tree/loading.gif); + color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:193 */ +.x-treelist-item-icon, +.x-treelist-item-tool { + color: #b0b0b0; + font-size: 16px; + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:206 */ +.x-treelist-item-tool { + width: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:216 */ +.x-treelist-item-expander { + color: #b0b0b0; + font-size: 16px; + width: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:232 */ +.x-treelist-item-expander:after { + content: "\f0da"; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:240 */ +.x-treelist-item-expanded > * > * > .x-treelist-item-expander:after { + content: "\f0d7"; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:253 */ +.x-treelist-item-text { + color: #000; + margin-left: 20px; + margin-right: 18px; + font-size: 13px; + line-height: 24px; + text-overflow: ellipsis; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:270 */ +.x-treelist-row { + padding-left: 6px; + padding-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:301 */ +.x-treelist-item-floated .x-treelist-container { + width: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:304 */ +.x-treelist-item-floated > .x-treelist-row { + background-color: #f8f8f8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:308 */ +.x-treelist-item-floated > .x-treelist-container { + margin-left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:311 */ +.x-big .x-treelist-item-floated > .x-treelist-container { + margin-left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:317 */ +.x-treelist-item-floated > * > * > .x-treelist-item-text { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:321 */ +.x-treelist-item-floated > * .x-treelist-row { + cursor: pointer; + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:326 */ +.x-treelist-item-floated .x-treelist-row:before { + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:330 */ +.x-treelist-item-floated > .x-treelist-row-over { + background-color: #f8f8f8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:333 */ +.x-treelist-item-floated > .x-treelist-row-over > * > .x-treelist-item-text { + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:346 */ +.x-treelist-item-expanded > .x-treelist-item-expander:after { + content: "\f0d7"; + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:351 */ +.x-treelist-item-collapsed > * > .x-treelist-item-expander:after { + content: "\f0da"; + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:357 */ +.x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-icon { + color: #b0b0b0; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:361 */ +.x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-text { + color: #000; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:365 */ +.x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-expander { + color: #b0b0b0; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:372 */ +.x-treelist-row-over { + background-color: #e2eff9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:376 */ +.x-treelist-row-over > * > .x-treelist-item-icon { + color: #b0b0b0; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:380 */ +.x-treelist-row-over > * > .x-treelist-item-text { + color: #000; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:384 */ +.x-treelist-row-over > * > .x-treelist-item-expander { + color: #b0b0b0; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:391 */ +.x-treelist-expander-first .x-treelist-item-icon { + left: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:400 */ +.x-treelist-expander-first .x-treelist-item-text { + margin-left: 38px; + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:410 */ +.x-treelist-expander-first .x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:420 */ +.x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:495 */ +.x-treelist-nav { + background-color: #32404e; + background-position: 24px 0%; + padding: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:103 */ +.x-treelist-nav .x-treelist-toolstrip { + background-color: #32404e; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:112 */ +.x-treelist-nav .x-treelist-item-selected.x-treelist-item-tool { + color: #f0f0f0; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:134 */ +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row { + background-color: #3f505f; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:143 */ +.x-treelist-nav .x-treelist-item-tool { + padding-left: 10px; + padding-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:150 */ +.x-treelist-nav .x-treelist-item-tool-floated:after { + height: 44px; + position: absolute; + top: 0; + left: 0; + content: " "; + width: 4px; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:166 */ +.x-treelist-nav .x-treelist-item-icon:before, +.x-treelist-nav .x-treelist-item-tool:before, +.x-treelist-nav .x-treelist-item-expander { + line-height: 44px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:178 */ +.x-treelist-nav .x-treelist-item-icon, +.x-treelist-nav .x-treelist-item-tool, +.x-treelist-nav .x-treelist-item-expander { + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:188 */ +.x-treelist-nav .x-treelist-item-loading .x-treelist-item-icon { + background-image: url(images/tree/loading.gif); + color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:193 */ +.x-treelist-nav .x-treelist-item-icon, +.x-treelist-nav .x-treelist-item-tool { + color: #adb3b8; + font-size: 18px; + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:206 */ +.x-treelist-nav .x-treelist-item-tool { + width: 44px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:216 */ +.x-treelist-nav .x-treelist-item-expander { + color: #adb3b8; + font-size: 16px; + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:253 */ +.x-treelist-nav .x-treelist-item-text { + color: #adb3b8; + margin-left: 28px; + margin-right: 24px; + font-size: 16px; + line-height: 44px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:270 */ +.x-treelist-nav .x-treelist-row { + padding-left: 10px; + padding-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:276 */ +.x-treelist-nav .x-treelist-row-over:before, +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before { + content: " "; + position: absolute; + display: block; + left: 0; + top: 0; + width: 6px; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:287 */ +.x-treelist-nav .x-treelist-row-over:before { + background-color: #2b99e9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:291 */ +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row-over:before { + background-color: #2b99e9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:295 */ +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:301 */ +.x-treelist-nav .x-treelist-item-floated .x-treelist-container { + width: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:304 */ +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row { + background-color: #32404e; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:308 */ +.x-treelist-nav .x-treelist-item-floated > .x-treelist-container { + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:311 */ +.x-big .x-treelist-nav .x-treelist-item-floated > .x-treelist-container { + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:317 */ +.x-treelist-nav .x-treelist-item-floated > * > * > .x-treelist-item-text { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:321 */ +.x-treelist-nav .x-treelist-item-floated > * .x-treelist-row { + cursor: pointer; + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:326 */ +.x-treelist-nav .x-treelist-item-floated .x-treelist-row:before { + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:330 */ +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row-over { + background-color: #32404e; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:333 */ +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row-over > * > .x-treelist-item-text { + color: #adb3b8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:339 */ +.x-treelist-nav .x-treelist-item-expanded { + background-color: #2c3845; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:357 */ +.x-treelist-nav .x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-icon { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:361 */ +.x-treelist-nav .x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-text { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:365 */ +.x-treelist-nav .x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-expander { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:372 */ +.x-treelist-nav .x-treelist-row-over { + background-color: #4f606f; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:376 */ +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-icon { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:380 */ +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-text { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:384 */ +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-expander { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:391 */ +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-icon { + left: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:400 */ +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-text { + margin-left: 52px; + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:410 */ +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:420 */ +.x-treelist-nav .x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:14 */ +.x-body { + margin: 0; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:23 */ +@-ms-viewport { + width: device-width; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:28 */ +img { + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:32 */ +.x-border-box, +.x-border-box * { + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:46 */ +.x-ltr { + direction: ltr; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:50 */ +.x-clear { + overflow: hidden; + clear: both; + font-size: 0; + line-height: 0; + display: table; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:58 */ +.x-layer { + position: absolute !important; + top: 0; + left: 0; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:72 */ +.x-fixed-layer { + position: fixed !important; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:77 */ +.x-shim { + position: absolute; + left: 0; + top: 0; + overflow: hidden; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:90 */ +.x-hidden-clip { + position: absolute !important; + clip: rect(0, 0, 0, 0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:95 */ +.x-masked-relative { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:101 */ +.x-ie-shadow { + background-color: #777; + position: absolute; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:108 */ +.x-selectable { + cursor: auto; + -moz-user-select: text; + -webkit-user-select: text; + -ms-user-select: text; + user-select: text; + -o-user-select: text; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:123 */ +.x-list-plain { + list-style-type: none; + margin: 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:130 */ +.x-table-plain { + border-collapse: collapse; + border-spacing: 0; + font-size: 1em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:138 */ +.x-frame-tl, +.x-frame-tr, +.x-frame-tc, +.x-frame-bl, +.x-frame-br, +.x-frame-bc { + overflow: hidden; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:148 */ +.x-frame-tc, +.x-frame-bc { + background-repeat: repeat-x; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:157 */ +td.x-frame-tl, +td.x-frame-tr, +td.x-frame-bl, +td.x-frame-br { + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:164 */ +.x-frame-mc { + background-repeat: repeat-x; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:169 */ +.x-proxy-el { + position: absolute; + background: #b4b4b4; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:176 */ +.x-css-shadow { + position: absolute; + -webkit-border-radius: 5px; + -moz-border-radius: 5px; + -ms-border-radius: 5px; + -o-border-radius: 5px; + border-radius: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:181 */ +.x-item-disabled, +.x-item-disabled * { + cursor: default; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:187 */ +.x-component, +.x-container { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:197 */ +:focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:206 */ +.x-body .x-sync-repaint:before, +.x-body .x-sync-repaint:after { + content: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:215 */ +.x-position-relative { + position: relative !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:221 */ +.x-tab-guard { + position: absolute; + clip: rect(0, 0, 0, 0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Container.scss:3 */ +.x-box-item { + position: absolute !important; + left: 0; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Auto.scss:1 */ +.x-autocontainer-outerCt { + display: table; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Auto.scss:4 */ +.x-mobile-safari .x-autocontainer-outerCt { + transform: translateZ(0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Auto.scss:14 */ +.x-clipped .x-autocontainer-outerCt { + transform: initial; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Auto.scss:18 */ +.x-autocontainer-innerCt { + display: table-cell; + height: 100%; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/LoadMask.scss:1 */ +.x-mask { + z-index: 100; + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + /* + * IE and FF will add an outline to focused elements, + * which we don't want when using our own focus treatment + */ + outline: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/LoadMask.scss:21 */ +.x-ie8 .x-mask { + /* + * IE8 will treat partially transparent divs as invalid click targets, + * allowing mouse events to reach elements beneath the mask. Placing + * a 1x1 transparent gif as the link el background will cure this. + */ + background-image: url(data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/LoadMask.scss:27 */ +.x-mask-fixed { + position: fixed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/LoadMask.scss:31 */ +.x-mask-msg { + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/ProgressBar.scss:1 */ +.x-progress { + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:21 */ +.x-btn { + display: inline-block; + outline: 0; + cursor: pointer; + white-space: nowrap; + text-decoration: none; + vertical-align: top; + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:33 */ +.x-btn > .x-frame { + height: 100%; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:39 */ +.x-btn-wrap { + height: 100%; + width: 100%; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: stretch; + -ms-flex-align: stretch; + align-items: stretch; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:47 */ +.x-btn-wrap.x-btn-arrow-bottom, +.x-btn-wrap.x-btn-split-bottom { + -webkit-box-orient: vertical; + -ms-flex-direction: column; + flex-direction: column; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:53 */ +.x-ie9m .x-btn-wrap { + display: table; + border-spacing: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:64 */ +.x-btn-button { + white-space: nowrap; + line-height: 0; + position: relative; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: center; + -ms-flex-align: center; + align-items: center; + -webkit-box-flex: 1; + -ms-flex: 1 1 auto; + flex: 1 1 auto; + min-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:76 */ +.x-btn-button.x-btn-icon-top, +.x-btn-button.x-btn-icon-bottom { + -webkit-box-orient: vertical; + -ms-flex-direction: column; + flex-direction: column; + -webkit-box-align: stretch; + -ms-flex-align: stretch; + align-items: stretch; + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:85 */ +.x-ie10p .x-btn-button.x-btn-icon-top, +.x-ie10p .x-btn-button.x-btn-icon-bottom { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:92 */ +.x-ie9m .x-btn-button { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:103 */ +.x-btn-inner { + overflow: hidden; + text-overflow: ellipsis; + -ms-flex-negative: 1; + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:112 */ +.x-ie9m .x-btn-inner { + display: inline-block; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:122 */ +.x-btn-icon.x-btn-no-text > .x-btn-inner { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:127 */ +.x-btn-icon-el { + display: none; + vertical-align: middle; + text-align: center; + background-position: center center; + background-repeat: no-repeat; + flex-shrink: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:137 */ +.x-btn-icon > .x-btn-icon-el { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:142 */ +.x-ie9m .x-btn-icon-left > .x-btn-icon-el, +.x-ie9m .x-btn-icon-right > .x-btn-icon-el { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:159 */ +.x-btn-button-center { + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:161 */ +.x-ie9m .x-btn-button-center { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:169 */ +.x-btn-button-center.x-btn-icon-top, +.x-btn-button-center.x-btn-icon-bottom { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:175 */ +.x-btn-button-left { + text-align: left; + -webkit-box-pack: start; + -ms-flex-pack: start; + justify-content: flex-start; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:188 */ +.x-btn-button-right { + text-align: right; + -webkit-box-pack: end; + -ms-flex-pack: end; + justify-content: flex-end; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:202 */ +.x-btn-arrow:after, +.x-btn-split:after { + display: block; + background-repeat: no-repeat; + content: ''; + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:216 */ +.x-btn-arrow-right:after, +.x-btn-split-right:after { + background-position: right center; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: center; + -ms-flex-align: center; + align-items: center; + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:226 */ +.x-ie9m .x-btn-arrow-right:after, +.x-ie9m .x-btn-split-right:after { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:246 */ +.x-btn-arrow-bottom:after, +.x-btn-split-bottom:after { + background-position: center bottom; + content: '\00a0'; + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:259 */ +.x-ie9m .x-btn-arrow-bottom:after, +.x-ie9m .x-btn-split-bottom:after { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:269 */ +.x-btn-split-right > .x-btn-button:after { + position: absolute; + display: block; + top: -100%; + right: 0; + height: 300%; + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:286 */ +.x-btn-split-bottom > .x-btn-button:after { + position: absolute; + display: block; + bottom: 0; + left: -100%; + font-size: 0; + width: 300%; + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:297 */ +.x-btn-mc { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:1 */ +.x-segmented-button { + display: table; + table-layout: fixed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:6 */ +.x-segmented-button-item { + display: table-cell; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:10 */ +.x-segmented-button-item > .x-frame { + width: 100%; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:17 */ +.x-segmented-button-item .x-btn-mc { + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:23 */ +.x-segmented-button-item-horizontal { + display: table-cell; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:30 */ +.x-segmented-button-item-horizontal.x-segmented-button-first { + border-top-right-radius: 0; + border-bottom-right-radius: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:35 */ +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-tr, +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-mr, +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-br { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:43 */ +.x-segmented-button-item-horizontal.x-segmented-button-middle { + border-radius: 0; + border-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:48 */ +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tl, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tr, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-ml, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-mr, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-bl, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-br { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:59 */ +.x-segmented-button-item-horizontal.x-segmented-button-last { + border-left: 0; + border-top-left-radius: 0; + border-bottom-left-radius: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:65 */ +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-tl, +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-ml, +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-bl { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:74 */ +.x-segmented-button-row { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:79 */ +.x-segmented-button-item-vertical.x-segmented-button-first { + border-bottom-right-radius: 0; + border-bottom-left-radius: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:84 */ +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bl, +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bc, +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-br { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:92 */ +.x-segmented-button-item-vertical.x-segmented-button-middle { + border-radius: 0; + border-top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:97 */ +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tl, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tc, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tr, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bl, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bc, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-br { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:108 */ +.x-segmented-button-item-vertical.x-segmented-button-last { + border-top: 0; + border-top-right-radius: 0; + border-top-left-radius: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:114 */ +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tl, +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tc, +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tr { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:1 */ +.x-title-icon { + background-repeat: no-repeat; + background-position: 0 0; + vertical-align: middle; + line-height: 1; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:9 */ +.x-title { + display: table; + table-layout: fixed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:21 */ +.x-title-text { + display: table-cell; + overflow: hidden; + white-space: nowrap; + -o-text-overflow: ellipsis; + text-overflow: ellipsis; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:30 */ +.x-title-align-left { + text-align: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:39 */ +.x-title-align-center { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:43 */ +.x-title-align-right { + text-align: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:52 */ +.x-title-rotate-right { + -webkit-transform: rotate(90deg); + -webkit-transform-origin: 0 0; + -moz-transform: rotate(90deg); + -moz-transform-origin: 0 0; + -ms-transform: rotate(90deg); + -ms-transform-origin: 0 0; + transform: rotate(90deg); + transform-origin: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/rotate-element.scss:41 */ +.x-ie8 .x-title-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:62 */ +.x-title-rotate-left { + -webkit-transform: rotate(270deg); + -webkit-transform-origin: 100% 0; + -moz-transform: rotate(270deg); + -moz-transform-origin: 100% 0; + -ms-transform: rotate(270deg); + -ms-transform-origin: 100% 0; + transform: rotate(270deg); + transform-origin: 100% 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/rotate-element.scss:41 */ +.x-ie8 .x-title-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:75 */ +.x-horizontal.x-header .x-title-rotate-right.x-title-align-left > .x-title-item { + vertical-align: bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:79 */ +.x-horizontal.x-header .x-title-rotate-right.x-title-align-center > .x-title-item { + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:83 */ +.x-horizontal.x-header .x-title-rotate-right.x-title-align-right > .x-title-item { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:89 */ +.x-horizontal.x-header .x-title-rotate-left.x-title-align-left > .x-title-item { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:93 */ +.x-horizontal.x-header .x-title-rotate-left.x-title-align-center > .x-title-item { + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:97 */ +.x-horizontal.x-header .x-title-rotate-left.x-title-align-right > .x-title-item { + vertical-align: bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:105 */ +.x-vertical.x-header .x-title-rotate-none.x-title-align-left > .x-title-item { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:109 */ +.x-vertical.x-header .x-title-rotate-none.x-title-align-center > .x-title-item { + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:113 */ +.x-vertical.x-header .x-title-rotate-none.x-title-align-right > .x-title-item { + vertical-align: bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:120 */ +.x-title-icon-wrap { + display: table-cell; + text-align: center; + vertical-align: middle; + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:125 */ +.x-title-icon-wrap.x-title-icon-top, +.x-title-icon-wrap.x-title-icon-bottom { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:131 */ +.x-title-icon { + display: inline-block; + vertical-align: middle; + background-position: center; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Tool.scss:1 */ +.x-tool { + font-size: 16px; + line-height: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Header.scss:4 */ +.x-header > .x-box-inner, +.x-panel-header-mc > .x-box-inner, +.x-window-header-mc > .x-box-inner { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:1 */ +.x-splitter { + font-size: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:5 */ +.x-splitter-horizontal { + cursor: e-resize; + cursor: row-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:10 */ +.x-splitter-vertical { + cursor: e-resize; + cursor: col-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:15 */ +.x-splitter-collapsed, +.x-splitter-horizontal-noresize, +.x-splitter-vertical-noresize { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:21 */ +.x-splitter-active { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:25 */ +.x-collapse-el { + position: absolute; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:30 */ +.x-splitter-focus { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:1 */ +.x-box-layout-ct { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:5 */ +.x-box-target { + position: absolute; + width: 20000px; + top: 0; + left: 0; + min-height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:32 */ +.x-box-inner { + overflow: hidden; + position: relative; + left: 0; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:39 */ +.x-box-scroller { + position: absolute; + background-repeat: no-repeat; + background-position: center; + line-height: 0; + font-size: 0; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:48 */ +.x-box-scroller-top { + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:52 */ +.x-box-scroller-right { + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:56 */ +.x-box-scroller-bottom { + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:60 */ +.x-box-scroller-left { + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:64 */ +.x-box-menu-body-horizontal { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:68 */ +.x-box-menu-after { + position: relative; + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:75 */ +.x-box-scroller-body-vertical, +.x-box-scroller-body-horizontal { + -ms-overflow-style: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:78 */ +.x-box-scroller-body-vertical .x-scroller, +.x-box-scroller-body-horizontal .x-scroller { + -ms-overflow-style: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:81 */ +.x-box-scroller-body-vertical :not(.x-scroller)::-webkit-scrollbar, +.x-box-scroller-body-horizontal :not(.x-scroller)::-webkit-scrollbar { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Toolbar.scss:1 */ +.x-toolbar-text { + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Toolbar.scss:5 */ +.x-toolbar-separator { + display: block; + font-size: 1px; + overflow: hidden; + cursor: default; + border: 0; + width: 0; + height: 0; + line-height: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Toolbar.scss:16 */ +.x-toolbar-scroller { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Toolbar.scss:23 */ +.x-toolbar-plain { + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/DD.scss:3 */ +.x-dd-drag-proxy, +.x-dd-drag-current { + z-index: 1000000!important; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:1 */ +.x-dd-drag-proxy { + display: table; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:6 */ +.x-dd-drag-repair .x-dd-drag-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:10 */ +.x-dd-drag-repair .x-dd-drop-icon { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:15 */ +.x-dd-drag-ghost, +.x-dd-drop-icon { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:21 */ +.x-dd-drag-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=85)"; + opacity: 0.85; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:26 */ +.x-dd-drop-icon { + height: 26px; + width: 26px; + background-color: transparent; + background-position: center; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:1 */ +.x-docked { + position: absolute !important; + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:7 */ +.x-docked-vertical { + position: static; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:11 */ +.x-docked-top { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:15 */ +.x-docked-bottom { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:19 */ +.x-docked-left { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:23 */ +.x-docked-right { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:27 */ +.x-docked-noborder-top { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:31 */ +.x-docked-noborder-right { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:35 */ +.x-docked-noborder-bottom { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:39 */ +.x-docked-noborder-left { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:45 */ +.x-noborder-l { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:48 */ +.x-noborder-b { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:51 */ +.x-noborder-bl { + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:55 */ +.x-noborder-r { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:58 */ +.x-noborder-rl { + border-right-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:62 */ +.x-noborder-rb { + border-right-width: 0 !important; + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:66 */ +.x-noborder-rbl { + border-right-width: 0 !important; + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:71 */ +.x-noborder-t { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:74 */ +.x-noborder-tl { + border-top-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:78 */ +.x-noborder-tb { + border-top-width: 0 !important; + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:82 */ +.x-noborder-tbl { + border-top-width: 0 !important; + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:87 */ +.x-noborder-tr { + border-top-width: 0 !important; + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:91 */ +.x-noborder-trl { + border-top-width: 0 !important; + border-right-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:96 */ +.x-noborder-trb { + border-top-width: 0 !important; + border-right-width: 0 !important; + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:101 */ +.x-noborder-trbl { + border-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:1 */ +.x-panel, +.x-plain { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:7 */ +.x-panel { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:13 */ +td.x-frame-mc { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:18 */ +.x-panel-bodyWrap { + overflow: hidden; + position: static; + height: 100%; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:25 */ +.x-panel-body { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:30 */ +.x-panel-header-plain, +.x-panel-body-plain { + border: 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:40 */ +.x-panel-collapsed-mini { + visibility: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:50 */ +.x-viewport > .x-body.x-panel > .x-panel-bodyWrap { + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Table.scss:1 */ +.x-table-layout { + font-size: 1em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/container/ButtonGroup.scss:1 */ +.x-btn-group { + position: relative; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/container/ButtonGroup.scss:6 */ +.x-btn-group-body { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/container/ButtonGroup.scss:8 */ +.x-btn-group-body .x-table-layout-cell { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:1 */ +.x-viewport, +.x-viewport > .x-body { + margin: 0; + padding: 0; + border: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:8 */ +.x-viewport { + width: 100%; + height: 100%; + position: static; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:16 */ +.x-viewport > .x-body { + position: fixed; + top: 0; + left: 0; + min-width: 100%; + min-height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:30 */ +@media print { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:33 */ + .x-viewport > .x-body { + position: static; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Column.scss:1 */ +.x-column { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/SplitterTracker.scss:1 */ +.x-resizable-overlay { + position: absolute; + left: 0; + top: 0; + width: 100%; + height: 100%; + display: none; + z-index: 200000; + background-color: #fff; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/window/Window.scss:1 */ +.x-window { + outline: none; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/window/Window.scss:5 */ +.x-window .x-window-wrap { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/window/Window.scss:10 */ +.x-window-body { + position: relative; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:1 */ +.x-form-item { + display: table; + table-layout: fixed; + border-spacing: 0; + border-collapse: separate; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:10 */ +.x-form-item-label { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:14 */ +.x-form-item.x-form-item-no-label > .x-form-item-label { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:18 */ +.x-form-item-label, +.x-form-item-body { + display: table-cell; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:23 */ +.x-form-item-body { + vertical-align: middle; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:28 */ +.x-form-item-label-inner { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:32 */ +.x-form-item-label-top { + display: table-row; + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:35 */ +.x-form-item-label-top > .x-form-item-label-inner { + display: table-cell; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:39 */ +.x-form-item-label-top-side-error:after { + display: table-cell; + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:44 */ +.x-form-item-label-right { + text-align: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:53 */ +.x-form-error-wrap-side { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:58 */ +.x-form-error-wrap-under { + display: table-row; + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:61 */ +.x-form-error-wrap-under > .x-form-error-msg { + display: table-cell; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:66 */ +.x-form-error-wrap-under-side-label:before { + display: table-cell; + content: ''; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:72 */ +.x-form-invalid-icon { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:74 */ +.x-form-invalid-icon ul { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:1 */ +.x-form-trigger-wrap { + display: table; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:6 */ +.x-form-text-heighted .x-form-trigger-wrap { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:17 */ +.x-gecko .x-form-trigger-wrap { + display: -moz-inline-box; + display: inline-flex; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:27 */ +.x-form-type-text.x-has-min-height { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:32 */ +.x-form-type-text.x-has-min-height .x-form-text-field-body, +.x-form-type-text.x-has-min-height .x-form-trigger-wrap, +.x-form-type-text.x-has-min-height .x-form-text-wrap { + min-height: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:40 */ +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-field-body, +.x-ie8 .x-form-type-text.x-has-min-height .x-form-trigger-wrap, +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-wrap { + min-height: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:47 */ +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text { + min-height: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:52 */ +.x-form-type-text.x-has-min-height .x-form-text { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:57 */ +.x-form-text-wrap { + display: table-cell; + overflow: hidden; + height: 100%; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:65 */ +.x-gecko .x-form-text-wrap { + display: block; + -moz-box-flex: 1; + flex: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:72 */ +.x-form-text-wrap .x-placeholder-label { + position: absolute; + top: 0; + left: 0; + cursor: text; + white-space: nowrap; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:84 */ +.x-form-item-body.x-form-text-grow { + min-width: inherit; + max-width: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:89 */ +.x-form-text { + border: 0; + margin: 0; + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + display: block; + background: repeat-x 0 0; + width: 100%; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:99 */ +.x-form-trigger { + display: table-cell; + vertical-align: top; + cursor: pointer; + overflow: hidden; + background-repeat: no-repeat; + text-align: center; + line-height: 0; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:111 */ +.x-item-disabled .x-form-trigger { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:114 */ +.x-form-trigger.x-form-trigger-cmp { + background: none; + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:131 */ +.x-gecko .x-form-trigger { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/TextArea.scss:2 */ +.x-form-textarea-body.x-form-text-grow > .x-form-trigger-wrap { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/TextArea.scss:7 */ +.x-form-textarea { + overflow: auto; + resize: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/TextArea.scss:12 */ +div.x-form-text-grow .x-form-textarea { + min-height: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/window/MessageBox.scss:2 */ +.x-message-box .x-form-display-field { + height: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldContainer.scss:4 */ +.x-safari .x-form-fieldcontainer { + table-layout: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldContainer.scss:12 */ +.x-ie8 .x-form-fieldcontainer > .x-form-item-body.x-field-container-body-vertical { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:1 */ +.x-form-cb-wrap { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:5 */ +.x-form-cb-wrap-inner { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:9 */ +.x-form-cb { + position: absolute; + left: 0; + right: auto; + vertical-align: top; + overflow: hidden; + padding: 0; + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:17 */ +.x-form-cb::-moz-focus-inner { + padding: 0; + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:23 */ +.x-form-cb-input { + position: absolute; + margin: 0; + padding: 0; + border: 0; + top: 0; + left: 0; + width: 100%; + height: 100%; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:43 */ +.x-form-cb-after { + /* allow for the component to be positioned after the label */ + left: auto; + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:57 */ +.x-form-cb-label { + /* some browsers like IE 10 need a block element to be able to measure +the height of a multi-line element */ + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:60 */ +.x-form-cb-label.x-form-cb-no-box-label { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:1 */ +.x-fieldset { + display: block; + /* preserve margins in IE */ + position: relative; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:7 */ +.x-fieldset-header { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:10 */ +.x-fieldset-header .x-form-item, +.x-fieldset-header .x-tool { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:15 */ +.x-fieldset-header .x-fieldset-header-text { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:19 */ +.x-fieldset-header .x-form-cb-wrap { + font-size: 0; + line-height: 0; + min-height: 0; + height: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:26 */ +.x-fieldset-header .x-form-cb { + margin: 0; + position: static; + display: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:35 */ +.x-fieldset-body { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:39 */ +.x-fieldset-collapsed { + padding-bottom: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:42 */ +.x-fieldset-collapsed > .x-fieldset-body { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:47 */ +.x-fieldset-header-text-collapsible { + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/view/View.scss:2 */ +.x-keyboard-mode .x-view-item-focused { + outline: 1px dashed #157fcc !important; + outline-offset: -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/view/BoundList.scss:8 */ +.x-ie9 .x-boundlist-list-ct { + min-height: 0%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:1 */ +.x-datepicker { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:4 */ +.x-datepicker .x-monthpicker { + left: 0; + top: 0; + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:10 */ +.x-datepicker .x-monthpicker-months, +.x-datepicker .x-monthpicker-years { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:16 */ +.x-datepicker-inner { + table-layout: fixed; + width: 100%; + border-collapse: separate; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:22 */ +.x-datepicker-cell { + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:26 */ +.x-datepicker-header { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:30 */ +.x-datepicker-arrow { + position: absolute; + outline: none; + font-size: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:45 */ +.x-datepicker-column-header { + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:49 */ +.x-datepicker-date { + display: block; + text-decoration: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:54 */ +.x-monthpicker { + display: table; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:57 */ +.x-monthpicker-body { + height: 100%; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:62 */ +.x-monthpicker-months, +.x-monthpicker-years { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:67 */ +.x-monthpicker-item { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:71 */ +.x-monthpicker-item-inner { + display: block; + text-decoration: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:76 */ +.x-monthpicker-yearnav-button-ct { + float: left; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:81 */ +.x-monthpicker-yearnav-button { + display: inline-block; + outline: none; + font-size: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:87 */ +.x-monthpicker-buttons { + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:91 */ +.x-datepicker .x-monthpicker-buttons { + position: absolute; + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:96 */ +.x-datepicker-month .x-btn-split > .x-btn-button:after { + content: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Display.scss:1 */ +.x-form-display-field-body { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Display.scss:3 */ +.x-form-display-field-body .x-form-display-field { + overflow-wrap: break-word; + word-wrap: break-word; + -ms-word-break: break-all; + /* This is dangerous in WebKit as it breaks things at random points */ + word-break: break-all; + /* Use this non-standard instead */ + word-break: break-word; + /* Adds a hyphen where the word breaks, if supported (No Blink) */ + -ms-hyphens: auto; + -moz-hyphens: auto; + -webkit-hyphens: auto; + hyphens: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/File.scss:1 */ +.x-form-file-btn { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/File.scss:6 */ +.x-form-file-input { + border: 0; + position: absolute; + cursor: pointer; + top: 0; + right: 0; + width: 100%; + height: 100%; + overflow: hidden; + text-indent: -10000px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; + /* Yes, there's actually a good reason for this... + * If the configured buttonText is set to something longer than the default, + * then it will quickly exceed the width of the hidden file input's "Browse..." + * button, so part of the custom button's clickable area will be covered by + * the hidden file input's text box instead. This results in a text-selection + * mouse cursor over that part of the button, at least in Firefox, which is + * confusing to a user. Giving the hidden file input a huge font-size makes + * the native button part very large so it will cover the whole clickable area. + */ + font-size: 1000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Hidden.scss:1 */ +.x-form-item-hidden { + margin: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tip/Tip.scss:1 */ +.x-tip { + position: absolute; + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tip/Tip.scss:6 */ +.x-tip-body { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tip/Tip.scss:11 */ +.x-tip-anchor { + position: absolute; + border-style: solid; + height: 0; + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Color.scss:1 */ +.x-color-picker-item { + float: left; + text-decoration: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Color.scss:6 */ +.x-color-picker-item-inner { + display: block; + font-size: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/HtmlEditor.scss:1 */ +.x-html-editor-tb .x-toolbar { + position: static !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/HtmlEditor.scss:5 */ +.x-htmleditor-iframe, +.x-htmleditor-textarea { + display: block; + overflow: auto; + width: 100%; + height: 100%; + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:1 */ +.x-tagfield-body { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:5 */ +.x-tagfield { + height: auto!important; + /* The wrap has to accommodate the list, so override the .x-form-text height rule */ + cursor: text; + overflow-y: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:11 */ +.x-tagfield .x-tagfield-list { + padding: 0; + margin: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:16 */ +.x-tagfield-list.x-tagfield-singleselect { + white-space: nowrap; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:21 */ +.x-tagfield-input, +.x-tagfield-item { + vertical-align: top; + display: inline-block; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:27 */ +.x-tagfield-input-field { + font: inherit; + border: 0; + margin: 0; + background: none; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:35 */ +.x-tagfield-stacked .x-tagfield-item { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:39 */ +.x-tagfield-item { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:43 */ +.x-tagfield-item-close { + cursor: pointer; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:48 */ +.x-tagfield-arialist { + list-style-type: none; + position: absolute; + clip: rect(0, 0, 0, 0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:54 */ +.x-tagfield-arialist-item { + list-style-type: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Fit.scss:1 */ +.x-fit-item { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:1 */ +.x-grid-view { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:11 */ +.x-grid-row-table { + /* A grid *item* is a dataview item. It is encapsulated by a . + * One item always corresponds to one store record + * But an item may contain more than one . + * ONE child row, will be the grid-row and will contain record data + */ + width: 0; + table-layout: fixed; + border: 0 none; + border-collapse: separate; + border-spacing: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:25 */ +.x-grid-item { + table-layout: fixed; + outline: none; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:34 */ +.x-ie10 .x-grid-item { + transform: translateZ(0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:39 */ +.x-grid-row { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:43 */ +.x-grid-td { + overflow: hidden; + border-width: 0; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:49 */ +.x-grid-cell-inner { + overflow: hidden; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:55 */ +.x-wrap-cell .x-grid-cell-inner { + white-space: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:60 */ +.x-grid-resize-marker { + position: absolute; + z-index: 5; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/view/Table.scss:3 */ +.x-grid-item-container { + min-height: 1px; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/header/DropZone.scss:1 */ +.x-col-move-top, +.x-col-move-bottom { + position: absolute; + top: 0; + line-height: 0; + font-size: 0; + overflow: hidden; + z-index: 20000; + background: no-repeat center top transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/header/Container.scss:1 */ +.x-grid-header-ct { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:1 */ +.x-column-header { + position: absolute; + overflow: hidden; + background-repeat: repeat-x; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:11 */ +.x-column-header-inner { + /* + * TODO: + * When IE8 retires, revisit https://jsbin.com/honawo/quiet for better way to center header text + */ + white-space: nowrap; + position: relative; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:17 */ +.x-leaf-column-header { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:19 */ +.x-leaf-column-header .x-column-header-text-container { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:26 */ +.x-column-header-text-container { + width: 100%; + display: table; + table-layout: fixed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:31 */ +.x-column-header-text-container.x-column-header-text-container-auto { + table-layout: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:36 */ +.x-column-header-text-wrapper { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:41 */ +.x-column-header-text { + display: block; + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:50 */ +.x-column-header-sort-DESC .x-column-header-text, +.x-column-header-sort-ASC .x-column-header-text { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:57 */ +.x-column-header-text-inner { + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:60 */ +.x-column-header-inner-empty .x-column-header-text-inner { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:63 */ +.x-column-header-inner-empty .x-column-header-text-container { + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:76 */ +.x-column-header-trigger { + display: none; + height: 100%; + background-repeat: no-repeat; + position: absolute; + right: 0; + top: 0; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:86 */ +.x-ie9m .x-column-header-trigger { + z-index: 6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:101 */ +.x-column-header-over .x-column-header-trigger, +.x-column-header-open .x-column-header-trigger { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:106 */ +.x-column-header-align-right { + text-align: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:116 */ +.x-column-header-align-left { + text-align: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:126 */ +.x-column-header-align-center { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Action.scss:1 */ +.x-grid-cell-inner-action-col { + line-height: 0; + font-size: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Action.scss:6 */ +.x-keyboard-mode .x-grid-cell-inner-action-col :focus { + outline: 1px solid #3d92cf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Action.scss:12 */ +.x-action-col-icon { + display: inline-block; + line-height: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Check.scss:4 */ +.x-column-header-checkbox .x-column-header-text { + margin-bottom: 0.4em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Check.scss:9 */ +.x-column-header-checkbox .x-column-header-inner-empty .x-column-header-text { + margin-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Check.scss:15 */ +.x-grid-checkcolumn-cell-inner { + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Check.scss:19 */ +.x-keyboard-mode .x-grid-checkcolumn-cell-inner :focus { + outline: 1px solid #3d92cf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/Grouping.scss:1 */ +.x-group-hd-container { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/Grouping.scss:5 */ +.x-grid-group-hd { + white-space: nowrap; + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/Grouping.scss:10 */ +.x-grid-group-title { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/Grouping.scss:29 */ +.x-grid-row-body-hidden, +.x-grid-group-collapsed { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/RowBody.scss:1 */ +.x-grid-row-body-hidden { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:1 */ +.x-menu { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:5 */ +.x-menu-body { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:9 */ +.x-menu-item { + white-space: nowrap; + overflow: hidden; + border-color: transparent; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:17 */ +.x-menu-item-cmp { + margin: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:20 */ +.x-menu-item-cmp .x-field-label-cell { + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:28 */ +.x-menu-icon-separator { + position: absolute; + top: 0px; + z-index: 0; + height: 100%; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:34 */ +.x-menu-plain .x-menu-icon-separator { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:39 */ +.x-menu-item-link { + -webkit-tap-highlight-color: transparent; + -webkit-touch-callout: none; + text-decoration: none; + outline: 0; + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:54 */ +.x-menu-item-link-href { + -webkit-touch-callout: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:58 */ +.x-menu-item-text { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:62 */ +.x-menu-item-icon, +.x-menu-item-icon-right, +.x-menu-item-arrow { + font-size: 0; + position: absolute; + text-align: center; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:1 */ +.x-grid-scroll-container { + position: absolute; + z-index: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:7 */ +.x-grid-scrollbar-clipper-floated, +.x-grid-scrollbar-floated { + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:12 */ +.x-grid-scroll-body { + width: 100%; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:17 */ +.x-grid-scrollbar-clipper { + overflow: hidden; + position: absolute; + top: 0; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:23 */ +.x-grid-scrollbar-clipper > .x-grid-view, +.x-grid-scrollbar-clipper > .x-tree-view { + overflow-y: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:29 */ +.x-grid-with-col-lines .x-grid-scrollbar-clipper-locked .x-grid-cell-last { + border-right-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:43 */ +.x-grid-scrollbar { + position: absolute; + bottom: 0; + left: 0; + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:56 */ +.x-grid-scrollbar-visible { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:61 */ +.x-grid-locking-body > .x-grid { + z-index: 2; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:65 */ +.x-grid-locking-body > .x-grid .x-docked { + pointer-events: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:70 */ +.x-grid-locking-body .x-grid-body { + background: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:74 */ +.x-grid-locking-body > .x-splitter { + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:80 */ +.x-grid-locking-body > .x-splitter-active { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:84 */ +.x-grid-locking-body > .x-splitter-focus { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:90 */ +.x-grid-inner-locked.x-border-region-slide-in { + z-index: 3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:92 */ +.x-grid-inner-locked.x-border-region-slide-in > .x-panel-bodyWrap > .x-grid-body > .x-grid-view, +.x-grid-inner-locked.x-border-region-slide-in > .x-panel-bodyWrap > .x-grid-body > .x-tree-view { + overflow-y: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/Editing.scss:7 */ +.x-grid-editor .x-form-cb-wrap { + /* + * Rules for fields which are rendered to fit inside grid cells. + * This includes cell and row editor fields and fields in widget columns. + */ + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/Editing.scss:12 */ +.x-grid-editor .x-form-cb { + position: static; + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/Editing.scss:20 */ +.x-grid-editor .x-form-display-field { + margin: 0; + white-space: nowrap; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/Editing.scss:28 */ +.x-grid-editor div.x-form-action-col-field { + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowEditing.scss:1 */ +.x-grid-row-editor-wrap { + position: absolute; + overflow: visible; + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowEditing.scss:8 */ +.x-grid-row-editor { + position: absolute; + z-index: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowEditing.scss:15 */ +.x-grid-row-editor-buttons { + position: absolute; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowExpander.scss:1 */ +.x-grid-row-expander { + font-size: 0; + line-height: 0; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowExpander.scss:8 */ +.x-keyboard-mode .x-grid-row-expander:focus { + outline: 1px solid #3d92cf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowExpander.scss:13 */ +.x-grid-hide-row-expander-spacer .x-grid-row-expander-spacer { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowExpander.scss:17 */ +.x-grid-row-expander-spacer { + border: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:1 */ +.x-ssm-row-numberer-hd { + cursor: se-resize!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:6 */ +.x-ssm-row-numberer-cell { + cursor: e-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:11 */ +.x-ssm-column-select .x-column-header { + cursor: s-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:16 */ +.x-ssm-extender-drag-handle { + position: absolute; + z-index: 1; + cursor: crosshair; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:22 */ +.x-ssm-extender-mask { + position: absolute; + z-index: 1; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Absolute.scss:1 */ +.x-abs-layout-ct { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Absolute.scss:5 */ +.x-abs-layout-item { + position: absolute !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Border.scss:1 */ +.x-border-layout-ct { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Border.scss:5 */ +.x-border-layout-ct { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Border.scss:9 */ +.x-border-region-slide-in { + z-index: 6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Border.scss:13 */ +.x-region-collapsed-placeholder { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Center.scss:1 */ +.x-center-layout-item { + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Center.scss:5 */ +.x-center-target { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:1 */ +.x-form-layout-wrap { + display: table; + width: 100%; + border-collapse: separate; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:7 */ +.x-form-layout-colgroup { + display: table-column-group; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:11 */ +.x-form-layout-column { + display: table-column; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:16 */ +.x-form-layout-auto-label > * > .x-form-item-label { + width: auto !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:20 */ +.x-form-layout-auto-label > * > .x-form-item-label > .x-form-item-label-inner { + width: auto !important; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:26 */ +.x-form-layout-auto-label > * > .x-form-layout-label-column { + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:33 */ +.x-form-layout-sized-label > * > .x-form-item-label { + width: auto !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:40 */ +.x-form-form-item { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:43 */ +.x-form-form-item > .x-form-item-label { + padding-left: 0 !important; + padding-right: 0 !important; + padding-bottom: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:51 */ +.x-form-form-item > .x-form-item-body { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:60 */ +.x-form-form-item.x-form-item-no-label:before { + content: ' '; + display: table-cell; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Resizer.scss:2 */ +.x-resizable-wrapped { + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:1 */ +.x-slider { + outline: none; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:6 */ +.x-slider-inner { + position: relative; + left: 0; + top: 0; + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:11 */ +.x-slider-vert .x-slider-inner { + background: repeat-y 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:16 */ +.x-slider-thumb { + position: absolute; + background: no-repeat 0 0; + cursor: default; + -webkit-user-callout: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:19 */ +.x-slider-horz .x-slider-thumb { + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:22 */ +.x-slider-vert .x-slider-thumb { + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:21 */ +.x-tab { + display: block; + outline: 0; + cursor: pointer; + white-space: nowrap; + text-decoration: none; + vertical-align: top; + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:33 */ +.x-tab > .x-frame { + height: 100%; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:39 */ +.x-tab-wrap { + height: 100%; + width: 100%; + display: table; + border-spacing: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:64 */ +.x-tab-button { + white-space: nowrap; + line-height: 0; + position: relative; + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:103 */ +.x-tab-inner { + overflow: hidden; + text-overflow: ellipsis; + display: inline-block; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:122 */ +.x-tab-icon.x-tab-no-text > .x-tab-inner { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:127 */ +.x-tab-icon-el { + display: none; + vertical-align: middle; + text-align: center; + background-position: center center; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:148 */ +.x-tab-icon > .x-tab-icon-el { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:152 */ +.x-tab-icon-top > .x-tab-icon-el, +.x-tab-icon-bottom > .x-tab-icon-el { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:161 */ +.x-ie9m .x-tab-button-center { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:169 */ +.x-tab-button-center.x-tab-icon-top, +.x-tab-button-center.x-tab-icon-bottom { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:175 */ +.x-tab-button-left { + text-align: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:188 */ +.x-tab-button-right { + text-align: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:297 */ +.x-tab-mc { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:13 */ +.x-tab { + z-index: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:17 */ +.x-tab-active { + z-index: 3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:21 */ +.x-tab-button { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:27 */ +.x-tab-close-btn { + display: block; + position: absolute; + overflow: hidden; + font-size: 0; + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:35 */ +.x-tab-rotate-left { + -webkit-transform: rotate(270deg); + -webkit-transform-origin: 100% 0; + -moz-transform: rotate(270deg); + -moz-transform-origin: 100% 0; + -ms-transform: rotate(270deg); + -ms-transform-origin: 100% 0; + transform: rotate(270deg); + transform-origin: 100% 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/rotate-element.scss:41 */ +.x-ie8 .x-tab-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:45 */ +.x-tab-rotate-right { + -webkit-transform: rotate(90deg); + -webkit-transform-origin: 0 0; + -moz-transform: rotate(90deg); + -moz-transform-origin: 0 0; + -ms-transform: rotate(90deg); + -ms-transform-origin: 0 0; + transform: rotate(90deg); + transform-origin: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/rotate-element.scss:41 */ +.x-ie8 .x-tab-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:57 */ +.x-tab-tr, +.x-tab-br, +.x-tab-mr, +.x-tab-tl, +.x-tab-bl, +.x-tab-ml { + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:1 */ +.x-tab-bar { + z-index: 0; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:6 */ +.x-tab-bar-strip { + position: absolute; + line-height: 0; + font-size: 0; + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:12 */ +.x-tab-bar-top > .x-tab-bar-strip { + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:16 */ +.x-tab-bar-bottom > .x-tab-bar-strip { + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:20 */ +.x-tab-bar-left > .x-tab-bar-strip { + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:31 */ +.x-tab-bar-right > .x-tab-bar-strip { + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:43 */ +.x-tab-bar-horizontal .x-tab-bar-strip { + width: 100%; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:48 */ +.x-tab-bar-vertical { + display: table-cell; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:54 */ +.x-tab-bar-vertical .x-tab-bar-strip { + height: 100%; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:60 */ +.x-tab-bar-plain { + background: transparent !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:64 */ +.x-box-scroller-plain { + background-color: transparent !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Breadcrumb.scss:1 */ +.x-breadcrumb-btn .x-box-target:first-child { + margin: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Breadcrumb.scss:7 */ +.x-breadcrumb-btn > .x-btn-split-right > .x-btn-button:after { + content: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Breadcrumb.scss:12 */ +.x-breadcrumb-btn.x-btn-over > .x-btn-split-right > .x-btn-button:after, +.x-breadcrumb-btn.x-btn-menu-active > .x-btn-split-right > .x-btn-button:after { + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:4 */ +.x-autowidth-table .x-grid-item-container { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:8 */ +.x-autowidth-table .x-grid-item { + table-layout: auto; + width: auto !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:14 */ +.x-tree-view { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:18 */ +.x-tree-elbow-img, +.x-tree-icon { + display: inline-block; + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:27 */ +.x-tree-checkbox { + display: inline-block; + vertical-align: top; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:33 */ +.x-tree-animator-wrap { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/Component.scss:1 */ +.x-body { + color: #000; + font-size: 13px; + line-height: 17px; + font-family: tahoma, verdana, sans-serif; + background: #f5f5f5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/Component.scss:18 */ +.x-animating-size, +.x-collapsed { + overflow: hidden!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/Component.scss:25 */ +.x-animating-size { + z-index: 10000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/Editor.scss:2 */ +.x-editor .x-form-item-body { + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:1 */ +.x-mask { + background-image: none; + background-color: rgba(255, 255, 255, 0.7); + cursor: default; + border-style: solid; + border-width: 1px; + border-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/background-opacity.scss:19 */ +.x-ie8 .x-mask { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#b3ffffff, endColorstr=#b3ffffff)"; + zoom: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:23 */ +.x-keyboard-mode .x-mask.x-focus { + border-style: solid; + border-width: 1px; + border-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:31 */ +.x-mask-msg { + padding: 8px; + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + background: #e5e5e5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:49 */ +.x-mask-msg-inner { + padding: 0; + background-color: transparent; + color: #666; + font: normal 13px tahoma, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:61 */ +.x-mask-msg-text { + padding: 21px 0 0; + background-image: url(images/loadmask/loading.gif); + background-repeat: no-repeat; + background-position: center 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:219 */ +.x-progress-default { + background-color: #f5f5f5; + border-width: 0; + height: 20px; + border-color: #157fcc; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:234 */ +.x-progress-default .x-progress-bar-default { + background-image: none; + background-color: #c2ddf2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:249 */ +.x-progress-default .x-progress-text { + color: #666; + font-weight: bold; + font-size: 13px; + font-family: tahoma, verdana, sans-serif; + text-align: center; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:258 */ +.x-progress-default .x-progress-text-back { + color: #666; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-keyboard-mode .x-progress-default.x-progress-focus:after { + position: absolute; + content: ' '; + top: 0; + right: 0; + bottom: 0; + left: 0; + border: 0 solid #157fcc; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:285 */ +.x-progressbar-default-cell > .x-grid-cell-inner, +.x-progress-default-cell > .x-grid-cell-inner, +.x-progressbarwidget-default-cell > .x-grid-cell-inner { + padding-top: 2px; + padding-bottom: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:288 */ +.x-progressbar-default-cell > .x-grid-cell-inner .x-progress-default, +.x-progress-default-cell > .x-grid-cell-inner .x-progress-default, +.x-progressbarwidget-default-cell > .x-grid-cell-inner .x-progress-default { + height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-small { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-small-mc { + background-image: url(images/btn/btn-default-small-fbg.gif); + background-position: 0 top; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-small-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-small-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-small-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-small-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-small-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-small-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-small-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-small-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-small-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-small-tr, +.x-btn-default-small-br, +.x-btn-default-small-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-small-tl, +.x-btn-default-small-bl, +.x-btn-default-small-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-small-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-small-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-small-tl, +.x-btn-default-small-bl, +.x-btn-default-small-tr, +.x-btn-default-small-br, +.x-btn-default-small-tc, +.x-btn-default-small-bc, +.x-btn-default-small-ml, +.x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-small-ml, +.x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-small-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-small { + border-color: #126daf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-small { + min-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-small { + min-height: auto; + height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-small { + font: bold 12px/16px tahoma, verdana, sans-serif; + color: #fff; + padding: 0 5px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-small { + max-width: calc(100% - 16px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-small { + max-width: calc(100% - 15px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-small { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-small { + font-size: 16px; + height: 16px; + color: #fff; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-small, +.x-btn-icon-right > .x-btn-icon-el-default-small { + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-small, +.x-btn-icon-bottom > .x-btn-icon-el-default-small { + min-width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-default-small.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-small.x-btn-glyph { + color: #9cc9e9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-small { + margin-right: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small { + margin-left: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-small { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-small { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-small, +.x-btn-split-bottom > .x-btn-button-default-small { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-small.x-btn-arrow-right:after { + width: 16px; + background-image: url(images/button/default-small-arrow.png); + padding-right: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-small.x-btn-arrow-bottom:after { + height: 13px; + background-image: url(images/button/default-small-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-small.x-btn-split-right:after { + width: 20px; + background-image: url(images/button/default-small-s-arrow.png); + padding-right: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-small.x-btn-split-bottom:after { + height: 15px; + background-image: url(images/button/default-small-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-small { + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + -webkit-box-shadow: #d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset; + -moz-box-shadow: #d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset; + box-shadow: #d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 23px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #d7e9f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-small { + border-color: #1164a1; + background-image: none; + background-color: #3487c3; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4893c9), color-stop(50%, #3487c3), color-stop(51%, #3180b9), color-stop(0%, #3487c3)); + background-image: -webkit-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -moz-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -o-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -ms-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-small { + -webkit-box-shadow: #d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset; + -moz-box-shadow: #d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset; + box-shadow: #d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-small, +.x-btn.x-btn-pressed.x-btn-default-small { + border-color: #0e5284; + background-image: none; + background-color: #2a6e9f; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #2a6e9f), color-stop(50%, #286897), color-stop(51%, #2a6e9f), color-stop(0%, #3f7ca8)); + background-image: -webkit-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -moz-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -o-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -ms-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-small { + -webkit-box-shadow: #d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset; + -moz-box-shadow: #d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset; + box-shadow: #d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-small { + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-small-mc { + background-color: #3892d4; + background-image: url(images/btn/btn-default-small-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-small-tl, +.x-btn-over .x-btn-default-small-bl, +.x-btn-over .x-btn-default-small-tr, +.x-btn-over .x-btn-default-small-br, +.x-btn-over .x-btn-default-small-tc, +.x-btn-over .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-small-ml, +.x-btn-over .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-small-mc { + background-color: #3487c3; + background-image: url(images/btn/btn-default-small-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mc { + background-color: #3487c3; + background-image: url(images/btn/btn-default-small-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-small-tl, +.x-btn.x-btn-menu-active .x-btn-default-small-bl, +.x-btn.x-btn-menu-active .x-btn-default-small-tr, +.x-btn.x-btn-menu-active .x-btn-default-small-br, +.x-btn.x-btn-menu-active .x-btn-default-small-tc, +.x-btn.x-btn-menu-active .x-btn-default-small-bc, +.x-btn.x-btn-pressed .x-btn-default-small-tl, +.x-btn.x-btn-pressed .x-btn-default-small-bl, +.x-btn.x-btn-pressed .x-btn-default-small-tr, +.x-btn.x-btn-pressed .x-btn-default-small-br, +.x-btn.x-btn-pressed .x-btn-default-small-tc, +.x-btn.x-btn-pressed .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-small-ml, +.x-btn.x-btn-menu-active .x-btn-default-small-mr, +.x-btn.x-btn-pressed .x-btn-default-small-ml, +.x-btn.x-btn-pressed .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-small-mc, +.x-btn.x-btn-pressed .x-btn-default-small-mc { + background-color: #2a6e9f; + background-image: url(images/btn/btn-default-small-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mc { + background-color: #2a6e9f; + background-image: url(images/btn/btn-default-small-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-small-tl, +.x-btn.x-btn-disabled .x-btn-default-small-bl, +.x-btn.x-btn-disabled .x-btn-default-small-tr, +.x-btn.x-btn-disabled .x-btn-default-small-br, +.x-btn.x-btn-disabled .x-btn-default-small-tc, +.x-btn.x-btn-disabled .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-small-ml, +.x-btn.x-btn-disabled .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-small-mc { + background-color: #3892d4; + background-image: url(images/btn/btn-default-small-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-small { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first .x-btn-default-small-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle .x-btn-default-small-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last .x-btn-default-small-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first .x-btn-default-small-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle .x-btn-default-small-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last .x-btn-default-small-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-small:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-small:after { + border-width: 1px; + border-color: #d7e9f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-small:after { + border-width: 1px; + border-color: #d6e7f3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-small:after { + border-width: 1px; + border-color: #d4e2ec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-small-cell > .x-grid-cell-inner >.x-btn-default-small { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-medium { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-medium-mc { + background-image: url(images/btn/btn-default-medium-fbg.gif); + background-position: 0 top; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-medium-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-medium-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-medium-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-medium-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-medium-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-medium-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-medium-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-medium-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-medium-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-medium-tr, +.x-btn-default-medium-br, +.x-btn-default-medium-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-medium-tl, +.x-btn-default-medium-bl, +.x-btn-default-medium-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-medium-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-medium-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-medium-tl, +.x-btn-default-medium-bl, +.x-btn-default-medium-tr, +.x-btn-default-medium-br, +.x-btn-default-medium-tc, +.x-btn-default-medium-bc, +.x-btn-default-medium-ml, +.x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-medium-ml, +.x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-medium-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-medium { + border-color: #126daf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-medium { + min-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-medium { + min-height: auto; + height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-medium { + font: bold 14px/18px tahoma, verdana, sans-serif; + color: #fff; + padding: 0 8px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-medium { + max-width: calc(100% - 24px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-medium { + max-width: calc(100% - 23px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-medium { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-medium { + font-size: 24px; + height: 24px; + color: #fff; + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-medium, +.x-btn-icon-right > .x-btn-icon-el-default-medium { + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-medium, +.x-btn-icon-bottom > .x-btn-icon-el-default-medium { + min-width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-default-medium.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-medium.x-btn-glyph { + color: #9cc9e9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-medium { + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-medium { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-medium { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-medium, +.x-btn-split-bottom > .x-btn-button-default-medium { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-medium.x-btn-arrow-right:after { + width: 24px; + background-image: url(images/button/default-medium-arrow.png); + padding-right: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-medium.x-btn-arrow-bottom:after { + height: 18px; + background-image: url(images/button/default-medium-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-medium.x-btn-split-right:after { + width: 28px; + background-image: url(images/button/default-medium-s-arrow.png); + padding-right: 28px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-medium.x-btn-split-bottom:after { + height: 24px; + background-image: url(images/button/default-medium-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-medium { + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + -webkit-box-shadow: #d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset; + -moz-box-shadow: #d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset; + box-shadow: #d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 31px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #d7e9f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-medium { + border-color: #1164a1; + background-image: none; + background-color: #3487c3; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4893c9), color-stop(50%, #3487c3), color-stop(51%, #3180b9), color-stop(0%, #3487c3)); + background-image: -webkit-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -moz-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -o-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -ms-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-medium { + -webkit-box-shadow: #d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset; + -moz-box-shadow: #d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset; + box-shadow: #d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-medium, +.x-btn.x-btn-pressed.x-btn-default-medium { + border-color: #0e5284; + background-image: none; + background-color: #2a6e9f; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #2a6e9f), color-stop(50%, #286897), color-stop(51%, #2a6e9f), color-stop(0%, #3f7ca8)); + background-image: -webkit-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -moz-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -o-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -ms-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-medium { + -webkit-box-shadow: #d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset; + -moz-box-shadow: #d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset; + box-shadow: #d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-medium { + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mc { + background-color: #3892d4; + background-image: url(images/btn/btn-default-medium-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-medium-tl, +.x-btn-over .x-btn-default-medium-bl, +.x-btn-over .x-btn-default-medium-tr, +.x-btn-over .x-btn-default-medium-br, +.x-btn-over .x-btn-default-medium-tc, +.x-btn-over .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-medium-ml, +.x-btn-over .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-medium-mc { + background-color: #3487c3; + background-image: url(images/btn/btn-default-medium-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mc { + background-color: #3487c3; + background-image: url(images/btn/btn-default-medium-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-medium-tl, +.x-btn.x-btn-menu-active .x-btn-default-medium-bl, +.x-btn.x-btn-menu-active .x-btn-default-medium-tr, +.x-btn.x-btn-menu-active .x-btn-default-medium-br, +.x-btn.x-btn-menu-active .x-btn-default-medium-tc, +.x-btn.x-btn-menu-active .x-btn-default-medium-bc, +.x-btn.x-btn-pressed .x-btn-default-medium-tl, +.x-btn.x-btn-pressed .x-btn-default-medium-bl, +.x-btn.x-btn-pressed .x-btn-default-medium-tr, +.x-btn.x-btn-pressed .x-btn-default-medium-br, +.x-btn.x-btn-pressed .x-btn-default-medium-tc, +.x-btn.x-btn-pressed .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-medium-ml, +.x-btn.x-btn-menu-active .x-btn-default-medium-mr, +.x-btn.x-btn-pressed .x-btn-default-medium-ml, +.x-btn.x-btn-pressed .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-medium-mc, +.x-btn.x-btn-pressed .x-btn-default-medium-mc { + background-color: #2a6e9f; + background-image: url(images/btn/btn-default-medium-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mc { + background-color: #2a6e9f; + background-image: url(images/btn/btn-default-medium-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-medium-tl, +.x-btn.x-btn-disabled .x-btn-default-medium-bl, +.x-btn.x-btn-disabled .x-btn-default-medium-tr, +.x-btn.x-btn-disabled .x-btn-default-medium-br, +.x-btn.x-btn-disabled .x-btn-default-medium-tc, +.x-btn.x-btn-disabled .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-medium-ml, +.x-btn.x-btn-disabled .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-medium-mc { + background-color: #3892d4; + background-image: url(images/btn/btn-default-medium-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-medium { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-medium { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first .x-btn-default-medium-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle .x-btn-default-medium-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last .x-btn-default-medium-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first .x-btn-default-medium-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle .x-btn-default-medium-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last .x-btn-default-medium-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-medium:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-medium:after { + border-width: 1px; + border-color: #d7e9f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-medium:after { + border-width: 1px; + border-color: #d6e7f3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-medium:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-medium:after { + border-width: 1px; + border-color: #d4e2ec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-medium-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-medium-cell > .x-grid-cell-inner >.x-btn-default-medium { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-large { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-large-mc { + background-image: url(images/btn/btn-default-large-fbg.gif); + background-position: 0 top; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-large-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-large-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-large-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-large-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-large-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-large-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-large-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-large-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-large-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-large-tr, +.x-btn-default-large-br, +.x-btn-default-large-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-large-tl, +.x-btn-default-large-bl, +.x-btn-default-large-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-large-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-large-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-large-tl, +.x-btn-default-large-bl, +.x-btn-default-large-tr, +.x-btn-default-large-br, +.x-btn-default-large-tc, +.x-btn-default-large-bc, +.x-btn-default-large-ml, +.x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-large-ml, +.x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-large-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-large { + border-color: #126daf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-large { + min-height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-large { + min-height: auto; + height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-large { + font: bold 16px/20px tahoma, verdana, sans-serif; + color: #fff; + padding: 0 10px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-large { + max-width: calc(100% - 32px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-large { + max-width: calc(100% - 31px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-large { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-large { + font-size: 32px; + height: 32px; + color: #fff; + line-height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-large, +.x-btn-icon-right > .x-btn-icon-el-default-large { + width: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-large, +.x-btn-icon-bottom > .x-btn-icon-el-default-large { + min-width: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-default-large.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-large.x-btn-glyph { + color: #9cc9e9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-large { + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-large { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-large { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-large, +.x-btn-split-bottom > .x-btn-button-default-large { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-large.x-btn-arrow-right:after { + width: 28px; + background-image: url(images/button/default-large-arrow.png); + padding-right: 28px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-large.x-btn-arrow-bottom:after { + height: 20px; + background-image: url(images/button/default-large-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-large.x-btn-split-right:after { + width: 35px; + background-image: url(images/button/default-large-s-arrow.png); + padding-right: 35px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-large.x-btn-split-bottom:after { + height: 29px; + background-image: url(images/button/default-large-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-large { + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + -webkit-box-shadow: #d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset; + -moz-box-shadow: #d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset; + box-shadow: #d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 38px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #d7e9f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-large { + border-color: #1164a1; + background-image: none; + background-color: #3487c3; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4893c9), color-stop(50%, #3487c3), color-stop(51%, #3180b9), color-stop(0%, #3487c3)); + background-image: -webkit-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -moz-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -o-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -ms-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-large { + -webkit-box-shadow: #d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset; + -moz-box-shadow: #d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset; + box-shadow: #d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-large, +.x-btn.x-btn-pressed.x-btn-default-large { + border-color: #0e5284; + background-image: none; + background-color: #2a6e9f; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #2a6e9f), color-stop(50%, #286897), color-stop(51%, #2a6e9f), color-stop(0%, #3f7ca8)); + background-image: -webkit-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -moz-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -o-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -ms-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-large { + -webkit-box-shadow: #d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset; + -moz-box-shadow: #d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset; + box-shadow: #d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-large { + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-large-mc { + background-color: #3892d4; + background-image: url(images/btn/btn-default-large-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-large-tl, +.x-btn-over .x-btn-default-large-bl, +.x-btn-over .x-btn-default-large-tr, +.x-btn-over .x-btn-default-large-br, +.x-btn-over .x-btn-default-large-tc, +.x-btn-over .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-large-ml, +.x-btn-over .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-large-mc { + background-color: #3487c3; + background-image: url(images/btn/btn-default-large-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mc { + background-color: #3487c3; + background-image: url(images/btn/btn-default-large-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-large-tl, +.x-btn.x-btn-menu-active .x-btn-default-large-bl, +.x-btn.x-btn-menu-active .x-btn-default-large-tr, +.x-btn.x-btn-menu-active .x-btn-default-large-br, +.x-btn.x-btn-menu-active .x-btn-default-large-tc, +.x-btn.x-btn-menu-active .x-btn-default-large-bc, +.x-btn.x-btn-pressed .x-btn-default-large-tl, +.x-btn.x-btn-pressed .x-btn-default-large-bl, +.x-btn.x-btn-pressed .x-btn-default-large-tr, +.x-btn.x-btn-pressed .x-btn-default-large-br, +.x-btn.x-btn-pressed .x-btn-default-large-tc, +.x-btn.x-btn-pressed .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-large-ml, +.x-btn.x-btn-menu-active .x-btn-default-large-mr, +.x-btn.x-btn-pressed .x-btn-default-large-ml, +.x-btn.x-btn-pressed .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-large-mc, +.x-btn.x-btn-pressed .x-btn-default-large-mc { + background-color: #2a6e9f; + background-image: url(images/btn/btn-default-large-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mc { + background-color: #2a6e9f; + background-image: url(images/btn/btn-default-large-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-large-tl, +.x-btn.x-btn-disabled .x-btn-default-large-bl, +.x-btn.x-btn-disabled .x-btn-default-large-tr, +.x-btn.x-btn-disabled .x-btn-default-large-br, +.x-btn.x-btn-disabled .x-btn-default-large-tc, +.x-btn.x-btn-disabled .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-large-ml, +.x-btn.x-btn-disabled .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-large-mc { + background-color: #3892d4; + background-image: url(images/btn/btn-default-large-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-large { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first .x-btn-default-large-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle .x-btn-default-large-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last .x-btn-default-large-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first .x-btn-default-large-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle .x-btn-default-large-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last .x-btn-default-large-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-large:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-large:after { + border-width: 1px; + border-color: #d7e9f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-large:after { + border-width: 1px; + border-color: #d6e7f3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-large:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-large:after { + border-width: 1px; + border-color: #d4e2ec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-large-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-large-cell > .x-grid-cell-inner >.x-btn-default-large { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-toolbar-small { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: #f5f5f5; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5)); + background-image: -webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-toolbar-small-mc { + background-image: url(images/btn/btn-default-toolbar-small-fbg.gif); + background-position: 0 top; + background-color: #f5f5f5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-toolbar-small-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-toolbar-small-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-toolbar-small-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-toolbar-small-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-toolbar-small-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-toolbar-small-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-toolbar-small-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-toolbar-small-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-toolbar-small-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-toolbar-small-tr, +.x-btn-default-toolbar-small-br, +.x-btn-default-toolbar-small-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-toolbar-small-tl, +.x-btn-default-toolbar-small-bl, +.x-btn-default-toolbar-small-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-toolbar-small-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-toolbar-small-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-toolbar-small-tl, +.x-btn-default-toolbar-small-bl, +.x-btn-default-toolbar-small-tr, +.x-btn-default-toolbar-small-br, +.x-btn-default-toolbar-small-tc, +.x-btn-default-toolbar-small-bc, +.x-btn-default-toolbar-small-ml, +.x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-toolbar-small-ml, +.x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-toolbar-small-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-toolbar-small { + border-color: #e1e1e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-toolbar-small { + min-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-toolbar-small { + min-height: auto; + height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-toolbar-small { + font: bold 12px/16px tahoma, verdana, sans-serif; + color: #666; + padding: 0 5px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-small { + max-width: calc(100% - 16px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-small { + max-width: calc(100% - 15px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-toolbar-small { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-toolbar-small { + font-size: 16px; + height: 16px; + color: #666; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small { + min-width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-default-toolbar-small.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-toolbar-small.x-btn-glyph { + color: #aeaeae; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small { + margin-right: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + margin-left: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-small, +.x-btn-split-bottom > .x-btn-button-default-toolbar-small { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-toolbar-small.x-btn-arrow-right:after { + width: 16px; + background-image: url(images/button/default-toolbar-small-arrow.png); + padding-right: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-toolbar-small.x-btn-arrow-bottom:after { + height: 13px; + background-image: url(images/button/default-toolbar-small-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-toolbar-small.x-btn-split-right:after { + width: 20px; + background-image: url(images/button/default-toolbar-small-s-arrow.png); + padding-right: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom:after { + height: 15px; + background-image: url(images/button/default-toolbar-small-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-small { + background-image: none; + background-color: #f5f5f5; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5)); + background-image: -webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 23px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-toolbar-small { + border-color: #d8d8d8; + background-image: none; + background-color: #ececec; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec)); + background-image: -webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-small { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-toolbar-small, +.x-btn.x-btn-pressed.x-btn-default-toolbar-small { + border-color: #cfcfcf; + background-image: none; + background-color: #e2e2e2; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5)); + background-image: -webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-toolbar-small { + background-image: none; + background-color: #f5f5f5; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5)); + background-image: -webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mc { + background-color: #f5f5f5; + background-image: url(images/btn/btn-default-toolbar-small-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-toolbar-small-tl, +.x-btn-over .x-btn-default-toolbar-small-bl, +.x-btn-over .x-btn-default-toolbar-small-tr, +.x-btn-over .x-btn-default-toolbar-small-br, +.x-btn-over .x-btn-default-toolbar-small-tc, +.x-btn-over .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-toolbar-small-ml, +.x-btn-over .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-toolbar-small-mc { + background-color: #ececec; + background-image: url(images/btn/btn-default-toolbar-small-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mc { + background-color: #ececec; + background-image: url(images/btn/btn-default-toolbar-small-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-default-toolbar-small-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-default-toolbar-small-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mc { + background-color: #f5f5f5; + background-image: url(images/btn/btn-default-toolbar-small-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-toolbar-small { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first .x-btn-default-toolbar-small-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle .x-btn-default-toolbar-small-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last .x-btn-default-toolbar-small-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first .x-btn-default-toolbar-small-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle .x-btn-default-toolbar-small-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last .x-btn-default-toolbar-small-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-small:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-toolbar-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-toolbar-small-cell > .x-grid-cell-inner >.x-btn-default-toolbar-small { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-toolbar-medium { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: #f5f5f5; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5)); + background-image: -webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-toolbar-medium-mc { + background-image: url(images/btn/btn-default-toolbar-medium-fbg.gif); + background-position: 0 top; + background-color: #f5f5f5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-toolbar-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-toolbar-medium-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-toolbar-medium-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-toolbar-medium-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-toolbar-medium-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-toolbar-medium-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-toolbar-medium-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-toolbar-medium-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-toolbar-medium-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-toolbar-medium-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-toolbar-medium-tr, +.x-btn-default-toolbar-medium-br, +.x-btn-default-toolbar-medium-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-toolbar-medium-tl, +.x-btn-default-toolbar-medium-bl, +.x-btn-default-toolbar-medium-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-toolbar-medium-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-toolbar-medium-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-toolbar-medium-tl, +.x-btn-default-toolbar-medium-bl, +.x-btn-default-toolbar-medium-tr, +.x-btn-default-toolbar-medium-br, +.x-btn-default-toolbar-medium-tc, +.x-btn-default-toolbar-medium-bc, +.x-btn-default-toolbar-medium-ml, +.x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-toolbar-medium-ml, +.x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-toolbar-medium-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-toolbar-medium { + border-color: #e1e1e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-toolbar-medium { + min-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-toolbar-medium { + min-height: auto; + height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-toolbar-medium { + font: bold 14px/18px tahoma, verdana, sans-serif; + color: #666; + padding: 0 8px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-medium { + max-width: calc(100% - 24px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-medium { + max-width: calc(100% - 23px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-toolbar-medium { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-toolbar-medium { + font-size: 24px; + height: 24px; + color: #666; + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium { + min-width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-default-toolbar-medium.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-toolbar-medium.x-btn-glyph { + color: #aeaeae; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium { + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-medium, +.x-btn-split-bottom > .x-btn-button-default-toolbar-medium { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-toolbar-medium.x-btn-arrow-right:after { + width: 24px; + background-image: url(images/button/default-toolbar-medium-arrow.png); + padding-right: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-toolbar-medium.x-btn-arrow-bottom:after { + height: 18px; + background-image: url(images/button/default-toolbar-medium-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-toolbar-medium.x-btn-split-right:after { + width: 28px; + background-image: url(images/button/default-toolbar-medium-s-arrow.png); + padding-right: 28px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom:after { + height: 24px; + background-image: url(images/button/default-toolbar-medium-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-medium { + background-image: none; + background-color: #f5f5f5; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5)); + background-image: -webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-toolbar-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 31px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-toolbar-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-toolbar-medium { + border-color: #d8d8d8; + background-image: none; + background-color: #ececec; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec)); + background-image: -webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-medium { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-toolbar-medium, +.x-btn.x-btn-pressed.x-btn-default-toolbar-medium { + border-color: #cfcfcf; + background-image: none; + background-color: #e2e2e2; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5)); + background-image: -webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-toolbar-medium { + background-image: none; + background-color: #f5f5f5; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5)); + background-image: -webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mc { + background-color: #f5f5f5; + background-image: url(images/btn/btn-default-toolbar-medium-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-toolbar-medium-tl, +.x-btn-over .x-btn-default-toolbar-medium-bl, +.x-btn-over .x-btn-default-toolbar-medium-tr, +.x-btn-over .x-btn-default-toolbar-medium-br, +.x-btn-over .x-btn-default-toolbar-medium-tc, +.x-btn-over .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-toolbar-medium-ml, +.x-btn-over .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-toolbar-medium-mc { + background-color: #ececec; + background-image: url(images/btn/btn-default-toolbar-medium-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mc { + background-color: #ececec; + background-image: url(images/btn/btn-default-toolbar-medium-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-default-toolbar-medium-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-default-toolbar-medium-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mc { + background-color: #f5f5f5; + background-image: url(images/btn/btn-default-toolbar-medium-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-toolbar-medium { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-toolbar-medium { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first .x-btn-default-toolbar-medium-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle .x-btn-default-toolbar-medium-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last .x-btn-default-toolbar-medium-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first .x-btn-default-toolbar-medium-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle .x-btn-default-toolbar-medium-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last .x-btn-default-toolbar-medium-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-medium:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-toolbar-medium-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-toolbar-medium-cell > .x-grid-cell-inner >.x-btn-default-toolbar-medium { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-toolbar-large { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: #f5f5f5; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5)); + background-image: -webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-toolbar-large-mc { + background-image: url(images/btn/btn-default-toolbar-large-fbg.gif); + background-position: 0 top; + background-color: #f5f5f5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-toolbar-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-toolbar-large-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-toolbar-large-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-toolbar-large-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-toolbar-large-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-toolbar-large-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-toolbar-large-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-toolbar-large-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-toolbar-large-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-toolbar-large-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-toolbar-large-tr, +.x-btn-default-toolbar-large-br, +.x-btn-default-toolbar-large-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-toolbar-large-tl, +.x-btn-default-toolbar-large-bl, +.x-btn-default-toolbar-large-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-toolbar-large-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-toolbar-large-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-toolbar-large-tl, +.x-btn-default-toolbar-large-bl, +.x-btn-default-toolbar-large-tr, +.x-btn-default-toolbar-large-br, +.x-btn-default-toolbar-large-tc, +.x-btn-default-toolbar-large-bc, +.x-btn-default-toolbar-large-ml, +.x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-toolbar-large-ml, +.x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-toolbar-large-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-toolbar-large { + border-color: #e1e1e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-toolbar-large { + min-height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-toolbar-large { + min-height: auto; + height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-toolbar-large { + font: bold 16px/20px tahoma, verdana, sans-serif; + color: #666; + padding: 0 10px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-large { + max-width: calc(100% - 32px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-large { + max-width: calc(100% - 31px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-toolbar-large { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-toolbar-large { + font-size: 32px; + height: 32px; + color: #666; + line-height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + width: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large { + min-width: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-default-toolbar-large.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-toolbar-large.x-btn-glyph { + color: #aeaeae; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large { + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-large, +.x-btn-split-bottom > .x-btn-button-default-toolbar-large { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-toolbar-large.x-btn-arrow-right:after { + width: 28px; + background-image: url(images/button/default-toolbar-large-arrow.png); + padding-right: 28px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-toolbar-large.x-btn-arrow-bottom:after { + height: 20px; + background-image: url(images/button/default-toolbar-large-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-toolbar-large.x-btn-split-right:after { + width: 35px; + background-image: url(images/button/default-toolbar-large-s-arrow.png); + padding-right: 35px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom:after { + height: 29px; + background-image: url(images/button/default-toolbar-large-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-large { + background-image: none; + background-color: #f5f5f5; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5)); + background-image: -webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-toolbar-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 38px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-toolbar-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-toolbar-large { + border-color: #d8d8d8; + background-image: none; + background-color: #ececec; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec)); + background-image: -webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-large { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-toolbar-large, +.x-btn.x-btn-pressed.x-btn-default-toolbar-large { + border-color: #cfcfcf; + background-image: none; + background-color: #e2e2e2; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5)); + background-image: -webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-toolbar-large { + background-image: none; + background-color: #f5f5f5; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5)); + background-image: -webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: -ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); + background-image: linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mc { + background-color: #f5f5f5; + background-image: url(images/btn/btn-default-toolbar-large-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-toolbar-large-tl, +.x-btn-over .x-btn-default-toolbar-large-bl, +.x-btn-over .x-btn-default-toolbar-large-tr, +.x-btn-over .x-btn-default-toolbar-large-br, +.x-btn-over .x-btn-default-toolbar-large-tc, +.x-btn-over .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-toolbar-large-ml, +.x-btn-over .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-toolbar-large-mc { + background-color: #ececec; + background-image: url(images/btn/btn-default-toolbar-large-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mc { + background-color: #ececec; + background-image: url(images/btn/btn-default-toolbar-large-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-default-toolbar-large-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-default-toolbar-large-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mc { + background-color: #f5f5f5; + background-image: url(images/btn/btn-default-toolbar-large-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-toolbar-large { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-toolbar-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first .x-btn-default-toolbar-large-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle .x-btn-default-toolbar-large-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last .x-btn-default-toolbar-large-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first .x-btn-default-toolbar-large-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle .x-btn-default-toolbar-large-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last .x-btn-default-toolbar-large-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-large:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-toolbar-large-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-toolbar-large-cell > .x-grid-cell-inner >.x-btn-default-toolbar-large { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:1 */ +.x-tool { + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:5 */ +.x-tool-tool-el { + overflow: hidden; + width: 16px; + height: 16px; + margin: 0; + color: #fff; + text-align: center; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:16 */ +.x-tool-over .x-tool-tool-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:21 */ +.x-tool-pressed .x-tool-tool-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:30 */ +.x-keyboard-mode .x-tool-focus { + outline: 1px solid #157fcc; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-tool-focus, +.x-edge .x-keyboard-mode .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #157fcc; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:40 */ +.x-tool-img { + background-image: url(images/tools/tool-sprites.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:44 */ +.x-tool-placeholder { + visibility: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:48 */ +.x-tool-close { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:57 */ +.x-tool-minimize { + background-position: 0 -16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:66 */ +.x-tool-maximize { + background-position: 0 -32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:75 */ +.x-tool-restore { + background-position: 0 -48px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:84 */ +.x-tool-toggle { + background-position: 0 -64px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:92 */ +.x-panel-collapsed .x-tool-toggle { + background-position: 0 -80px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:102 */ +.x-tool-gear { + background-position: 0 -96px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:111 */ +.x-tool-prev { + background-position: 0 -112px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:120 */ +.x-tool-next { + background-position: 0 -128px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:129 */ +.x-tool-pin { + background-position: 0 -144px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:138 */ +.x-tool-unpin { + background-position: 0 -160px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:147 */ +.x-tool-right { + background-position: 0 -176px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:156 */ +.x-tool-left { + background-position: 0 -192px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:165 */ +.x-tool-down { + background-position: 0 -208px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:174 */ +.x-tool-up { + background-position: 0 -224px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:183 */ +.x-tool-refresh { + background-position: 0 -240px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:192 */ +.x-tool-plus { + background-position: 0 -256px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:201 */ +.x-tool-minus { + background-position: 0 -272px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:210 */ +.x-tool-search { + background-position: 0 -288px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:219 */ +.x-tool-save { + background-position: 0 -304px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:228 */ +.x-tool-help { + background-position: 0 -320px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:237 */ +.x-tool-print { + background-position: 0 -336px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:246 */ +.x-tool-expand { + background-position: 0 -352px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:255 */ +.x-tool-collapse { + background-position: 0 -368px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:264 */ +.x-tool-resize { + background-position: 0 -384px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:273 */ +.x-tool-move { + background-position: 0 -400px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:282 */ +.x-tool-expand-bottom { + background-position: 0 -208px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:291 */ +.x-tool-collapse-bottom { + background-position: 0 -208px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:300 */ +.x-tool-expand-top { + background-position: 0 -224px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:309 */ +.x-tool-collapse-top { + background-position: 0 -224px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:318 */ +.x-tool-expand-left { + background-position: 0 -192px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:327 */ +.x-tool-collapse-left { + background-position: 0 -192px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:336 */ +.x-tool-expand-right { + background-position: 0 -176px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:345 */ +.x-tool-collapse-right { + background-position: 0 -176px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Header.scss:1 */ +.x-header-draggable, +.x-header-ghost { + cursor: move; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Header.scss:6 */ +.x-header-text { + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:22 */ +.x-collapse-el { + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:46 */ +.x-layout-split-left { + background-image: url(images/util/splitter/mini-left.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:55 */ +.x-layout-split-right { + background-image: url(images/util/splitter/mini-right.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:86 */ +.x-layout-split-top { + background-image: url(images/util/splitter/mini-top.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:95 */ +.x-layout-split-bottom { + background-image: url(images/util/splitter/mini-bottom.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:105 */ +.x-splitter-collapsed .x-layout-split-left { + background-image: url(images/util/splitter/mini-right.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:114 */ +.x-splitter-collapsed .x-layout-split-right { + background-image: url(images/util/splitter/mini-left.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:145 */ +.x-splitter-collapsed .x-layout-split-top { + background-image: url(images/util/splitter/mini-bottom.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:154 */ +.x-splitter-collapsed .x-layout-split-bottom { + background-image: url(images/util/splitter/mini-top.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:164 */ +.x-splitter-active { + background-color: #b4b4b4; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:168 */ +.x-splitter-active .x-collapse-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:173 */ +.x-layout-split-left, +.x-layout-split-right { + top: 50%; + margin-top: -24px; + width: 100%; + height: 48px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:184 */ +.x-layout-split-top, +.x-layout-split-bottom { + left: 50%; + width: 48px; + height: 100%; + margin-left: -24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-keyboard-mode .x-splitter-focus:after { + position: absolute; + content: ' '; + top: 1px; + right: 1px; + bottom: 1px; + left: 1px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:598 */ +.x-toolbar-default { + padding: 6px 0 6px 8px; + border-style: solid; + border-color: #c2c2c2; + border-width: 1px; + background-image: none; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:614 */ +.x-toolbar-default .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:629 */ +.x-toolbar-default .x-toolbar-item { + margin: 0 8px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:639 */ +.x-toolbar-default .x-toolbar-separator-horizontal { + margin: 0 8px 0 0; + height: 14px; + border-style: solid; + border-width: 0 0 0 1px; + border-left-color: #e1e1e1; + border-right-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:648 */ +.x-toolbar-default .x-box-menu-after { + margin: 0 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:653 */ +.x-toolbar-default-vertical { + padding: 6px 8px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:662 */ +.x-toolbar-default-vertical .x-toolbar-item { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:671 */ +.x-toolbar-default-vertical .x-toolbar-separator-vertical { + margin: 0 5px 6px; + border-style: solid none; + border-width: 1px 0 0; + border-top-color: #e1e1e1; + border-bottom-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:679 */ +.x-toolbar-default-vertical .x-box-menu-after { + margin: 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:694 */ +.x-toolbar-text-default { + padding: 0 4px; + color: #334049; + font: normal 13px/16px tahoma, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:700 */ +.x-toolbar-spacer-default { + width: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-toolbar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-toolbar-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-toolbar-default { + cursor: pointer; + color: #b0b0b0; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-toolbar-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-toolbar-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-toolbar-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:232 */ +.x-box-scroller-toolbar-default.x-box-scroller-left, +.x-box-scroller-toolbar-default.x-box-scroller-right { + width: 16px; + height: 16px; + top: 50%; + margin-top: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:259 */ +.x-box-scroller-toolbar-default.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + background-image: url(images/toolbar/default-scroll-left.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:284 */ +.x-box-scroller-toolbar-default.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + background-image: url(images/toolbar/default-scroll-right.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:311 */ +.x-box-scroller-toolbar-default.x-box-scroller-top, +.x-box-scroller-toolbar-default.x-box-scroller-bottom { + height: 16px; + width: 16px; + left: 50%; + margin-left: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:338 */ +.x-box-scroller-toolbar-default.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + background-image: url(images/toolbar/default-scroll-top.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:363 */ +.x-box-scroller-toolbar-default.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + background-image: url(images/toolbar/default-scroll-bottom.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:742 */ +.x-ie8 .x-box-scroller-toolbar-default { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:748 */ +.x-toolbar-more-icon { + background-image: url(images/toolbar/default-more.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:598 */ +.x-toolbar-footer { + padding: 6px 0 6px 6px; + border-style: solid; + border-color: #c2c2c2; + border-width: 0; + background-image: none; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:614 */ +.x-toolbar-footer .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:629 */ +.x-toolbar-footer .x-toolbar-item { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:639 */ +.x-toolbar-footer .x-toolbar-separator-horizontal { + margin: 0 8px 0 0; + height: 14px; + border-style: solid; + border-width: 0 0 0 1px; + border-left-color: #e1e1e1; + border-right-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:648 */ +.x-toolbar-footer .x-box-menu-after { + margin: 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:653 */ +.x-toolbar-footer-vertical { + padding: 6px 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:662 */ +.x-toolbar-footer-vertical .x-toolbar-item { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:671 */ +.x-toolbar-footer-vertical .x-toolbar-separator-vertical { + margin: 0 5px 6px; + border-style: solid none; + border-width: 1px 0 0; + border-top-color: #e1e1e1; + border-bottom-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:679 */ +.x-toolbar-footer-vertical .x-box-menu-after { + margin: 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:694 */ +.x-toolbar-text-footer { + padding: 0 4px; + color: #334049; + font: normal 13px/16px tahoma, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:700 */ +.x-toolbar-spacer-footer { + width: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-toolbar-footer-scroller .x-box-scroller-body-horizontal { + margin-left: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-toolbar-footer-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-toolbar-footer { + cursor: pointer; + color: #b0b0b0; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-toolbar-footer.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-toolbar-footer.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-toolbar-footer.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:232 */ +.x-box-scroller-toolbar-footer.x-box-scroller-left, +.x-box-scroller-toolbar-footer.x-box-scroller-right { + width: 16px; + height: 16px; + top: 50%; + margin-top: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:259 */ +.x-box-scroller-toolbar-footer.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + background-image: url(images/toolbar/footer-scroll-left.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:284 */ +.x-box-scroller-toolbar-footer.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + background-image: url(images/toolbar/footer-scroll-right.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:742 */ +.x-ie8 .x-box-scroller-toolbar-footer { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:748 */ +.x-toolbar-more-icon { + background-image: url(images/toolbar/footer-more.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:1 */ +.x-dd-drag-proxy { + color: #000; + font: normal 13px/17px tahoma, verdana, sans-serif; + border: 1px solid #e1e1e1; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:8 */ +.x-dd-drag-ghost, +.x-dd-drop-icon { + padding: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:19 */ +.x-dd-drag-ghost { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:30 */ +.x-dd-drop-ok .x-dd-drop-icon { + background-image: url(images/dd/drop-yes.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:38 */ +.x-dd-drop-ok-add .x-dd-drop-icon { + background-image: url(images/dd/drop-add.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:47 */ +.x-dd-drop-nodrop div.x-dd-drop-icon { + background-image: url(images/dd/drop-no.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Panel.scss:1 */ +.x-panel-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:799 */ +.x-panel-default { + border-color: #157fcc; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:802 */ +.x-panel-default.x-masked { + border-color: #b9d9f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:810 */ +.x-panel-header-default { + font-size: 13px; + border: 1px solid #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:836 */ +.x-panel-header-default .x-tool-tool-el { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:842 */ +.x-panel-header-default-horizontal { + padding: 9px 9px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:846 */ +.x-panel-header-default-horizontal .x-panel-header-default-tab-bar { + margin-top: -9px; + margin-bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:854 */ +.x-panel-header-default-horizontal.x-header-noborder { + padding: 10px 10px 10px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:858 */ +.x-panel-header-default-horizontal.x-header-noborder .x-panel-header-default-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:866 */ +.x-panel-header-default-vertical { + padding: 9px 9px 9px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:870 */ +.x-panel-header-default-vertical .x-panel-header-default-tab-bar { + margin-right: -9px; + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:878 */ +.x-panel-header-default-vertical.x-header-noborder { + padding: 10px 10px 10px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:882 */ +.x-panel-header-default-vertical.x-header-noborder .x-panel-header-default-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:916 */ +.x-panel-header-title-default { + color: #fff; + font-size: 13px; + font-weight: bold; + font-family: tahoma, verdana, sans-serif; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:929 */ +.x-keyboard-mode .x-panel-header-title-default.x-title-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:950 */ +.x-panel-header-title-default > .x-title-text-default { + text-transform: none; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:997 */ +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-top { + height: 22px; + padding-bottom: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1002 */ +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-right { + width: 22px; + padding-left: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1014 */ +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-bottom { + height: 22px; + padding-top: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1019 */ +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-left { + width: 22px; + padding-right: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1031 */ +.x-panel-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default { + width: 16px; + height: 16px; + font-size: 16px; + color: #fff; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1038 */ +.x-panel-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1051 */ +.x-ie8 .x-panel-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph { + color: #8abfe6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1062 */ +.x-panel-body-default { + background: #fff; + border-color: #c2c2c2; + color: #000; + font-size: 13px; + font-weight: normal; + font-family: tahoma, verdana, sans-serif; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1226 */ +.x-panel-header-default { + background-image: none; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1230 */ +.x-panel-header-default-vertical { + background-image: none; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1288 */ +.x-panel .x-panel-header-default-collapsed-border-top { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1292 */ +.x-panel .x-panel-header-default-collapsed-border-right { + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1296 */ +.x-panel .x-panel-header-default-collapsed-border-bottom { + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1300 */ +.x-panel .x-panel-header-default-collapsed-border-left { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1336 */ +.x-panel-header-default-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1346 */ +.x-panel-header-default-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1358 */ +.x-panel-header-default-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1368 */ +.x-panel-header-default-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1381 */ +.x-keyboard-mode .x-panel-header-default .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1429 */ +.x-panel-default-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-panel-default-outer-border-l { + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-panel-default-outer-border-b { + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-panel-default-outer-border-bl { + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-panel-default-outer-border-r { + border-right-color: #157fcc !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-panel-default-outer-border-rl { + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-panel-default-outer-border-rb { + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-panel-default-outer-border-rbl { + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-panel-default-outer-border-t { + border-top-color: #157fcc !important; + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-panel-default-outer-border-tl { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-panel-default-outer-border-tb { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-panel-default-outer-border-tbl { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-panel-default-outer-border-tr { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-right-color: #157fcc !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-panel-default-outer-border-trl { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-panel-default-outer-border-trb { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-panel-default-outer-border-trbl { + border-color: #157fcc !important; + border-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:799 */ +.x-panel-default-framed { + border-color: #157fcc; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:802 */ +.x-panel-default-framed.x-masked { + border-color: #b9d9f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:810 */ +.x-panel-header-default-framed { + font-size: 13px; + border: 5px solid #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:836 */ +.x-panel-header-default-framed .x-tool-tool-el { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:842 */ +.x-panel-header-default-framed-horizontal { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:846 */ +.x-panel-header-default-framed-horizontal .x-panel-header-default-framed-tab-bar { + margin-top: -5px; + margin-bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:854 */ +.x-panel-header-default-framed-horizontal.x-header-noborder { + padding: 10px 10px 5px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:858 */ +.x-panel-header-default-framed-horizontal.x-header-noborder .x-panel-header-default-framed-tab-bar { + margin-top: -10px; + margin-bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:866 */ +.x-panel-header-default-framed-vertical { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:870 */ +.x-panel-header-default-framed-vertical .x-panel-header-default-framed-tab-bar { + margin-right: -5px; + margin-left: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:878 */ +.x-panel-header-default-framed-vertical.x-header-noborder { + padding: 10px 10px 10px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:882 */ +.x-panel-header-default-framed-vertical.x-header-noborder .x-panel-header-default-framed-tab-bar { + margin-right: -10px; + margin-left: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:916 */ +.x-panel-header-title-default-framed { + color: #fff; + font-size: 13px; + font-weight: bold; + font-family: tahoma, verdana, sans-serif; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:929 */ +.x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:950 */ +.x-panel-header-title-default-framed > .x-title-text-default-framed { + text-transform: none; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:997 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-top { + height: 22px; + padding-bottom: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1002 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-right { + width: 22px; + padding-left: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1014 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-bottom { + height: 22px; + padding-top: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1019 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-left { + width: 22px; + padding-right: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1031 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed > .x-title-icon-default-framed { + width: 16px; + height: 16px; + font-size: 16px; + color: #fff; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1038 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed > .x-title-icon-default-framed.x-title-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1051 */ +.x-ie8 .x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed > .x-title-icon-default-framed.x-title-glyph { + color: #8abfe6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1062 */ +.x-panel-body-default-framed { + background: #fff; + border-color: #c2c2c2; + color: #000; + font-size: 13px; + font-weight: normal; + font-family: tahoma, verdana, sans-serif; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-default-framed { + -webkit-border-radius: 4px; + -moz-border-radius: 4px; + -ms-border-radius: 4px; + -o-border-radius: 4px; + border-radius: 4px; + padding: 0px 0px 0px 0px; + border-width: 5px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-default-framed-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-default-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-default-framed-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-0-0-0-0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-default-framed-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-default-framed-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-default-framed-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-default-framed-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-default-framed-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-default-framed-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-default-framed-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-default-framed-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-default-framed-tr, +.x-panel-default-framed-br, +.x-panel-default-framed-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-default-framed-tl, +.x-panel-default-framed-bl, +.x-panel-default-framed-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-default-framed-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-default-framed-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-default-framed-tl, +.x-panel-default-framed-bl, +.x-panel-default-framed-tr, +.x-panel-default-framed-br, +.x-panel-default-framed-tc, +.x-panel-default-framed-bc, +.x-panel-default-framed-ml, +.x-panel-default-framed-mr { + background-image: url(images/panel/panel-default-framed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-default-framed-ml, +.x-panel-default-framed-mr { + background-image: url(images/panel/panel-default-framed-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-default-framed-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-top { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 5px 5px 5px 5px; + border-width: 5px 5px 0 5px; + border-style: solid; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-top-mc { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-top-frameInfo { + font-family: dh-5-5-0-5-5-5-0-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-top-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-top-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-top-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-top-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-top-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-top-tr, +.x-panel-header-default-framed-top-br, +.x-panel-header-default-framed-top-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-top-tl, +.x-panel-header-default-framed-top-bl, +.x-panel-header-default-framed-top-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-top-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-top-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-top-tl, +.x-panel-header-default-framed-top-bl, +.x-panel-header-default-framed-top-tr, +.x-panel-header-default-framed-top-br, +.x-panel-header-default-framed-top-tc, +.x-panel-header-default-framed-top-bc, +.x-panel-header-default-framed-top-ml, +.x-panel-header-default-framed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-top-ml, +.x-panel-header-default-framed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-top-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 5px 5px 5px 5px; + border-width: 5px 5px 5px 0; + border-style: solid; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-right-mc { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-right-frameInfo { + font-family: dh-5-5-5-0-5-5-5-0-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-right-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-right-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-right-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-right-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-right-ml { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-right-mr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-right-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-right-tr, +.x-panel-header-default-framed-right-br, +.x-panel-header-default-framed-right-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-right-tl, +.x-panel-header-default-framed-right-bl, +.x-panel-header-default-framed-right-ml { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-right-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-right-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-right-tl, +.x-panel-header-default-framed-right-bl, +.x-panel-header-default-framed-right-tr, +.x-panel-header-default-framed-right-br, +.x-panel-header-default-framed-right-tc, +.x-panel-header-default-framed-right-bc, +.x-panel-header-default-framed-right-ml, +.x-panel-header-default-framed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-right-ml, +.x-panel-header-default-framed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-right-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 0 5px 5px 5px; + border-style: solid; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-bottom-mc { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-bottom-frameInfo { + font-family: dh-0-5-5-5-0-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-bottom-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-bottom-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-bottom-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-bottom-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-bottom-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-bottom-tr, +.x-panel-header-default-framed-bottom-br, +.x-panel-header-default-framed-bottom-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-bottom-tl, +.x-panel-header-default-framed-bottom-bl, +.x-panel-header-default-framed-bottom-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-bottom-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-bottom-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-bottom-tl, +.x-panel-header-default-framed-bottom-bl, +.x-panel-header-default-framed-bottom-tr, +.x-panel-header-default-framed-bottom-br, +.x-panel-header-default-framed-bottom-tc, +.x-panel-header-default-framed-bottom-bc, +.x-panel-header-default-framed-bottom-ml, +.x-panel-header-default-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-bottom-ml, +.x-panel-header-default-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-bottom-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-left { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px 0 5px 5px; + border-style: solid; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-left-mc { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-left-frameInfo { + font-family: dh-5-0-5-5-5-0-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-left-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-left-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-left-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-left-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-left-ml { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-left-mr { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-left-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-left-tr, +.x-panel-header-default-framed-left-br, +.x-panel-header-default-framed-left-mr { + padding-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-left-tl, +.x-panel-header-default-framed-left-bl, +.x-panel-header-default-framed-left-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-left-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-left-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-left-tl, +.x-panel-header-default-framed-left-bl, +.x-panel-header-default-framed-left-tr, +.x-panel-header-default-framed-left-br, +.x-panel-header-default-framed-left-tc, +.x-panel-header-default-framed-left-bc, +.x-panel-header-default-framed-left-ml, +.x-panel-header-default-framed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-left-ml, +.x-panel-header-default-framed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-left-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-collapsed-top { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-collapsed-top-mc { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-collapsed-top-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-collapsed-top-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-collapsed-top-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-collapsed-top-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-collapsed-top-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-collapsed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-collapsed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-collapsed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-collapsed-top-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-collapsed-top-tr, +.x-panel-header-default-framed-collapsed-top-br, +.x-panel-header-default-framed-collapsed-top-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-collapsed-top-tl, +.x-panel-header-default-framed-collapsed-top-bl, +.x-panel-header-default-framed-collapsed-top-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-collapsed-top-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-collapsed-top-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-collapsed-top-tl, +.x-panel-header-default-framed-collapsed-top-bl, +.x-panel-header-default-framed-collapsed-top-tr, +.x-panel-header-default-framed-collapsed-top-br, +.x-panel-header-default-framed-collapsed-top-tc, +.x-panel-header-default-framed-collapsed-top-bc, +.x-panel-header-default-framed-collapsed-top-ml, +.x-panel-header-default-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-collapsed-top-ml, +.x-panel-header-default-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-collapsed-top-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-collapsed-right { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-collapsed-right-mc { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-collapsed-right-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-collapsed-right-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-collapsed-right-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-collapsed-right-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-collapsed-right-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-collapsed-right-ml { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-collapsed-right-mr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-collapsed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-collapsed-right-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-collapsed-right-tr, +.x-panel-header-default-framed-collapsed-right-br, +.x-panel-header-default-framed-collapsed-right-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-collapsed-right-tl, +.x-panel-header-default-framed-collapsed-right-bl, +.x-panel-header-default-framed-collapsed-right-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-collapsed-right-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-collapsed-right-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-collapsed-right-tl, +.x-panel-header-default-framed-collapsed-right-bl, +.x-panel-header-default-framed-collapsed-right-tr, +.x-panel-header-default-framed-collapsed-right-br, +.x-panel-header-default-framed-collapsed-right-tc, +.x-panel-header-default-framed-collapsed-right-bc, +.x-panel-header-default-framed-collapsed-right-ml, +.x-panel-header-default-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-collapsed-right-ml, +.x-panel-header-default-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-collapsed-right-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-collapsed-bottom { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-collapsed-bottom-mc { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-collapsed-bottom-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-collapsed-bottom-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-collapsed-bottom-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-collapsed-bottom-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-collapsed-bottom-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-collapsed-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-collapsed-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-collapsed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-collapsed-bottom-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-collapsed-bottom-tr, +.x-panel-header-default-framed-collapsed-bottom-br, +.x-panel-header-default-framed-collapsed-bottom-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-collapsed-bottom-tl, +.x-panel-header-default-framed-collapsed-bottom-bl, +.x-panel-header-default-framed-collapsed-bottom-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-collapsed-bottom-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-collapsed-bottom-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-collapsed-bottom-tl, +.x-panel-header-default-framed-collapsed-bottom-bl, +.x-panel-header-default-framed-collapsed-bottom-tr, +.x-panel-header-default-framed-collapsed-bottom-br, +.x-panel-header-default-framed-collapsed-bottom-tc, +.x-panel-header-default-framed-collapsed-bottom-bc, +.x-panel-header-default-framed-collapsed-bottom-ml, +.x-panel-header-default-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-collapsed-bottom-ml, +.x-panel-header-default-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-collapsed-bottom-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-collapsed-left { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-collapsed-left-mc { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-collapsed-left-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-collapsed-left-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-collapsed-left-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-collapsed-left-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-collapsed-left-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-collapsed-left-ml { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-collapsed-left-mr { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-collapsed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-collapsed-left-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-collapsed-left-tr, +.x-panel-header-default-framed-collapsed-left-br, +.x-panel-header-default-framed-collapsed-left-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-collapsed-left-tl, +.x-panel-header-default-framed-collapsed-left-bl, +.x-panel-header-default-framed-collapsed-left-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-collapsed-left-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-collapsed-left-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-collapsed-left-tl, +.x-panel-header-default-framed-collapsed-left-bl, +.x-panel-header-default-framed-collapsed-left-tr, +.x-panel-header-default-framed-collapsed-left-br, +.x-panel-header-default-framed-collapsed-left-tc, +.x-panel-header-default-framed-collapsed-left-bc, +.x-panel-header-default-framed-collapsed-left-ml, +.x-panel-header-default-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-collapsed-left-ml, +.x-panel-header-default-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-collapsed-left-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1188 */ +.x-panel .x-panel-header-default-framed-top { + border-bottom-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1192 */ +.x-panel .x-panel-header-default-framed-right { + border-left-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1196 */ +.x-panel .x-panel-header-default-framed-bottom { + border-top-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1200 */ +.x-panel .x-panel-header-default-framed-left { + border-right-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1206 */ +.x-nbr .x-panel-header-default-framed-collapsed-top { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1210 */ +.x-nbr .x-panel-header-default-framed-collapsed-right { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1214 */ +.x-nbr .x-panel-header-default-framed-collapsed-bottom { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1218 */ +.x-nbr .x-panel-header-default-framed-collapsed-left { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1336 */ +.x-panel-header-default-framed-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1346 */ +.x-panel-header-default-framed-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1358 */ +.x-panel-header-default-framed-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1368 */ +.x-panel-header-default-framed-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1381 */ +.x-keyboard-mode .x-panel-header-default-framed .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1426 */ +.x-panel-default-framed-resizable { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1429 */ +.x-panel-default-framed-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1438 */ +.x-panel-default-framed-resizable .x-panel-handle-north-br { + top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1441 */ +.x-panel-default-framed-resizable .x-panel-handle-south-br { + bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1444 */ +.x-panel-default-framed-resizable .x-panel-handle-east-br { + right: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1447 */ +.x-panel-default-framed-resizable .x-panel-handle-west-br { + left: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1450 */ +.x-panel-default-framed-resizable .x-panel-handle-northwest-br { + left: -5px; + top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1454 */ +.x-panel-default-framed-resizable .x-panel-handle-northeast-br { + right: -5px; + top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1458 */ +.x-panel-default-framed-resizable .x-panel-handle-southeast-br { + right: -5px; + bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1462 */ +.x-panel-default-framed-resizable .x-panel-handle-southwest-br { + left: -5px; + bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-panel-default-framed-outer-border-l { + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-panel-default-framed-outer-border-b { + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-panel-default-framed-outer-border-bl { + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-panel-default-framed-outer-border-r { + border-right-color: #157fcc !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-panel-default-framed-outer-border-rl { + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-panel-default-framed-outer-border-rb { + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-panel-default-framed-outer-border-rbl { + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-panel-default-framed-outer-border-t { + border-top-color: #157fcc !important; + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-panel-default-framed-outer-border-tl { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-panel-default-framed-outer-border-tb { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-panel-default-framed-outer-border-tbl { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-panel-default-framed-outer-border-tr { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-right-color: #157fcc !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-panel-default-framed-outer-border-trl { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-left-color: #157fcc !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-panel-default-framed-outer-border-trb { + border-top-color: #157fcc !important; + border-top-width: 1px !important; + border-right-color: #157fcc !important; + border-right-width: 1px !important; + border-bottom-color: #157fcc !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-panel-default-framed-outer-border-trbl { + border-color: #157fcc !important; + border-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:243 */ +.x-btn-group-default { + border-color: #e0ebf3; + -webkit-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + -moz-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:252 */ +.x-btn-group-header-default { + padding: 4px 5px; + line-height: 16px; + background: #e0ebf3; + -moz-border-radius-topleft: 0px; + -webkit-border-top-left-radius: 0px; + border-top-left-radius: 0px; + -moz-border-radius-topright: 0px; + -webkit-border-top-right-radius: 0px; + border-top-right-radius: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:263 */ +.x-btn-group-header-default .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:274 */ +.x-btn-group-header-title-default { + font: normal 13px tahoma, verdana, sans-serif; + line-height: 16px; + color: #666; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:280 */ +.x-btn-group-body-default { + padding: 0 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:282 */ +.x-btn-group-body-default .x-table-layout { + border-spacing: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-group-default-framed { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 0px 1px 0px 1px; + border-width: 3px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-group-default-framed-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-group-default-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-group-default-framed-frameInfo { + font-family: dh-3-3-3-3-3-3-3-3-0-1-0-1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-group-default-framed-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-group-default-framed-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-group-default-framed-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-group-default-framed-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-group-default-framed-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-group-default-framed-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-group-default-framed-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-group-default-framed-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-group-default-framed-tr, +.x-btn-group-default-framed-br, +.x-btn-group-default-framed-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-group-default-framed-tl, +.x-btn-group-default-framed-bl, +.x-btn-group-default-framed-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-group-default-framed-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-group-default-framed-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-group-default-framed-tl, +.x-btn-group-default-framed-bl, +.x-btn-group-default-framed-tr, +.x-btn-group-default-framed-br, +.x-btn-group-default-framed-tc, +.x-btn-group-default-framed-bc, +.x-btn-group-default-framed-ml, +.x-btn-group-default-framed-mr { + background-image: url(images/btn-group/btn-group-default-framed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-group-default-framed-ml, +.x-btn-group-default-framed-mr { + background-image: url(images/btn-group/btn-group-default-framed-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-group-default-framed-mc { + padding: 0px 1px 0px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-group-default-framed-notitle { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 0px 1px 0px 1px; + border-width: 3px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-group-default-framed-notitle-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-group-default-framed-notitle { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-group-default-framed-notitle-frameInfo { + font-family: dh-3-3-3-3-3-3-3-3-0-1-0-1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-group-default-framed-notitle-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-group-default-framed-notitle-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-group-default-framed-notitle-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-group-default-framed-notitle-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-group-default-framed-notitle-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-group-default-framed-notitle-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-group-default-framed-notitle-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-group-default-framed-notitle-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-group-default-framed-notitle-tr, +.x-btn-group-default-framed-notitle-br, +.x-btn-group-default-framed-notitle-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-group-default-framed-notitle-tl, +.x-btn-group-default-framed-notitle-bl, +.x-btn-group-default-framed-notitle-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-group-default-framed-notitle-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-group-default-framed-notitle-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-group-default-framed-notitle-tl, +.x-btn-group-default-framed-notitle-bl, +.x-btn-group-default-framed-notitle-tr, +.x-btn-group-default-framed-notitle-br, +.x-btn-group-default-framed-notitle-tc, +.x-btn-group-default-framed-notitle-bc, +.x-btn-group-default-framed-notitle-ml, +.x-btn-group-default-framed-notitle-mr { + background-image: url(images/btn-group/btn-group-default-framed-notitle-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-group-default-framed-notitle-ml, +.x-btn-group-default-framed-notitle-mr { + background-image: url(images/btn-group/btn-group-default-framed-notitle-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-group-default-framed-notitle-mc { + padding: 0px 1px 0px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:243 */ +.x-btn-group-default-framed { + border-color: #e0ebf3; + -webkit-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + -moz-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:252 */ +.x-btn-group-header-default-framed { + padding: 4px 5px; + line-height: 16px; + background: #e0ebf3; + -moz-border-radius-topleft: 3px; + -webkit-border-top-left-radius: 3px; + border-top-left-radius: 3px; + -moz-border-radius-topright: 3px; + -webkit-border-top-right-radius: 3px; + border-top-right-radius: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:263 */ +.x-btn-group-header-default-framed .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:274 */ +.x-btn-group-header-title-default-framed { + font: normal 13px tahoma, verdana, sans-serif; + line-height: 16px; + color: #666; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:280 */ +.x-btn-group-body-default-framed { + padding: 0 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:282 */ +.x-btn-group-body-default-framed .x-table-layout { + border-spacing: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:1 */ +.x-dashboard-column { + padding: 0 0 7px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:5 */ +.x-dashboard-panel { + margin-top: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:9 */ +.x-dashboard-column-first { + padding-left: 7px; + clear: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:14 */ +.x-dashboard-column-last { + padding-right: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:18 */ +.x-dashboard .x-panel-dd-spacer { + border: 2px dashed #99bbe8; + background: #f6f6f6; + border-radius: 4px; + -moz-border-radius: 4px; + margin-top: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:28 */ +.x-dashboard-dd-over { + overflow: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Window.scss:1 */ +.x-window-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:545 */ +.x-window-default { + border-color: #3892d4; + -webkit-border-radius: 4px; + -moz-border-radius: 4px; + -ms-border-radius: 4px; + -o-border-radius: 4px; + border-radius: 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-default { + -webkit-border-radius: 4px; + -moz-border-radius: 4px; + -ms-border-radius: 4px; + -o-border-radius: 4px; + border-radius: 4px; + padding: 0px 0px 0px 0px; + border-width: 5px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-default-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-default { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-default-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-0-0-0-0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-default-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-default-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-default-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-default-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-default-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-default-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-default-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-default-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-default-tr, +.x-window-default-br, +.x-window-default-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-default-tl, +.x-window-default-bl, +.x-window-default-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-default-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-default-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-default-tl, +.x-window-default-bl, +.x-window-default-tr, +.x-window-default-br, +.x-window-default-tc, +.x-window-default-bc, +.x-window-default-ml, +.x-window-default-mr { + background-image: url(images/window/window-default-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-default-ml, +.x-window-default-mr { + background-image: url(images/window/window-default-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-default-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:567 */ +.x-window-body-default { + border-color: #3892d4; + border-width: 1px; + border-style: solid; + background: #fff; + color: #000; + font-size: 13px; + font-weight: normal; + font-family: tahoma, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:581 */ +.x-window-header-default { + font-size: 13px; + border-color: #3892d4; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:586 */ +.x-window-header-default .x-tool-img { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:599 */ +.x-window-header-default-horizontal .x-window-header-default-tab-bar { + margin-top: -5px; + margin-bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:606 */ +.x-window-header-default-vertical .x-window-header-default-tab-bar { + margin-right: -5px; + margin-left: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:622 */ +.x-window-header-title-default { + color: #fff; + font-size: 13px; + font-weight: bold; + font-family: tahoma, verdana, sans-serif; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:631 */ +.x-window-header-title-default > .x-title-text-default { + padding: 0; + text-transform: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:678 */ +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-top { + height: 22px; + padding-bottom: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:683 */ +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-right { + width: 22px; + padding-left: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:695 */ +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-bottom { + height: 22px; + padding-top: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:700 */ +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-left { + width: 22px; + padding-right: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:712 */ +.x-window-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default { + width: 16px; + height: 16px; + font-size: 16px; + color: #fff; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:719 */ +.x-window-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:732 */ +.x-ie8 .x-window-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph { + color: #9cc9e9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-top { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 5px 5px 5px 5px; + border-width: 5px 5px 5px 5px; + border-style: solid; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-top-mc { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-top-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-top-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-top-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-top-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-top-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-top-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-top-tr, +.x-window-header-default-top-br, +.x-window-header-default-top-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-top-tl, +.x-window-header-default-top-bl, +.x-window-header-default-top-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-top-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-top-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-top-tl, +.x-window-header-default-top-bl, +.x-window-header-default-top-tr, +.x-window-header-default-top-br, +.x-window-header-default-top-tc, +.x-window-header-default-top-bc, +.x-window-header-default-top-ml, +.x-window-header-default-top-mr { + background-image: url(images/window-header/window-header-default-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-top-ml, +.x-window-header-default-top-mr { + background-image: url(images/window-header/window-header-default-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-top-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 5px 5px 5px 5px; + border-width: 5px 5px 5px 5px; + border-style: solid; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-right-mc { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-right-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-right-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-right-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-right-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-right-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-right-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-right-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-right-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-right-tr, +.x-window-header-default-right-br, +.x-window-header-default-right-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-right-tl, +.x-window-header-default-right-bl, +.x-window-header-default-right-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-right-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-right-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-right-tl, +.x-window-header-default-right-bl, +.x-window-header-default-right-tr, +.x-window-header-default-right-br, +.x-window-header-default-right-tc, +.x-window-header-default-right-bc, +.x-window-header-default-right-ml, +.x-window-header-default-right-mr { + background-image: url(images/window-header/window-header-default-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-right-ml, +.x-window-header-default-right-mr { + background-image: url(images/window-header/window-header-default-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-right-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px 5px 5px 5px; + border-style: solid; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-bottom-mc { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-bottom-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-bottom-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-bottom-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-bottom-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-bottom-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-bottom-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-bottom-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-bottom-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-bottom-tr, +.x-window-header-default-bottom-br, +.x-window-header-default-bottom-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-bottom-tl, +.x-window-header-default-bottom-bl, +.x-window-header-default-bottom-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-bottom-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-bottom-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-bottom-tl, +.x-window-header-default-bottom-bl, +.x-window-header-default-bottom-tr, +.x-window-header-default-bottom-br, +.x-window-header-default-bottom-tc, +.x-window-header-default-bottom-bc, +.x-window-header-default-bottom-ml, +.x-window-header-default-bottom-mr { + background-image: url(images/window-header/window-header-default-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-bottom-ml, +.x-window-header-default-bottom-mr { + background-image: url(images/window-header/window-header-default-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-bottom-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-left { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px 5px 5px 5px; + border-style: solid; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-left-mc { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-left-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-left-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-left-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-left-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-left-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-left-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-left-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-left-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-left-tr, +.x-window-header-default-left-br, +.x-window-header-default-left-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-left-tl, +.x-window-header-default-left-bl, +.x-window-header-default-left-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-left-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-left-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-left-tl, +.x-window-header-default-left-bl, +.x-window-header-default-left-tr, +.x-window-header-default-left-br, +.x-window-header-default-left-tc, +.x-window-header-default-left-bc, +.x-window-header-default-left-ml, +.x-window-header-default-left-mr { + background-image: url(images/window-header/window-header-default-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-left-ml, +.x-window-header-default-left-mr { + background-image: url(images/window-header/window-header-default-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-left-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-collapsed-top { + -webkit-border-radius: 4px; + -moz-border-radius: 4px; + -ms-border-radius: 4px; + -o-border-radius: 4px; + border-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-collapsed-top-mc { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-collapsed-top-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-collapsed-top-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-collapsed-top-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-collapsed-top-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-collapsed-top-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-collapsed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-collapsed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-collapsed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-collapsed-top-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-collapsed-top-tr, +.x-window-header-default-collapsed-top-br, +.x-window-header-default-collapsed-top-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-collapsed-top-tl, +.x-window-header-default-collapsed-top-bl, +.x-window-header-default-collapsed-top-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-collapsed-top-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-collapsed-top-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-collapsed-top-tl, +.x-window-header-default-collapsed-top-bl, +.x-window-header-default-collapsed-top-tr, +.x-window-header-default-collapsed-top-br, +.x-window-header-default-collapsed-top-tc, +.x-window-header-default-collapsed-top-bc, +.x-window-header-default-collapsed-top-ml, +.x-window-header-default-collapsed-top-mr { + background-image: url(images/window-header/window-header-default-collapsed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-collapsed-top-ml, +.x-window-header-default-collapsed-top-mr { + background-image: url(images/window-header/window-header-default-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-collapsed-top-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-collapsed-right { + -webkit-border-radius: 4px; + -moz-border-radius: 4px; + -ms-border-radius: 4px; + -o-border-radius: 4px; + border-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-collapsed-right-mc { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-collapsed-right-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-collapsed-right-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-collapsed-right-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-collapsed-right-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-collapsed-right-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-collapsed-right-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-collapsed-right-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-collapsed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-collapsed-right-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-collapsed-right-tr, +.x-window-header-default-collapsed-right-br, +.x-window-header-default-collapsed-right-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-collapsed-right-tl, +.x-window-header-default-collapsed-right-bl, +.x-window-header-default-collapsed-right-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-collapsed-right-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-collapsed-right-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-collapsed-right-tl, +.x-window-header-default-collapsed-right-bl, +.x-window-header-default-collapsed-right-tr, +.x-window-header-default-collapsed-right-br, +.x-window-header-default-collapsed-right-tc, +.x-window-header-default-collapsed-right-bc, +.x-window-header-default-collapsed-right-ml, +.x-window-header-default-collapsed-right-mr { + background-image: url(images/window-header/window-header-default-collapsed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-collapsed-right-ml, +.x-window-header-default-collapsed-right-mr { + background-image: url(images/window-header/window-header-default-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-collapsed-right-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-collapsed-bottom { + -webkit-border-radius: 4px; + -moz-border-radius: 4px; + -ms-border-radius: 4px; + -o-border-radius: 4px; + border-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-collapsed-bottom-mc { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-collapsed-bottom-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-collapsed-bottom-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-collapsed-bottom-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-collapsed-bottom-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-collapsed-bottom-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-collapsed-bottom-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-collapsed-bottom-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-collapsed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-collapsed-bottom-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-collapsed-bottom-tr, +.x-window-header-default-collapsed-bottom-br, +.x-window-header-default-collapsed-bottom-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-collapsed-bottom-tl, +.x-window-header-default-collapsed-bottom-bl, +.x-window-header-default-collapsed-bottom-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-collapsed-bottom-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-collapsed-bottom-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-collapsed-bottom-tl, +.x-window-header-default-collapsed-bottom-bl, +.x-window-header-default-collapsed-bottom-tr, +.x-window-header-default-collapsed-bottom-br, +.x-window-header-default-collapsed-bottom-tc, +.x-window-header-default-collapsed-bottom-bc, +.x-window-header-default-collapsed-bottom-ml, +.x-window-header-default-collapsed-bottom-mr { + background-image: url(images/window-header/window-header-default-collapsed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-collapsed-bottom-ml, +.x-window-header-default-collapsed-bottom-mr { + background-image: url(images/window-header/window-header-default-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-collapsed-bottom-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-collapsed-left { + -webkit-border-radius: 4px; + -moz-border-radius: 4px; + -ms-border-radius: 4px; + -o-border-radius: 4px; + border-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-collapsed-left-mc { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-collapsed-left-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-collapsed-left-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-collapsed-left-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-collapsed-left-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-collapsed-left-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-collapsed-left-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-collapsed-left-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-collapsed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-collapsed-left-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-collapsed-left-tr, +.x-window-header-default-collapsed-left-br, +.x-window-header-default-collapsed-left-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-collapsed-left-tl, +.x-window-header-default-collapsed-left-bl, +.x-window-header-default-collapsed-left-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-collapsed-left-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-collapsed-left-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-collapsed-left-tl, +.x-window-header-default-collapsed-left-bl, +.x-window-header-default-collapsed-left-tr, +.x-window-header-default-collapsed-left-br, +.x-window-header-default-collapsed-left-tc, +.x-window-header-default-collapsed-left-bc, +.x-window-header-default-collapsed-left-ml, +.x-window-header-default-collapsed-left-mr { + background-image: url(images/window-header/window-header-default-collapsed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-collapsed-left-ml, +.x-window-header-default-collapsed-left-mr { + background-image: url(images/window-header/window-header-default-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-collapsed-left-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:857 */ +.x-window-header-default .x-window-header-icon { + width: 16px; + height: 16px; + color: #fff; + font-size: 16px; + line-height: 16px; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:866 */ +.x-window-header-default .x-window-header-glyph { + color: #fff; + font-size: 16px; + line-height: 16px; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:883 */ +.x-ie8 .x-window-header-default .x-window-header-glyph { + color: #9cc9e9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:892 */ +.x-window-header-default-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:902 */ +.x-window-header-default-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:914 */ +.x-window-header-default-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:924 */ +.x-window-header-default-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:937 */ +.x-keyboard-mode .x-window-header-default .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus, +.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:951 */ +.x-window-header-default { + border-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:961 */ +.x-nbr .x-window-default-collapsed .x-window-header { + border-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:972 */ +.x-window-default-resizable { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:977 */ +.x-window-default-resizable .x-window-handle-north-br { + top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:980 */ +.x-window-default-resizable .x-window-handle-south-br { + bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:983 */ +.x-window-default-resizable .x-window-handle-east-br { + right: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:986 */ +.x-window-default-resizable .x-window-handle-west-br { + left: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:989 */ +.x-window-default-resizable .x-window-handle-northwest-br { + left: -5px; + top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:993 */ +.x-window-default-resizable .x-window-handle-northeast-br { + right: -5px; + top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:997 */ +.x-window-default-resizable .x-window-handle-southeast-br { + right: -5px; + bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:1001 */ +.x-window-default-resizable .x-window-handle-southwest-br { + left: -5px; + bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-window-default-outer-border-l { + border-left-color: #3892d4 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-window-default-outer-border-b { + border-bottom-color: #3892d4 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-window-default-outer-border-bl { + border-bottom-color: #3892d4 !important; + border-bottom-width: 1px !important; + border-left-color: #3892d4 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-window-default-outer-border-r { + border-right-color: #3892d4 !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-window-default-outer-border-rl { + border-right-color: #3892d4 !important; + border-right-width: 1px !important; + border-left-color: #3892d4 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-window-default-outer-border-rb { + border-right-color: #3892d4 !important; + border-right-width: 1px !important; + border-bottom-color: #3892d4 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-window-default-outer-border-rbl { + border-right-color: #3892d4 !important; + border-right-width: 1px !important; + border-bottom-color: #3892d4 !important; + border-bottom-width: 1px !important; + border-left-color: #3892d4 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-window-default-outer-border-t { + border-top-color: #3892d4 !important; + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-window-default-outer-border-tl { + border-top-color: #3892d4 !important; + border-top-width: 1px !important; + border-left-color: #3892d4 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-window-default-outer-border-tb { + border-top-color: #3892d4 !important; + border-top-width: 1px !important; + border-bottom-color: #3892d4 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-window-default-outer-border-tbl { + border-top-color: #3892d4 !important; + border-top-width: 1px !important; + border-bottom-color: #3892d4 !important; + border-bottom-width: 1px !important; + border-left-color: #3892d4 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-window-default-outer-border-tr { + border-top-color: #3892d4 !important; + border-top-width: 1px !important; + border-right-color: #3892d4 !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-window-default-outer-border-trl { + border-top-color: #3892d4 !important; + border-top-width: 1px !important; + border-right-color: #3892d4 !important; + border-right-width: 1px !important; + border-left-color: #3892d4 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-window-default-outer-border-trb { + border-top-color: #3892d4 !important; + border-top-width: 1px !important; + border-right-color: #3892d4 !important; + border-right-width: 1px !important; + border-bottom-color: #3892d4 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-window-default-outer-border-trbl { + border-color: #3892d4 !important; + border-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Window.scss:11 */ +.x-window-body-plain { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:97 */ +.x-form-item-label-default { + color: #000; + font: normal 13px/17px tahoma, verdana, sans-serif; + min-height: 24px; + padding-top: 4px; + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:113 */ +.x-ie8 .x-form-item-label-default { + min-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:119 */ +.x-form-item-label-default.x-form-item-label-top { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:121 */ +.x-form-item-label-default.x-form-item-label-top > .x-form-item-label-inner { + padding-top: 4px; + padding-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:127 */ +.x-form-item-label-default.x-form-item-label-top-side-error:after { + width: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:132 */ +.x-form-item-body-default { + min-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:136 */ +.x-form-invalid-icon-default { + width: 16px; + height: 16px; + margin: 0 5px; + background: url(images/form/exclamation.png) no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:143 */ +.x-form-invalid-under-default { + padding: 2px 2px 2px 20px; + color: #cf4c35; + font: normal 13px/16px tahoma, verdana, sans-serif; + background: no-repeat 0 2px; + background-image: url(images/form/exclamation.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:151 */ +.x-form-error-wrap-default.x-form-error-wrap-side { + width: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:156 */ +.x-form-item-default.x-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/Labelable.scss:33 */ +.x-autocontainer-form-item, +.x-anchor-form-item, +.x-vbox-form-item, +.x-table-form-item { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:201 */ +.x-form-text-field-body-default { + min-width: 170px; + max-width: 170px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:221 */ +.x-form-trigger-wrap-default { + border-width: 1px; + border-style: solid; + border-color: #c2c2c2 #dadada #dadada; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:229 */ +.x-form-trigger-wrap-default.x-form-trigger-wrap-focus { + border-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:233 */ +.x-form-trigger-wrap-default.x-form-trigger-wrap-invalid { + border-color: #cf4c35; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:258 */ +.x-form-text-default { + color: #000; + padding: 3px 6px 2px; + background-color: #fff; + font: normal 13px/17px tahoma, verdana, sans-serif; + min-height: 22px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:272 */ +.x-ie8 .x-form-text-default { + min-height: 17px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:278 */ +.x-form-text-default.x-form-textarea { + line-height: 15px; + min-height: 60px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:283 */ +.x-ie8 .x-form-text-default.x-form-textarea { + min-height: 55px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:290 */ +.x-form-text-default.x-form-text-file { + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:294 */ +.x-form-text-default.x-webkit-border-box-bug { + height: calc(100% + 5px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:300 */ +.x-placeholder-label-default { + padding: 3px 6px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:304 */ +.x-form-empty-field-default + .x-placeholder-label-default { + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:309 */ +.x-form-text-default:-ms-input-placeholder { + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:313 */ +.x-form-invalid-field-default { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:324 */ +.x-form-trigger-default { + width: 22px; + background: 0 center #fff url(images/form/trigger.png) no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:347 */ +.x-form-trigger-default.x-form-trigger-over { + background-position: -22px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:353 */ +.x-form-trigger-default.x-form-trigger-over.x-form-trigger-focus { + background-position: -88px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:358 */ +.x-form-trigger-default.x-form-trigger-focus { + background-position: -66px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:367 */ +.x-form-trigger.x-form-trigger-default.x-form-trigger-click { + background-position: -44px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:376 */ +.x-textfield-default-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/Text.scss:54 */ +.x-form-clear-trigger { + background-image: url(images/form/clear-trigger.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/Text.scss:67 */ +.x-form-search-trigger { + background-image: url(images/form/search-trigger.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:1 */ +.x-message-box .x-window-body { + background-color: #fff; + border-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:10 */ +.x-message-box-info, +.x-message-box-warning, +.x-message-box-question, +.x-message-box-error { + background-position: left top; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:29 */ +.x-message-box-icon { + height: 32px; + width: 32px; + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:35 */ +.x-message-box-info { + background-image: url(images/shared/icon-info.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:44 */ +.x-message-box-warning { + background-image: url(images/shared/icon-warning.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:53 */ +.x-message-box-question { + background-image: url(images/shared/icon-question.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:62 */ +.x-message-box-error { + background-image: url(images/shared/icon-error.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:89 */ +.x-form-cb-wrap-default { + height: 24px; + min-width: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:98 */ +.x-form-cb-default { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:103 */ +.x-form-checkbox-default, +.x-form-radio-default { + width: 15px; + height: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:109 */ +.x-form-radio-default { + background: url(images/form/radio.png) no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:120 */ +.x-form-cb-checked .x-form-radio-default { + background-position: 0 -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:126 */ +.x-form-checkbox-default { + background: url(images/form/checkbox.png) no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:137 */ +.x-form-cb-checked .x-form-checkbox-default { + background-position: 0 -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:145 */ +.x-keyboard-mode .x-form-checkbox-focus.x-form-radio-default { + background-position: -15px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:154 */ +.x-keyboard-mode .x-form-checkbox-focus.x-form-checkbox-default { + background-position: -15px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:165 */ +.x-keyboard-mode .x-form-cb-checked .x-form-checkbox-focus.x-form-radio-default { + background-position: -15px -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:174 */ +.x-keyboard-mode .x-form-cb-checked .x-form-checkbox-focus.x-form-checkbox-default { + background-position: -15px -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:185 */ +.x-form-cb-label-default { + margin-top: 4px; + font: normal 13px/17px tahoma, verdana, sans-serif; + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:190 */ +.x-form-cb-label-default.x-form-cb-label-before { + padding-right: 19px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:201 */ +.x-form-cb-label-default.x-form-cb-label-after { + padding-left: 19px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:215 */ +.x-checkbox-default-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/CheckboxGroup.scss:96 */ +.x-form-item-body-default.x-form-checkboxgroup-body { + padding: 0 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/CheckboxGroup.scss:99 */ +.x-form-invalid .x-form-item-body-default.x-form-checkboxgroup-body { + border-width: 1px; + border-style: solid; + border-color: #cf4c35; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:282 */ +.x-fieldset-default { + border: 1px solid #b0b0b0; + padding: 0 10px; + margin: 0 0 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:295 */ +.x-ie8 .x-fieldset-default { + padding-top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:298 */ +.x-ie8 .x-fieldset-body-default { + padding-top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:304 */ +.x-fieldset-header-default { + padding: 0 3px 1px; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:308 */ +.x-fieldset-header-default > .x-fieldset-header-text { + font: normal 12px/16px tahoma, verdana, sans-serif; + color: #000; + padding: 1px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:315 */ +.x-fieldset-header-checkbox-default { + margin: 2px 4px 0 0; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:325 */ +.x-fieldset-header-tool-default { + margin: 2px 4px 0 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:334 */ +.x-fieldset-header-tool-default > .x-tool-img { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; + height: 15px; + width: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:341 */ +.x-fieldset-header-tool-default.x-tool-over > .x-tool-img { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=90)"; + opacity: 0.9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:347 */ +.x-fieldset-header-tool-default.x-tool-pressed > .x-tool-img { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:358 */ +.x-fieldset-header-tool-default > .x-tool-toggle { + background-image: url(images/fieldset/collapse-tool.png); + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:365 */ +.x-fieldset-header-tool-default.x-tool-over > .x-tool-toggle { + background-position: 0 -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:373 */ +.x-keyboard-mode .x-fieldset-header-tool-default.x-focus { + outline: 1px solid #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:380 */ +.x-fieldset-default.x-fieldset-collapsed { + border-width: 1px 1px 0 1px; + border-left-color: transparent; + border-right-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:393 */ +.x-fieldset-default.x-fieldset-collapsed .x-tool-toggle { + background-position: -15px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:397 */ +.x-fieldset-default.x-fieldset-collapsed .x-tool-over > .x-tool-toggle { + background-position: -15px -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:71 */ +.x-form-trigger-spinner-default { + width: 22px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:85 */ +.x-form-spinner-default { + background-image: url(images/form/spinner.png); + background-color: #fff; + width: 22px; + height: 11px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:143 */ +.x-form-spinner-up-default { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:146 */ +.x-form-spinner-up-default.x-form-spinner-over { + background-position: -22px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:148 */ +.x-form-spinner-up-default.x-form-spinner-over.x-form-spinner-focus { + background-position: -88px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:153 */ +.x-form-spinner-up-default.x-form-spinner-focus { + background-position: -66px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:158 */ +.x-form-spinner-up-default.x-form-spinner.x-form-spinner-click { + background-position: -44px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:163 */ +.x-form-spinner-down-default { + background-position: 0 -11px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:166 */ +.x-form-spinner-down-default.x-form-spinner-over { + background-position: -22px -11px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:168 */ +.x-form-spinner-down-default.x-form-spinner-over.x-form-spinner-focus { + background-position: -88px -11px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:173 */ +.x-form-spinner-down-default.x-form-spinner-focus { + background-position: -66px -11px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:178 */ +.x-form-spinner-down-default.x-form-spinner.x-form-spinner-click { + background-position: -44px -11px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:1 */ +.x-tbar-page-number { + width: 30px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:10 */ +.x-btn-icon-el.x-tbar-page-first { + background-image: url(images/grid/page-first.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:19 */ +.x-btn-icon-el.x-tbar-page-prev { + background-image: url(images/grid/page-prev.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:28 */ +.x-btn-icon-el.x-tbar-page-next { + background-image: url(images/grid/page-next.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:37 */ +.x-btn-icon-el.x-tbar-page-last { + background-image: url(images/grid/page-last.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:46 */ +.x-btn-icon-el.x-tbar-loading { + background-image: url(images/grid/refresh.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:1 */ +.x-boundlist { + border-width: 1px; + border-style: solid; + border-color: #e1e1e1; + background: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:8 */ +.x-boundlist-item { + padding: 0 6px; + font: normal 13px tahoma, verdana, sans-serif; + line-height: 22px; + cursor: pointer; + cursor: hand; + position: relative; + /*allow hover in IE on empty items*/ + border-width: 1px; + border-style: dotted; + border-color: #fff; + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:25 */ +.x-boundlist-selected { + background: #c2ddf2; + border-color: #c2ddf2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:33 */ +.x-boundlist-item-over { + background: #d6e9f6; + border-color: #d6e9f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:42 */ +.x-boundlist-floating { + border-top-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:46 */ +.x-boundlist-above { + border-top-width: 1px; + border-bottom-width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:9 */ +.x-datepicker { + border-width: 1px; + border-style: solid; + border-color: #e1e1e1; + background-color: #fff; + width: 212px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:19 */ +.x-datepicker-header { + padding: 4px 6px; + text-align: center; + background-color: #f5f5f5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:29 */ +.x-datepicker-arrow { + width: 12px; + height: 12px; + top: 9px; + cursor: pointer; + -webkit-touch-callout: none; + background-color: #f5f5f5; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:51 */ +div.x-datepicker-arrow:hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:56 */ +.x-datepicker-next { + right: 6px; + background: url(images/datepicker/arrow-right.png) no-repeat 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:65 */ +.x-datepicker-prev { + left: 6px; + background: url(images/datepicker/arrow-left.png) no-repeat 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:74 */ +.x-datepicker-month { + background: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:77 */ +.x-datepicker-month .x-btn, +.x-datepicker-month .x-btn .x-btn-tc, +.x-datepicker-month .x-btn .x-btn-tl, +.x-datepicker-month .x-btn .x-btn-tr, +.x-datepicker-month .x-btn .x-btn-mc, +.x-datepicker-month .x-btn .x-btn-ml, +.x-datepicker-month .x-btn .x-btn-mr, +.x-datepicker-month .x-btn .x-btn-bc, +.x-datepicker-month .x-btn .x-btn-bl, +.x-datepicker-month .x-btn .x-btn-br { + background: transparent; + border-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:93 */ +.x-datepicker-month .x-btn-inner { + color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:98 */ +.x-datepicker-month .x-btn-split-right:after, +.x-datepicker-month .x-btn-over .x-btn-split-right:after { + background-image: url(images/datepicker/month-arrow.png); + padding: 0; + text-align: right; + width: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:111 */ +.x-datepicker-month .x-btn { + padding: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:115 */ +.x-datepicker-month .x-btn-over { + border-color: transparent; + background: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:120 */ +.x-datepicker-month .x-btn.x-btn-pressed { + border-color: transparent; + background: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:125 */ +.x-datepicker-month .x-btn-inner { + font-size: 12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:130 */ +.x-datepicker-column-header { + width: 30px; + color: #000; + font: bold 13px tahoma, verdana, sans-serif; + text-align: right; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:149 */ +.x-datepicker-column-header-inner { + line-height: 25px; + padding: 0 9px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:154 */ +.x-datepicker-cell { + text-align: right; + border: 1px solid #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:163 */ +.x-datepicker-date { + padding: 0 7px 0 0; + font: normal 13px tahoma, verdana, sans-serif; + color: #000; + cursor: pointer; + line-height: 23px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:173 */ +div.x-datepicker-date:hover { + color: #000; + background-color: #ebf4fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:178 */ +.x-datepicker-selected { + border-style: solid; + border-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:181 */ +.x-datepicker-selected div.x-datepicker-date { + background-color: #d6e9f6; + color: #000; + font-weight: bold; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:188 */ +.x-datepicker-today { + border-color: darkred; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:199 */ +.x-datepicker-prevday .x-datepicker-date, +.x-datepicker-nextday .x-datepicker-date { + color: #bfbfbf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:206 */ +.x-datepicker-disabled .x-datepicker-date { + background-color: #eee; + cursor: default; + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:214 */ +.x-datepicker-disabled div.x-datepicker-date:hover { + background-color: #eee; + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:219 */ +.x-datepicker-footer, +.x-monthpicker-buttons { + padding: 3px 0; + background-color: #f5f5f5; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:236 */ +.x-datepicker-footer .x-btn, +.x-monthpicker-buttons .x-btn { + margin: 0 3px 0 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:242 */ +.x-monthpicker { + width: 212px; + border-width: 1px; + border-style: solid; + border-color: #e1e1e1; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:252 */ +.x-monthpicker-months { + border-width: 0 1px 0 0; + border-color: #e1e1e1; + border-style: solid; + width: 105px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:261 */ +.x-monthpicker-months .x-monthpicker-item { + width: 52px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:266 */ +.x-monthpicker-years { + width: 105px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:269 */ +.x-monthpicker-years .x-monthpicker-item { + width: 52px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:274 */ +.x-monthpicker-item { + margin: 5px 0 5px; + font: normal 13px tahoma, verdana, sans-serif; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:280 */ +.x-monthpicker-item-inner { + margin: 0 5px 0 5px; + color: #000; + border: 1px solid #fff; + line-height: 22px; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:295 */ +a.x-monthpicker-item-inner:hover { + color: #000; + background-color: #ebf4fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:301 */ +.x-monthpicker-item a.x-monthpicker-selected { + background-color: #d6e9f6; + color: #000; + border-style: solid; + border-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:308 */ +.x-monthpicker-yearnav { + height: 34px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:312 */ +.x-monthpicker-yearnav-button-ct { + width: 52px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:316 */ +.x-monthpicker-yearnav-button { + height: 12px; + width: 12px; + cursor: pointer; + margin-top: 11px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; + -webkit-touch-callout: none; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:337 */ +a.x-monthpicker-yearnav-button:hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:342 */ +.x-monthpicker-yearnav-next { + background: url(images/datepicker/arrow-right.png) no-repeat 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:351 */ +.x-monthpicker-yearnav-next-over { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:356 */ +.x-monthpicker-yearnav-prev { + background: url(images/datepicker/arrow-left.png) no-repeat 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:365 */ +.x-monthpicker-yearnav-prev-over { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:371 */ +.x-monthpicker-small .x-monthpicker-item { + margin: 2px 0 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:375 */ +.x-monthpicker-small .x-monthpicker-item-inner { + margin: 0 5px 0 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:379 */ +.x-monthpicker-small .x-monthpicker-yearnav { + height: 28px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:383 */ +.x-monthpicker-small .x-monthpicker-yearnav-button { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/Date.scss:2 */ +.x-form-field-date .x-form-date-trigger { + background-image: url(images/form/date-trigger.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Display.scss:52 */ +.x-form-display-field-default { + min-height: 24px; + font: normal 13px/17px tahoma, verdana, sans-serif; + color: #000; + margin-top: 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Display.scss:60 */ +.x-keyboard-mode .x-form-display-field-default.x-field-form-focus { + outline: 1px solid #3892d4; + outline-offset: -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus, +.x-ie10p .x-keyboard-mode .x-form-display-field-default.x-field-form-focus, +.x-edge .x-keyboard-mode .x-form-display-field-default.x-field-form-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after, +.x-ie10p .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after, +.x-edge .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after { + position: absolute; + content: ' '; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + border: 1px solid #3892d4; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Display.scss:71 */ +.x-ie8 .x-form-display-field-default.x-field-form-focus { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tip-default { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 2px 2px 2px 2px; + border-width: 1px; + border-style: solid; + background-color: #ebf4fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tip-default-mc { + background-color: #ebf4fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tip-default { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tip-default-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-2-2-2-2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tip-default-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tip-default-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tip-default-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tip-default-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tip-default-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tip-default-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tip-default-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tip-default-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tip-default-tr, +.x-tip-default-br, +.x-tip-default-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tip-default-tl, +.x-tip-default-bl, +.x-tip-default-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tip-default-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tip-default-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-tip-default-tl, +.x-tip-default-bl, +.x-tip-default-tr, +.x-tip-default-br, +.x-tip-default-tc, +.x-tip-default-bc, +.x-tip-default-ml, +.x-tip-default-mr { + background-image: url(images/tip/tip-default-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-tip-default-ml, +.x-tip-default-mr { + background-image: url(images/tip/tip-default-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tip-default-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:318 */ +.x-tip-default { + background-color: #ebf4fb; + border-color: #e1e1e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:328 */ +.x-tip-default .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #ebf4fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:343 */ +.x-tip-header-default .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:353 */ +.x-tip-header-default .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:364 */ +.x-tip-header-default { + padding: 3px 3px 0 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:368 */ +.x-tip-header-title-default { + color: #000; + font-size: 13px; + font-weight: bold; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:374 */ +.x-tip-body-default { + padding: 3px; + color: #000; + font-size: 13px; + font-weight: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:379 */ +.x-tip-body-default a { + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:390 */ +.x-tip-default .x-tip-anchor { + border: 6px solid transparent; + _border-color: pink; + _filter: chroma(color=pink); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:404 */ +.x-tip-default .x-tip-anchor:after { + position: absolute; + border: 6px solid transparent; + content: ""; + _border-color: pink; + _filter: chroma(color=pink); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:415 */ +.x-tip-default .x-tip-anchor-top { + border-top-width: 0; + border-bottom: 6px solid #d4d4d4; + top: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:421 */ +.x-tip-default .x-tip-anchor-bottom { + border-bottom-width: 0; + border-top: 6px solid #d4d4d4; + bottom: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:427 */ +.x-tip-default .x-tip-anchor-left { + border-left-width: 0; + border-right: 6px solid #d4d4d4; + left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:433 */ +.x-tip-default .x-tip-anchor-right { + border-right-width: 0; + border-left: 6px solid #d4d4d4; + right: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:439 */ +.x-tip-default .x-tip-anchor-top:after { + border-top-width: 0; + border-bottom: 6px solid #ebf4fb; + top: 1px; + margin-left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:446 */ +.x-tip-default .x-tip-anchor-bottom:after { + border-bottom-width: 0; + border-top: 6px solid #ebf4fb; + bottom: 1px; + margin-left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:453 */ +.x-tip-default .x-tip-anchor-left:after { + border-left-width: 0; + border-right: 6px solid #ebf4fb; + left: 1px; + margin-top: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:460 */ +.x-tip-default .x-tip-anchor-right:after { + border-right-width: 0; + border-left: 6px solid #ebf4fb; + right: 1px; + margin-top: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tip-form-invalid { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 2px 2px 2px 2px; + border-width: 1px; + border-style: solid; + background-color: #ebf4fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tip-form-invalid-mc { + background-color: #ebf4fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tip-form-invalid { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tip-form-invalid-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-2-2-2-2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tip-form-invalid-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tip-form-invalid-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tip-form-invalid-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tip-form-invalid-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tip-form-invalid-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tip-form-invalid-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tip-form-invalid-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tip-form-invalid-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tip-form-invalid-tr, +.x-tip-form-invalid-br, +.x-tip-form-invalid-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tip-form-invalid-tl, +.x-tip-form-invalid-bl, +.x-tip-form-invalid-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tip-form-invalid-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tip-form-invalid-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-tip-form-invalid-tl, +.x-tip-form-invalid-bl, +.x-tip-form-invalid-tr, +.x-tip-form-invalid-br, +.x-tip-form-invalid-tc, +.x-tip-form-invalid-bc, +.x-tip-form-invalid-ml, +.x-tip-form-invalid-mr { + background-image: url(images/tip/tip-form-invalid-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-tip-form-invalid-ml, +.x-tip-form-invalid-mr { + background-image: url(images/tip/tip-form-invalid-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tip-form-invalid-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:318 */ +.x-tip-form-invalid { + background-color: #ebf4fb; + border-color: #e1e1e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:328 */ +.x-tip-form-invalid .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #ebf4fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:343 */ +.x-tip-header-form-invalid .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:353 */ +.x-tip-header-form-invalid .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:364 */ +.x-tip-header-form-invalid { + padding: 3px 3px 0 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:368 */ +.x-tip-header-title-form-invalid { + color: #000; + font-size: 13px; + font-weight: bold; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:374 */ +.x-tip-body-form-invalid { + padding: 3px 3px 3px 22px; + color: #000; + font-size: 13px; + font-weight: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:379 */ +.x-tip-body-form-invalid a { + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:390 */ +.x-tip-form-invalid .x-tip-anchor { + border: 6px solid transparent; + _border-color: pink; + _filter: chroma(color=pink); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:404 */ +.x-tip-form-invalid .x-tip-anchor:after { + position: absolute; + border: 6px solid transparent; + content: ""; + _border-color: pink; + _filter: chroma(color=pink); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:415 */ +.x-tip-form-invalid .x-tip-anchor-top { + border-top-width: 0; + border-bottom: 6px solid #d4d4d4; + top: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:421 */ +.x-tip-form-invalid .x-tip-anchor-bottom { + border-bottom-width: 0; + border-top: 6px solid #d4d4d4; + bottom: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:427 */ +.x-tip-form-invalid .x-tip-anchor-left { + border-left-width: 0; + border-right: 6px solid #d4d4d4; + left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:433 */ +.x-tip-form-invalid .x-tip-anchor-right { + border-right-width: 0; + border-left: 6px solid #d4d4d4; + right: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:439 */ +.x-tip-form-invalid .x-tip-anchor-top:after { + border-top-width: 0; + border-bottom: 6px solid #ebf4fb; + top: 1px; + margin-left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:446 */ +.x-tip-form-invalid .x-tip-anchor-bottom:after { + border-bottom-width: 0; + border-top: 6px solid #ebf4fb; + bottom: 1px; + margin-left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:453 */ +.x-tip-form-invalid .x-tip-anchor-left:after { + border-left-width: 0; + border-right: 6px solid #ebf4fb; + left: 1px; + margin-top: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:460 */ +.x-tip-form-invalid .x-tip-anchor-right:after { + border-right-width: 0; + border-left: 6px solid #ebf4fb; + right: 1px; + margin-top: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tip/Tip.scss:25 */ +.x-tip-body-form-invalid { + background: 1px 1px no-repeat; + background-image: url(images/form/exclamation.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tip/Tip.scss:28 */ +.x-tip-body-form-invalid li { + margin-bottom: 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tip/Tip.scss:30 */ +.x-tip-body-form-invalid li.last { + margin-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:1 */ +.x-color-picker { + width: 192px; + height: 120px; + background-color: #fff; + border-color: #fff; + border-width: 0; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:10 */ +.x-color-picker-item { + width: 24px; + height: 24px; + border-width: 1px; + border-color: #fff; + border-style: solid; + background-color: #fff; + cursor: pointer; + padding: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:22 */ +a.x-color-picker-item:hover { + border-color: #8bb8f3; + background-color: #e6e6e6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:27 */ +.x-color-picker-selected { + border-color: #8bb8f3; + background-color: #e6e6e6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:32 */ +.x-color-picker-item-inner { + line-height: 16px; + border-color: #e1e1e1; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:7 */ +.x-html-editor-tb .x-edit-bold, +.x-menu-item div.x-edit-bold { + background-position: 0 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:18 */ +.x-html-editor-tb .x-edit-italic, +.x-menu-item div.x-edit-italic { + background-position: -16px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:29 */ +.x-html-editor-tb .x-edit-underline, +.x-menu-item div.x-edit-underline { + background-position: -32px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:40 */ +.x-html-editor-tb .x-edit-forecolor, +.x-menu-item div.x-edit-forecolor { + background-position: -160px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:51 */ +.x-html-editor-tb .x-edit-backcolor, +.x-menu-item div.x-edit-backcolor { + background-position: -176px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:62 */ +.x-html-editor-tb .x-edit-justifyleft, +.x-menu-item div.x-edit-justifyleft { + background-position: -112px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:73 */ +.x-html-editor-tb .x-edit-justifycenter, +.x-menu-item div.x-edit-justifycenter { + background-position: -128px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:84 */ +.x-html-editor-tb .x-edit-justifyright, +.x-menu-item div.x-edit-justifyright { + background-position: -144px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:95 */ +.x-html-editor-tb .x-edit-insertorderedlist, +.x-menu-item div.x-edit-insertorderedlist { + background-position: -80px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:106 */ +.x-html-editor-tb .x-edit-insertunorderedlist, +.x-menu-item div.x-edit-insertunorderedlist { + background-position: -96px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:117 */ +.x-html-editor-tb .x-edit-increasefontsize, +.x-menu-item div.x-edit-increasefontsize { + background-position: -48px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:128 */ +.x-html-editor-tb .x-edit-decreasefontsize, +.x-menu-item div.x-edit-decreasefontsize { + background-position: -64px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:139 */ +.x-html-editor-tb .x-edit-sourceedit, +.x-menu-item div.x-edit-sourceedit { + background-position: -192px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:150 */ +.x-html-editor-tb .x-edit-createlink, +.x-menu-item div.x-edit-createlink { + background-position: -208px 0; + background-image: url(images/editor/tb-sprite.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:161 */ +.x-html-editor-tip .x-tip-bd .x-tip-bd-inner { + padding: 5px; + padding-bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:166 */ +.x-html-editor-tb .x-font-select { + font-size: 13px; + font-family: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:171 */ +.x-html-editor-wrap textarea { + font: normal 13px tahoma, verdana, sans-serif; + background-color: #fff; + resize: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:177 */ +.x-htmleditor-iframe { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:320 */ +.x-form-text-default.x-tagfield { + padding: 2px 0 0 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:324 */ +.x-form-text-default .x-tagfield-input { + margin: 0 4px 2px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:328 */ +.x-form-text-default .x-tagfield-input-field { + height: 18px; + line-height: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:333 */ +.x-form-text-default .x-tagfield-item { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + background-color: #e6e6e6; + border: 1px solid #e6e6e6; + padding: 0 19px 0 5px; + margin: 0 4px 2px 0; + color: #000; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:344 */ +.x-form-text-default .x-tagfield-item:hover { + background-color: #dadada; + border-color: #dadada; + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:352 */ +.x-form-text-default .x-tagfield-item.x-tagfield-item-selected { + background-color: #3892d4; + border-color: #3892d4; + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:367 */ +.x-form-text-default .x-tagfield-item-close { + width: 12px; + height: 12px; + top: 1px; + right: 1px; + background-image: url(images/form/tag-field-item-close.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:384 */ +.x-form-text-default .x-tagfield-item-close:hover { + background-position: -12px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:395 */ +.x-form-text-default .x-tagfield-item-close:active { + background-position: -24px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:412 */ +.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:422 */ +.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close:hover { + background-position: -12px -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:426 */ +.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close:active { + background-position: -24px -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:5 */ +.x-grid-view, +.x-tree-view { + z-index: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:11 */ +.x-theme-row-height-el { + height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:15 */ +.x-grid-body { + background: #fff; + border-width: 1px; + border-style: solid; + border-color: #c2c2c2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:22 */ +.x-grid-empty { + padding: 10px; + color: grey; + background-color: #fff; + font: normal 13px tahoma, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:30 */ +.x-grid-item { + color: #000; + font: normal 13px/15px tahoma, verdana, sans-serif; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:36 */ +.x-grid-item-alt { + background-color: #fafafa; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:40 */ +.x-grid-item-over { + color: #000; + background-color: #e2eff9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:47 */ +.x-grid-item-focused { + outline: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:51 */ +.x-grid-item-focused .x-grid-cell-inner { + z-index: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:57 */ +.x-keyboard-mode .x-grid-item-focused { + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:60 */ +.x-keyboard-mode .x-grid-item-focused .x-grid-cell-inner:before { + content: ""; + position: absolute; + z-index: -1; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + pointer-events: none; + border: 1px solid #3d92cf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:83 */ +.x-grid-item-selected { + color: #000; + background-color: #c2ddf2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:89 */ +.x-grid-with-row-lines .x-grid-item { + border-style: solid; + border-width: 1px 0 0; + border-color: #ededed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:95 */ +.x-grid-with-row-lines .x-grid-item:first-child { + border-top-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:101 */ +.x-grid-with-row-lines .x-grid-item.x-grid-item-over { + border-style: solid; + border-color: #e2eff9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:106 */ +.x-grid-with-row-lines .x-grid-item-over + .x-grid-item { + border-top-style: solid; + border-top-color: #e2eff9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:111 */ +.x-grid-with-row-lines .x-grid-item.x-grid-item-selected { + border-style: solid; + border-color: #c2ddf2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:116 */ +.x-grid-with-row-lines .x-grid-item-selected + .x-grid-item { + border-top-style: solid; + border-top-color: #c2ddf2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:121 */ +.x-grid-with-row-lines .x-grid-item:last-child { + border-bottom-width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:131 */ +.x-ie8 .x-grid-with-row-lines .x-grid-item { + border-width: 1px 0; + margin-top: -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:136 */ +.x-ie8 .x-grid-with-row-lines .x-grid-item:first-child { + margin-top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:142 */ +.x-grid-cell-inner { + position: relative; + text-overflow: ellipsis; + padding: 5px 10px 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:158 */ +.x-grid-cell-special { + border-color: #ededed; + border-style: solid; + border-right-width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:208 */ +.x-grid-dirty-cell { + background: url(images/grid/dirty.png) no-repeat 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:238 */ +.x-grid-row .x-grid-cell-selected { + color: #000; + background-color: #c2ddf2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:245 */ +.x-grid-with-col-lines .x-grid-cell { + border-style: solid; + border-color: #ededed; + border-width: 0 1px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:251 */ +.x-grid-with-col-lines .x-grid-item-over .x-grid-cell { + border-color: #e2eff9; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:256 */ +.x-grid-with-col-lines .x-grid-item-selected .x-grid-cell { + border-color: #c2ddf2; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:269 */ +.x-grid-resize-marker { + width: 1px; + background-color: #0f0f0f; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/DropZone.scss:1 */ +.x-grid-drop-indicator { + position: absolute; + height: 1px; + line-height: 0px; + background-color: #77bc71; + overflow: visible; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/DropZone.scss:9 */ +.x-grid-drop-indicator .x-grid-drop-indicator-left { + position: absolute; + top: -8px; + left: -12px; + background-image: url(images/grid/dd-insert-arrow-right.png); + height: 16px; + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/DropZone.scss:18 */ +.x-grid-drop-indicator .x-grid-drop-indicator-right { + position: absolute; + top: -8px; + right: -11px; + background-image: url(images/grid/dd-insert-arrow-left.png); + height: 16px; + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/DropZone.scss:1 */ +.x-col-move-top, +.x-col-move-bottom { + width: 9px; + height: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/DropZone.scss:7 */ +.x-col-move-top { + background-image: url(images/grid/col-move-top.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/DropZone.scss:11 */ +.x-col-move-bottom { + background-image: url(images/grid/col-move-bottom.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:1 */ +.x-grid-header-ct { + border: 1px solid #c2c2c2; + border-bottom-color: #f5f5f5; + background-color: #f5f5f5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:14 */ +.x-accordion-item .x-grid-header-ct { + border-width: 0 0 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:21 */ +.x-grid-header-ct-hidden { + border-top: 0 !important; + border-bottom: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:31 */ +.x-grid-body { + border-top-color: #c2c2c2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:35 */ +.x-hmenu-sort-asc { + background-image: url(images/grid/hmenu-asc.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:46 */ +.x-hmenu-sort-desc { + background-image: url(images/grid/hmenu-desc.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:57 */ +.x-cols-icon { + background-image: url(images/grid/columns.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:1 */ +.x-column-header { + border-right: 1px solid #c2c2c2; + color: #666; + font: bold 13px/15px tahoma, verdana, sans-serif; + outline: 0; + background-color: #f5f5f5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:27 */ +.x-group-sub-header { + background: transparent; + border-top: 1px solid #c2c2c2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:32 */ +.x-group-sub-header .x-column-header-inner { + padding: 6px 10px 7px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:37 */ +.x-column-header-inner { + padding: 7px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:41 */ +.x-column-header-inner-empty { + text-overflow: clip; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:50 */ +.x-keyboard-mode .x-column-header.x-column-header-focus { + color: #666; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:51 */ +.x-keyboard-mode .x-column-header.x-column-header-focus .x-column-header-inner:after { + content: ""; + position: absolute; + z-index: 5; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + border: 1px solid #4297d4; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:65 */ +.x-keyboard-mode .x-column-header.x-column-header-focus.x-group-sub-header .x-column-header-inner:before { + bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:79 */ +.x-column-header-over { + background-image: none; + background-color: #eff6fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:83 */ +.x-column-header-sort-ASC, +.x-column-header-sort-DESC { + background-image: none; + background-color: #eff6fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:111 */ +.x-column-header-open { + background-color: #eff6fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:114 */ +.x-column-header-open .x-column-header-trigger { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:119 */ +.x-column-header-over .x-column-header-trigger, +.x-column-header-open .x-column-header-trigger { + width: 18px; + cursor: pointer; + background: transparent url(images/grid/hd-pop.png) no-repeat center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:151 */ +.x-column-header-align-right .x-column-header-text { + margin-right: 12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:165 */ +.x-column-header-sort-ASC .x-column-header-text-inner, +.x-column-header-sort-DESC .x-column-header-text-inner { + padding-right: 17px; + background-position: right center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:198 */ +.x-column-header-sort-ASC .x-column-header-text-inner { + background-image: url(images/grid/sort_asc.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:210 */ +.x-column-header-sort-DESC .x-column-header-text-inner { + background-image: url(images/grid/sort_desc.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:224 */ +.x-no-header-borders .x-column-header { + border: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:227 */ +.x-no-header-borders .x-column-header .x-column-header-inner { + padding-top: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Action.scss:1 */ +.x-grid-cell-inner-action-col { + padding: 4px 4px 4px 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Action.scss:14 */ +.x-action-col-cell .x-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Action.scss:18 */ +.x-action-col-icon { + color: #b0b0b0; + font-size: 16px; + height: 16px; + width: 16px; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:2 */ +.x-column-header-checkbox .x-column-header-inner, +.x-grid-checkcolumn-cell-inner { + padding: 5px 4px 4px 4px; + text-overflow: clip; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:20 */ +.x-column-header-checkbox { + border-color: #f5f5f5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:22 */ +.x-column-header-checkbox .x-column-header-text { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:34 */ +.x-column-header-checkbox .x-column-header-checkbox:after, +.x-grid-checkcolumn:after { + content: " "; + height: 15px; + width: 15px; + background-image: url(images/form/checkbox.png); + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:42 */ +.x-item-disabled .x-column-header-checkbox .x-column-header-checkbox, +.x-item-disabled .x-grid-checkcolumn { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:53 */ +.x-grid-hd-checker-on .x-column-header-checkbox:after, +.x-grid-checkcolumn-checked:after { + background-position: 0 -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:72 */ +.x-grid-item-selected .x-selmodel-column .x-grid-checkcolumn:after { + background-position: 0 -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:79 */ +.x-gecko .x-selmodel-checkbox .x-grid-checkcolumn { + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/RowNumberer.scss:1 */ +.x-grid-cell-row-numberer { + background-color: #f5f5f5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/RowNumberer.scss:10 */ +.x-grid-cell-inner-row-numberer { + padding: 5px 5px 4px 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-grid-cell-small { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-grid-cell-small-mc { + background-image: url(images/btn/btn-grid-cell-small-fbg.gif); + background-position: 0 top; + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-grid-cell-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-grid-cell-small-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-grid-cell-small-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-grid-cell-small-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-grid-cell-small-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-grid-cell-small-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-grid-cell-small-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-grid-cell-small-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-grid-cell-small-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-grid-cell-small-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-grid-cell-small-tr, +.x-btn-grid-cell-small-br, +.x-btn-grid-cell-small-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-grid-cell-small-tl, +.x-btn-grid-cell-small-bl, +.x-btn-grid-cell-small-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-grid-cell-small-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-grid-cell-small-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-grid-cell-small-tl, +.x-btn-grid-cell-small-bl, +.x-btn-grid-cell-small-tr, +.x-btn-grid-cell-small-br, +.x-btn-grid-cell-small-tc, +.x-btn-grid-cell-small-bc, +.x-btn-grid-cell-small-ml, +.x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-grid-cell-small-ml, +.x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-grid-cell-small-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-grid-cell-small { + border-color: #126daf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-grid-cell-small { + min-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-grid-cell-small { + min-height: auto; + height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-grid-cell-small { + font: bold 12px/16px tahoma, verdana, sans-serif; + color: #fff; + padding: 0 5px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-grid-cell-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-grid-cell-small { + max-width: calc(100% - 16px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-grid-cell-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-grid-cell-small { + max-width: calc(100% - 15px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-grid-cell-small { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-grid-cell-small { + font-size: 16px; + height: 16px; + color: #fff; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-grid-cell-small, +.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-grid-cell-small, +.x-btn-icon-bottom > .x-btn-icon-el-grid-cell-small { + min-width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-grid-cell-small.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-grid-cell-small.x-btn-glyph { + color: #9cc9e9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-grid-cell-small { + margin-right: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + margin-left: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-grid-cell-small { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-grid-cell-small { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-grid-cell-small { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-grid-cell-small, +.x-btn-split-bottom > .x-btn-button-grid-cell-small { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-grid-cell-small.x-btn-arrow-right:after { + width: 8px; + background-image: url(images/button/grid-cell-small-arrow.png); + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-grid-cell-small.x-btn-arrow-bottom:after { + height: 8px; + background-image: url(images/button/grid-cell-small-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-grid-cell-small.x-btn-split-right:after { + width: 14px; + background-image: url(images/button/grid-cell-small-s-arrow.png); + padding-right: 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-grid-cell-small.x-btn-split-bottom:after { + height: 14px; + background-image: url(images/button/grid-cell-small-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-grid-cell-small { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-grid-cell-small { + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-grid-cell-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 17px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-grid-cell-small { + border-color: #1164a1; + background-image: none; + background-color: #3487c3; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4893c9), color-stop(50%, #3487c3), color-stop(51%, #3180b9), color-stop(0%, #3487c3)); + background-image: -webkit-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -moz-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -o-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: -ms-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); + background-image: linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-grid-cell-small, +.x-btn.x-btn-pressed.x-btn-grid-cell-small { + border-color: #0e5284; + background-image: none; + background-color: #2a6e9f; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #2a6e9f), color-stop(50%, #286897), color-stop(51%, #2a6e9f), color-stop(0%, #3f7ca8)); + background-image: -webkit-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -moz-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -o-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: -ms-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); + background-image: linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-grid-cell-small { + background-image: none; + background-color: #3892d4; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4)); + background-image: -webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: -ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); + background-image: linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-mc { + background-color: #3892d4; + background-image: url(images/btn/btn-grid-cell-small-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-grid-cell-small-tl, +.x-btn-over .x-btn-grid-cell-small-bl, +.x-btn-over .x-btn-grid-cell-small-tr, +.x-btn-over .x-btn-grid-cell-small-br, +.x-btn-over .x-btn-grid-cell-small-tc, +.x-btn-over .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-grid-cell-small-ml, +.x-btn-over .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-grid-cell-small-mc { + background-color: #3487c3; + background-image: url(images/btn/btn-grid-cell-small-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-mc { + background-color: #3487c3; + background-image: url(images/btn/btn-grid-cell-small-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tl, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-bl, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tr, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-br, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tc, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-bc, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-tl, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-bl, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-tr, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-br, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-tc, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-ml, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-mr, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-ml, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-mc, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-mc { + background-color: #2a6e9f; + background-image: url(images/btn/btn-grid-cell-small-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-mc { + background-color: #2a6e9f; + background-image: url(images/btn/btn-grid-cell-small-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-grid-cell-small-tl, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-bl, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-tr, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-br, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-tc, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-grid-cell-small-ml, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-grid-cell-small-mc { + background-color: #3892d4; + background-image: url(images/btn/btn-grid-cell-small-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-grid-cell-small { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-grid-cell-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first .x-btn-grid-cell-small-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-middle .x-btn-grid-cell-small-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-last .x-btn-grid-cell-small-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first .x-btn-grid-cell-small-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-middle .x-btn-grid-cell-small-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-last .x-btn-grid-cell-small-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-grid-cell-small:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-grid-cell-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-grid-cell-small-cell > .x-grid-cell-inner >.x-btn-grid-cell-small { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Widget.scss:110 */ +.x-grid-widgetcolumn-cell-inner { + text-overflow: clip; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:1 */ +.x-grid-group-hd { + border-width: 0 0 1px 0; + border-style: solid; + border-color: #c2c2c2; + padding: 7px 4px; + background: #f5f5f5; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:10 */ +.x-grid-group-hd-not-collapsible { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:14 */ +.x-grid-group-hd-collapsible .x-grid-group-title { + padding: 0 0 0 17px; + background: url(images/grid/group-collapse.png) no-repeat left center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:36 */ +.x-grid-group-title { + color: #666; + font: bold 13px/15px tahoma, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:41 */ +.x-grid-group-hd-collapsed .x-grid-group-title { + background-image: url(images/grid/group-expand.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:54 */ +.x-group-by-icon { + background-image: url(images/grid/group-by.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/RowBody.scss:1 */ +.x-grid-rowbody { + font: normal 13px/15px tahoma, verdana, sans-serif; + padding: 5px 10px 5px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:1 */ +.x-docked-summary { + border-width: 1px; + border-color: #c2c2c2; + border-style: solid; + background: #fff!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:6 */ +.x-docked-summary .x-grid-table { + border: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:14 */ +.x-grid-row-summary .x-grid-cell, +.x-grid-row-summary .x-grid-rowwrap, +.x-grid-row-summary .x-grid-cell-rowbody { + border-color: #ededed; + background-color: #fff !important; + border-top: 1px solid #ededed; + font: normal 13px/15px tahoma, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:26 */ +.x-docked-summary .x-grid-item, +.x-docked-summary .x-grid-row-summary .x-grid-cell { + border-bottom: 0 none; + border-top: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:34 */ +.x-docked-summary > :first-child { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:40 */ +.x-grid-row-summary .x-grid-cell-inner-row-expander { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:818 */ +.x-menu-default { + border-style: solid; + border-width: 1px; + border-color: #e1e1e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:824 */ +.x-menu-body-default { + background: #fff; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:829 */ +.x-menu-icon-separator-default { + left: 26px; + border-left: solid 1px #e1e1e1; + background-color: #fff; + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:843 */ +.x-menu-item-default { + border-width: 0; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:849 */ +.x-menu-item-default.x-menu-item-focus, +.x-menu-item-default.x-menu-item-active { + background-image: none; + background-color: #d6e9f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:862 */ +.x-nlg .x-menu-item-default.x-menu-item-focus, +.x-nlg .x-menu-item-default.x-menu-item-active { + background: #d6e9f6 repeat-x left top; + background-image: url(images/menu/menu-item-default-active-bg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:869 */ +.x-menu-item-default.x-menu-item-disabled { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:872 */ +.x-menu-item-default.x-menu-item-disabled a { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:877 */ +.x-menu-item-default.x-menu-item-separator { + height: 1px; + border-top: solid 1px #e1e1e1; + background-color: #fff; + margin: 2px 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:885 */ +.x-menu-item-default.x-menu-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:890 */ +.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-icon-ui { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:894 */ +.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-text-default { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:904 */ +.x-menu-item-default .x-form-item-label { + font-size: 13px; + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:911 */ +.x-menu-item-text-default, +.x-menu-item-cmp-default { + margin: 0 5px 0 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:916 */ +.x-menu-item-text-default { + font: normal 13px tahoma, verdana, sans-serif; + line-height: 23px; + padding-top: 1px; + color: #000; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:934 */ +.x-menu-item-text-default.x-menu-item-indent { + margin-left: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:938 */ +.x-menu-item-text-default.x-menu-item-indent-no-separator { + margin-left: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:942 */ +.x-menu-item-text-default.x-menu-item-indent-right-icon { + margin-right: 31px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:946 */ +.x-menu-item-text-default.x-menu-item-indent-right-arrow { + margin-right: 22px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:950 */ +.x-menu-item-disabled .x-menu-item-text-default { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:982 */ +.x-menu-item-indent-default { + margin-left: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:992 */ +.x-menu-item-icon-default { + width: 16px; + height: 16px; + top: 4px; + left: 5px; + line-height: 16px; + font-size: 16px; + color: grey; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1028 */ +.x-menu-item-icon-default.x-menu-item-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1041 */ +.x-ie8 .x-menu-item-icon-default.x-menu-item-glyph { + color: silver; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1049 */ +.x-menu-item-icon-default.x-menu-item-icon-right { + width: 16px; + height: 16px; + top: 4px; + right: 5px; + left: auto; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1087 */ +.x-menu-item-checked .x-menu-item-icon-default.x-menu-item-checkbox { + background-image: url(images/menu/default-checked.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1095 */ +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-item-checkbox { + background-image: url(images/menu/default-unchecked.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1117 */ +.x-menu-item-checked .x-menu-item-icon-default.x-menu-group-icon { + background-image: url(images/menu/default-group-checked.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1125 */ +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-group-icon { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1140 */ +.x-menu-item-arrow-default { + width: 12px; + height: 9px; + top: 8px; + right: 0; + background-image: url(images/menu/default-menu-parent.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1161 */ +.x-menu-item-focus .x-menu-item-arrow-default, +.x-menu-item-active .x-menu-item-arrow-default { + top: 8px; + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-menu-default-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-menu-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-menu-default { + cursor: pointer; + color: #e1e1e1; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-menu-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-menu-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-menu-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:311 */ +.x-box-scroller-menu-default.x-box-scroller-top, +.x-box-scroller-menu-default.x-box-scroller-bottom { + height: 16px; + width: 16px; + left: 50%; + margin-left: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:338 */ +.x-box-scroller-menu-default.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + background-image: url(images/menu/default-scroll-top.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:363 */ +.x-box-scroller-menu-default.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + background-image: url(images/menu/default-scroll-bottom.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1217 */ +.x-ie8 .x-box-scroller-menu-default { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:818 */ +.x-menu-default-menubar { + border-style: solid; + border-width: 1px; + border-color: #e1e1e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:824 */ +.x-menu-body-default-menubar { + background: #fff; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:829 */ +.x-menu-icon-separator-default-menubar { + left: 26px; + border-left: solid 1px #e1e1e1; + background-color: #fff; + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:843 */ +.x-menu-item-default-menubar { + border-width: 0; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:849 */ +.x-menu-item-default-menubar.x-menu-item-focus, +.x-menu-item-default-menubar.x-menu-item-active { + background-image: none; + background-color: #d6e9f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:862 */ +.x-nlg .x-menu-item-default-menubar.x-menu-item-focus, +.x-nlg .x-menu-item-default-menubar.x-menu-item-active { + background: #d6e9f6 repeat-x left top; + background-image: url(images/menu/menu-item-default-menubar-active-bg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:869 */ +.x-menu-item-default-menubar.x-menu-item-disabled { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:872 */ +.x-menu-item-default-menubar.x-menu-item-disabled a { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:877 */ +.x-menu-item-default-menubar.x-menu-item-separator { + height: 1px; + border-top: solid 1px #e1e1e1; + background-color: #fff; + margin: 2px 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:885 */ +.x-menu-item-default-menubar.x-menu-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:890 */ +.x-ie9m .x-menu-item-default-menubar.x-menu-item-disabled .x-menu-item-icon-ui { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:894 */ +.x-ie9m .x-menu-item-default-menubar.x-menu-item-disabled .x-menu-item-text-default-menubar { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:904 */ +.x-menu-item-default-menubar .x-form-item-label { + font-size: 13px; + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:911 */ +.x-menu-item-text-default-menubar, +.x-menu-item-cmp-default-menubar { + margin: 0 5px 0 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:916 */ +.x-menu-item-text-default-menubar { + font: normal 13px tahoma, verdana, sans-serif; + line-height: 23px; + padding-top: 1px; + color: #000; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:934 */ +.x-menu-item-text-default-menubar.x-menu-item-indent { + margin-left: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:938 */ +.x-menu-item-text-default-menubar.x-menu-item-indent-no-separator { + margin-left: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:942 */ +.x-menu-item-text-default-menubar.x-menu-item-indent-right-icon { + margin-right: 31px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:946 */ +.x-menu-item-text-default-menubar.x-menu-item-indent-right-arrow { + margin-right: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:950 */ +.x-menu-item-disabled .x-menu-item-text-default-menubar { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:982 */ +.x-menu-item-indent-default-menubar { + margin-left: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:992 */ +.x-menu-item-icon-default-menubar { + width: 16px; + height: 16px; + top: 4px; + left: 5px; + line-height: 16px; + font-size: 16px; + color: grey; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1028 */ +.x-menu-item-icon-default-menubar.x-menu-item-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1041 */ +.x-ie8 .x-menu-item-icon-default-menubar.x-menu-item-glyph { + color: silver; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1049 */ +.x-menu-item-icon-default-menubar.x-menu-item-icon-right { + width: 16px; + height: 16px; + top: 4px; + right: 5px; + left: auto; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1087 */ +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + background-image: url(images/menu/default-menubar-checked.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1095 */ +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + background-image: url(images/menu/default-menubar-unchecked.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1117 */ +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-group-icon { + background-image: url(images/menu/default-menubar-group-checked.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1125 */ +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-group-icon { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1140 */ +.x-menu-item-arrow-default-menubar { + width: 9px; + height: 6px; + top: 10px; + right: 5px; + background-image: url(images/menu/default-menubar-menu-parent.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1161 */ +.x-menu-item-focus .x-menu-item-arrow-default-menubar, +.x-menu-item-active .x-menu-item-arrow-default-menubar { + top: 10px; + right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-menu-default-menubar-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-menu-default-menubar-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-menu-default-menubar { + cursor: pointer; + color: #e1e1e1; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:311 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-top, +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom { + height: 16px; + width: 16px; + left: 50%; + margin-left: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:338 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + background-image: url(images/menu/default-menubar-scroll-top.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:363 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + background-image: url(images/menu/default-menubar-scroll-bottom.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1217 */ +.x-ie8 .x-box-scroller-menu-default-menubar { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:1 */ +.x-grid-filters-filtered-column { + font-style: italic; + font-weight: bold; + text-decoration: underline; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:7 */ +.x-grid-filters-icon { + background-repeat: no-repeat; + background-position: center center; + color: grey; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:14 */ +.x-grid-filters-find { + background-image: url(images/grid/filters/find.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:24 */ +.x-grid-filters-gt { + background-image: url(images/grid/filters/greater_than.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:34 */ +.x-grid-filters-lt { + background-image: url(images/grid/filters/less_than.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:44 */ +.x-grid-filters-eq { + background-image: url(images/grid/filters/equals.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:1 */ +.x-grid-locked .x-grid-inner-locked { + border-width: 0 1px 0 0; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:12 */ +.x-grid-locked-split .x-grid-inner-normal { + border-width: 0 0 0 1px; + border-style: solid; + border-left-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:24 */ +.x-grid-locking-body { + border-width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:31 */ +.x-grid-locking-body > .x-splitter { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:35 */ +.x-grid-locking-body > .x-splitter-active { + background-color: #b4b4b4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:40 */ +.x-grid-inner-locked { + border-right-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:45 */ +.x-grid-inner-locked .x-column-header-last, +.x-grid-inner-locked .x-grid-cell-last { + border-right-width: 0!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:75 */ +.x-hmenu-lock { + background-image: url(images/grid/hmenu-lock.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:86 */ +.x-hmenu-unlock { + background-image: url(images/grid/hmenu-unlock.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:101 */ +.x-grid-scrollbar-clipper > .x-grid-view, +.x-grid-scrollbar-clipper > .x-tree-view { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:108 */ +.x-grid-scrollbar-clipper-locked, +.x-grid-scrollbar-locked { + border-width: 0 1px 0 0; + border-style: solid; + border-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:123 */ +.x-grid-scroll-container { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/Editing.scss:18 */ +.x-grid-editor .x-form-display-field { + text-overflow: ellipsis; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/Editing.scss:24 */ +.x-grid-editor .x-form-action-col-field { + padding: 4px 4px 4px 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/Editing.scss:30 */ +.x-grid-editor .x-form-text { + padding-left: 9px; + padding-right: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/CellEditing.scss:3 */ +.x-tree-cell-editor .x-form-text { + padding-left: 3px; + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:2 */ +.x-grid-row-editor .x-field { + margin: 0 3px 0 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:7 */ +.x-grid-row-editor .x-form-display-field { + padding: 5px 8px 4px 8px; + line-height: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:18 */ +.x-ie9m .x-grid-row-editor .x-form-display-field { + min-height: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:26 */ +.x-grid-row-editor .x-form-action-col-field { + padding: 4px 1px 4px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:37 */ +.x-grid-row-editor .x-form-text { + padding: 3px 6px 2px 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:41 */ +.x-gecko .x-grid-row-editor .x-form-text { + padding-left: 6px; + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:50 */ +.x-grid-row-editor .x-panel-body { + border-top: 1px solid #e1e1e1 !important; + border-bottom: 1px solid #e1e1e1 !important; + padding: 5px 0 5px 0; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:60 */ +.x-grid-with-col-lines .x-grid-row-editor .x-form-cb { + margin-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-grid-row-editor-buttons-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 5px; + -webkit-border-bottom-right-radius: 5px; + border-bottom-right-radius: 5px; + -moz-border-radius-bottomleft: 5px; + -webkit-border-bottom-left-radius: 5px; + border-bottom-left-radius: 5px; + padding: 5px 5px 5px 5px; + border-width: 0 1px 1px 1px; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-grid-row-editor-buttons-default-bottom-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-grid-row-editor-buttons-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-grid-row-editor-buttons-default-bottom-frameInfo { + font-family: th-0-5-5-5-0-1-1-1-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-grid-row-editor-buttons-default-bottom-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-grid-row-editor-buttons-default-bottom-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-grid-row-editor-buttons-default-bottom-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-grid-row-editor-buttons-default-bottom-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-grid-row-editor-buttons-default-bottom-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-grid-row-editor-buttons-default-bottom-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-grid-row-editor-buttons-default-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-grid-row-editor-buttons-default-bottom-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-grid-row-editor-buttons-default-bottom-tr, +.x-grid-row-editor-buttons-default-bottom-br, +.x-grid-row-editor-buttons-default-bottom-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-grid-row-editor-buttons-default-bottom-tl, +.x-grid-row-editor-buttons-default-bottom-bl, +.x-grid-row-editor-buttons-default-bottom-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-grid-row-editor-buttons-default-bottom-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-grid-row-editor-buttons-default-bottom-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-grid-row-editor-buttons-default-bottom-tl, +.x-grid-row-editor-buttons-default-bottom-bl, +.x-grid-row-editor-buttons-default-bottom-tr, +.x-grid-row-editor-buttons-default-bottom-br, +.x-grid-row-editor-buttons-default-bottom-tc, +.x-grid-row-editor-buttons-default-bottom-bc, +.x-grid-row-editor-buttons-default-bottom-ml, +.x-grid-row-editor-buttons-default-bottom-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-grid-row-editor-buttons-default-bottom-ml, +.x-grid-row-editor-buttons-default-bottom-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-grid-row-editor-buttons-default-bottom-mc { + padding: 5px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-grid-row-editor-buttons-default-top { + -moz-border-radius-topleft: 5px; + -webkit-border-top-left-radius: 5px; + border-top-left-radius: 5px; + -moz-border-radius-topright: 5px; + -webkit-border-top-right-radius: 5px; + border-top-right-radius: 5px; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 5px 5px 5px 5px; + border-width: 1px 1px 0 1px; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-grid-row-editor-buttons-default-top-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-grid-row-editor-buttons-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-grid-row-editor-buttons-default-top-frameInfo { + font-family: th-5-5-0-5-1-1-0-1-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-grid-row-editor-buttons-default-top-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-grid-row-editor-buttons-default-top-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-grid-row-editor-buttons-default-top-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-grid-row-editor-buttons-default-top-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-grid-row-editor-buttons-default-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-grid-row-editor-buttons-default-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-grid-row-editor-buttons-default-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-grid-row-editor-buttons-default-top-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-grid-row-editor-buttons-default-top-tr, +.x-grid-row-editor-buttons-default-top-br, +.x-grid-row-editor-buttons-default-top-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-grid-row-editor-buttons-default-top-tl, +.x-grid-row-editor-buttons-default-top-bl, +.x-grid-row-editor-buttons-default-top-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-grid-row-editor-buttons-default-top-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-grid-row-editor-buttons-default-top-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-grid-row-editor-buttons-default-top-tl, +.x-grid-row-editor-buttons-default-top-bl, +.x-grid-row-editor-buttons-default-top-tr, +.x-grid-row-editor-buttons-default-top-br, +.x-grid-row-editor-buttons-default-top-tc, +.x-grid-row-editor-buttons-default-top-bc, +.x-grid-row-editor-buttons-default-top-ml, +.x-grid-row-editor-buttons-default-top-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-grid-row-editor-buttons-default-top-ml, +.x-grid-row-editor-buttons-default-top-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-grid-row-editor-buttons-default-top-mc { + padding: 1px 1px 5px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:108 */ +.x-grid-row-editor-buttons { + border-color: #e1e1e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:112 */ +.x-row-editor-update-button { + margin-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:115 */ +.x-row-editor-cancel-button { + margin-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:131 */ +.x-grid-row-editor-errors .x-tip-body { + padding: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:136 */ +.x-grid-row-editor-errors-item { + list-style: disc; + margin-left: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowExpander.scss:1 */ +.x-grid-cell-inner-row-expander { + padding: 7px 6px 6px 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowExpander.scss:16 */ +.x-grid-row-expander { + width: 11px; + height: 11px; + cursor: pointer; + background-image: url(images/grid/group-collapse.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowExpander.scss:31 */ +.x-grid-row-collapsed .x-grid-row-expander { + background-image: url(images/grid/group-expand.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:1 */ +.x-ssm-row-numberer-hd { + cursor: se-resize!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:6 */ +.x-ssm-row-numberer-cell { + cursor: e-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:11 */ +.x-ssm-column-select .x-column-header { + cursor: s-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:16 */ +.x-ssm-extender-drag-handle { + height: 7px; + width: 7px; + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:22 */ +.x-ssm-extender-mask { + border: 1px dotted #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:1 */ +.x-accordion-layout-ct { + background-color: #fff; + padding: 5px 5px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:6 */ +.x-accordion-hd .x-panel-header-title { + color: #666; + font-weight: bold; + font-family: tahoma, verdana, sans-serif; + text-transform: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:13 */ +.x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus { + outline: 1px solid #157fcc; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus, +.x-edge .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus:after, +.x-edge .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #157fcc; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:34 */ +.x-accordion-item { + margin: 0 0 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:37 */ +.x-accordion-item .x-accordion-hd { + background: #e0ebf3; + border-width: 0; + border-color: #157fcc; + padding: 8px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:45 */ +.x-accordion-item .x-accordion-hd-over { + background-color: #e6f2fa; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:48 */ +.x-accordion-item .x-accordion-hd-over .x-tool-tool-el { + background-color: #e6f2fa; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:54 */ +.x-accordion-item .x-accordion-hd-sibling-expanded { + border-top-color: #157fcc; + border-top-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:59 */ +.x-accordion-item .x-accordion-hd-last-collapsed { + border-bottom-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:63 */ +.x-accordion-item .x-accordion-body { + border-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:72 */ +.x-accordion-hd .x-tool-tool-el { + background-color: #e0ebf3; + color: #666; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:77 */ +.x-accordion-hd .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:87 */ +.x-accordion-hd .x-tool-collapse-top, +.x-accordion-hd .x-tool-collapse-bottom { + background-position: 0 -272px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:106 */ +.x-accordion-hd .x-tool-expand-top, +.x-accordion-hd .x-tool-expand-bottom { + background-position: 0 -256px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:126 */ +.x-keyboard-mode .x-accordion-hd .x-tool-focus { + outline: 1px solid #157fcc; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus, +.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #157fcc; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Border.scss:5 */ +body.x-border-layout-ct, +div.x-border-layout-ct { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Form.scss:1 */ +.x-form-layout-wrap { + border-spacing: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:1 */ +.x-resizable-handle { + position: absolute; + z-index: 100; + font-size: 1px; + line-height: 5px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; + background-color: #c2c2c2; + -webkit-border-radius: 5px; + -moz-border-radius: 5px; + -ms-border-radius: 5px; + -o-border-radius: 5px; + border-radius: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:20 */ +.x-collapsed .x-resizable-handle { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:24 */ +.x-resizable-handle-southeast { + cursor: se-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:34 */ +.x-resizable-handle-northwest { + cursor: nw-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:44 */ +.x-resizable-handle-northeast { + cursor: ne-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:54 */ +.x-resizable-handle-southwest { + cursor: sw-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:78 */ +.x-resizable-handle-east { + cursor: e-resize; + width: 5px; + right: 0; + top: 0; + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:86 */ +.x-resizable-handle-south { + cursor: s-resize; + height: 5px; + left: 0; + right: 0; + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:94 */ +.x-resizable-handle-west { + cursor: w-resize; + width: 5px; + left: 0; + top: 0; + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:102 */ +.x-resizable-handle-north { + cursor: n-resize; + height: 5px; + left: 0; + right: 0; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:110 */ +.x-resizable-handle-southeast { + width: 5px; + height: 5px; + right: 0; + bottom: 0; + z-index: 101; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:118 */ +.x-resizable-handle-northwest { + width: 5px; + height: 5px; + left: 0; + top: 0; + z-index: 101; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:126 */ +.x-resizable-handle-northeast { + width: 5px; + height: 5px; + right: 0; + top: 0; + z-index: 101; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:134 */ +.x-resizable-handle-southwest { + width: 5px; + height: 5px; + left: 0; + bottom: 0; + z-index: 101; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:145 */ +.x-tablet .x-resizable-handle-north, +.x-tablet .x-resizable-handle-south { + height: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:149 */ +.x-tablet .x-resizable-handle-east, +.x-tablet .x-resizable-handle-west { + width: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:153 */ +.x-tablet .x-resizable-handle-northwest, +.x-tablet .x-resizable-handle-northeast, +.x-tablet .x-resizable-handle-southwest, +.x-tablet .x-resizable-handle-southeast { + width: 10px; + height: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:163 */ +.x-window .x-window-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:167 */ +.x-window-collapsed .x-window-handle { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:172 */ +.x-resizable-proxy { + border: 1px dashed #3b5a82; + position: absolute; + overflow: hidden; + z-index: 50000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:180 */ +.x-resizable-handle-over, +.x-resizable-pinned .x-resizable-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:186 */ +.x-resizable-handle-east-over, +.x-resizable-handle-west-over, +.x-resizable-pinned > .x-resizable-handle-east, +.x-resizable-pinned > .x-resizable-handle-west { + background-image: url(images/sizer/e-handle.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:198 */ +.x-resizable-handle-south-over, +.x-resizable-handle-north-over, +.x-resizable-pinned > .x-resizable-handle-south, +.x-resizable-pinned > .x-resizable-handle-north { + background-image: url(images/sizer/s-handle.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:210 */ +.x-resizable-handle-southeast-over, +.x-resizable-pinned > .x-resizable-handle-southeast { + background-position: top left; + background-image: url(images/sizer/se-handle.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:220 */ +.x-resizable-handle-northwest-over, +.x-resizable-pinned > .x-resizable-handle-northwest { + background-position: bottom right; + background-image: url(images/sizer/nw-handle.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:230 */ +.x-resizable-handle-northeast-over, +.x-resizable-pinned > .x-resizable-handle-northeast { + background-position: bottom left; + background-image: url(images/sizer/ne-handle.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:240 */ +.x-resizable-handle-southwest-over, +.x-resizable-pinned > .x-resizable-handle-southwest { + background-position: top right; + background-image: url(images/sizer/sw-handle.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:79 */ +.x-slider-horz { + padding-left: 7px; + background: no-repeat 0 -15px; + margin: 5px 0 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:86 */ +.x-slider-horz .x-slider-end { + padding-right: 8px; + background: no-repeat right -30px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:91 */ +.x-slider-horz .x-slider-inner { + height: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:106 */ +.x-slider-horz .x-slider-thumb { + width: 15px; + height: 15px; + margin-left: -7px; + background-image: url(images/slider/slider-thumb.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:121 */ +.x-keyboard-mode .x-slider-horz.x-slider-focus .x-slider-thumb { + background-position: -45px -45px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:126 */ +.x-slider-horz .x-slider-thumb-over { + background-position: -15px -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:131 */ +.x-keyboard-mode .x-slider-horz.x-slider-focus .x-slider-thumb-over { + background-position: -60px -60px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:136 */ +.x-slider-horz .x-slider-thumb-drag { + background-position: -30px -30px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:141 */ +.x-keyboard-mode .x-slider-horz.x-slider-focus .x-slider-thumb-drag { + background-position: -75px -75px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:170 */ +.x-slider-ct-vert { + /* Vertical styles */ + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:174 */ +.x-slider-vert { + padding-top: 7px; + background: no-repeat -30px 0; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:181 */ +.x-slider-vert > .x-slider-end { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:183 */ +.x-slider-vert > .x-slider-end > .x-slider-inner { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:199 */ +.x-slider-vert .x-slider-end { + padding-bottom: 8px; + background: no-repeat -15px bottom; + width: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:205 */ +.x-slider-vert .x-slider-inner { + width: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:209 */ +.x-slider-vert .x-slider-thumb { + width: 15px; + height: 15px; + margin-bottom: -8px; + background-image: url(images/slider/slider-v-thumb.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:224 */ +.x-keyboard-mode .x-slider-vert.x-slider-focus .x-slider-thumb { + background-position: -45px -45px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:229 */ +.x-slider-vert .x-slider-thumb-over { + background-position: -15px -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:234 */ +.x-keyboard-mode .x-slider-vert.x-slider-focus .x-slider-thumb-over { + background-position: -60px -60px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:239 */ +.x-slider-vert .x-slider-thumb-drag { + background-position: -30px -30px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:244 */ +.x-keyboard-mode .x-slider-vert.x-slider-focus .x-slider-thumb-drag { + background-position: -75px -75px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:249 */ +.x-slider-horz, +.x-slider-horz .x-slider-end, +.x-slider-horz .x-slider-inner { + background-image: url(images/slider/slider-bg.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:255 */ +.x-slider-vert, +.x-slider-vert .x-slider-end, +.x-slider-vert .x-slider-inner { + background-image: url(images/slider/slider-v-bg.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:262 */ +.x-slider-default-cell > .x-grid-cell-inner, +.x-sliderwidget-default-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tab-default-top { + -moz-border-radius-topleft: 3px; + -webkit-border-top-left-radius: 3px; + border-top-left-radius: 3px; + -moz-border-radius-topright: 3px; + -webkit-border-top-right-radius: 3px; + border-top-right-radius: 3px; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 7px 12px 6px 12px; + border-width: 1px; + border-style: solid; + background-color: #4c9dd8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tab-default-top-mc { + background-color: #4c9dd8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tab-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tab-default-top-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-7-12-6-12; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tab-default-top-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tab-default-top-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tab-default-top-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tab-default-top-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tab-default-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tab-default-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tab-default-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tab-default-top-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tab-default-top-tr, +.x-tab-default-top-br, +.x-tab-default-top-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tab-default-top-tl, +.x-tab-default-top-bl, +.x-tab-default-top-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tab-default-top-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tab-default-top-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-tab-default-top-tl, +.x-tab-default-top-bl, +.x-tab-default-top-tr, +.x-tab-default-top-br, +.x-tab-default-top-tc, +.x-tab-default-top-bc, +.x-tab-default-top-ml, +.x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-tab-default-top-ml, +.x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tab-default-top-mc { + padding: 5px 10px 4px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tab-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 3px; + -webkit-border-bottom-right-radius: 3px; + border-bottom-right-radius: 3px; + -moz-border-radius-bottomleft: 3px; + -webkit-border-bottom-left-radius: 3px; + border-bottom-left-radius: 3px; + padding: 6px 12px 7px 12px; + border-width: 1px 1px 1px 1px; + border-style: solid; + background-color: #4c9dd8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tab-default-bottom-mc { + background-color: #4c9dd8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tab-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tab-default-bottom-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-6-12-7-12; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tab-default-bottom-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tab-default-bottom-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tab-default-bottom-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tab-default-bottom-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tab-default-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tab-default-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tab-default-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tab-default-bottom-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tab-default-bottom-tr, +.x-tab-default-bottom-br, +.x-tab-default-bottom-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tab-default-bottom-tl, +.x-tab-default-bottom-bl, +.x-tab-default-bottom-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tab-default-bottom-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tab-default-bottom-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-tab-default-bottom-tl, +.x-tab-default-bottom-bl, +.x-tab-default-bottom-tr, +.x-tab-default-bottom-br, +.x-tab-default-bottom-tc, +.x-tab-default-bottom-bc, +.x-tab-default-bottom-ml, +.x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-tab-default-bottom-ml, +.x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tab-default-bottom-mc { + padding: 4px 10px 5px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tab-default-left { + -moz-border-radius-topleft: 3px; + -webkit-border-top-left-radius: 3px; + border-top-left-radius: 3px; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 3px; + -webkit-border-bottom-left-radius: 3px; + border-bottom-left-radius: 3px; + padding: 7px 12px 6px 12px; + border-width: 1px 1px 1px 1px; + border-style: solid; + background-color: #4c9dd8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tab-default-left-mc { + background-color: #4c9dd8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tab-default-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tab-default-left-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-7-12-6-12; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tab-default-left-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tab-default-left-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tab-default-left-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tab-default-left-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tab-default-left-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tab-default-left-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tab-default-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tab-default-left-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tab-default-left-tr, +.x-tab-default-left-br, +.x-tab-default-left-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tab-default-left-tl, +.x-tab-default-left-bl, +.x-tab-default-left-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tab-default-left-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tab-default-left-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-tab-default-left-tl, +.x-tab-default-left-bl, +.x-tab-default-left-tr, +.x-tab-default-left-br, +.x-tab-default-left-tc, +.x-tab-default-left-bc, +.x-tab-default-left-ml, +.x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-tab-default-left-ml, +.x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tab-default-left-mc { + padding: 5px 10px 4px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tab-default-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 3px; + -webkit-border-top-right-radius: 3px; + border-top-right-radius: 3px; + -moz-border-radius-bottomright: 3px; + -webkit-border-bottom-right-radius: 3px; + border-bottom-right-radius: 3px; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 7px 12px 6px 12px; + border-width: 1px 1px 1px 1px; + border-style: solid; + background-color: #4c9dd8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tab-default-right-mc { + background-color: #4c9dd8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tab-default-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tab-default-right-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-7-12-6-12; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tab-default-right-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tab-default-right-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tab-default-right-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tab-default-right-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tab-default-right-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tab-default-right-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tab-default-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tab-default-right-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tab-default-right-tr, +.x-tab-default-right-br, +.x-tab-default-right-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tab-default-right-tl, +.x-tab-default-right-bl, +.x-tab-default-right-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tab-default-right-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tab-default-right-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-tab-default-right-tl, +.x-tab-default-right-bl, +.x-tab-default-right-tr, +.x-tab-default-right-br, +.x-tab-default-right-tc, +.x-tab-default-right-bc, +.x-tab-default-right-ml, +.x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-tab-default-right-ml, +.x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tab-default-right-mc { + padding: 5px 10px 4px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2672 */ +.x-tab-default { + border-color: #4c9dd8; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2731 */ +.x-tab-default-top { + margin: 0 1px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2740 */ +.x-tab-default-top.x-tab-rotate-left { + margin: 0 0 0 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2763 */ +.x-keyboard-mode .x-tab-default-top.x-tab-focus { + -webkit-box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; + -moz-box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; + box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2794 */ +.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-over { + -webkit-box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; + -moz-box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; + box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2825 */ +.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-active { + -webkit-box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; + -moz-box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; + box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2852 */ +.x-tab-default-right { + margin: 0 0 1px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2861 */ +.x-tab-default-right.x-tab-rotate-right { + margin: 1px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2884 */ +.x-keyboard-mode .x-tab-default-right.x-tab-focus { + -webkit-box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; + -moz-box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; + box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2915 */ +.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-over { + -webkit-box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; + -moz-box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; + box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2946 */ +.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-active { + -webkit-box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; + -moz-box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; + box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2973 */ +.x-tab-default-bottom { + margin: 0 1px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2982 */ +.x-tab-default-bottom.x-tab-rotate-left { + margin: 0 0 0 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3005 */ +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus { + -webkit-box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; + -moz-box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; + box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3036 */ +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-over { + -webkit-box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; + -moz-box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; + box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3067 */ +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-active { + -webkit-box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; + -moz-box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; + box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3094 */ +.x-tab-default-left { + margin: 0 0 1px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3103 */ +.x-tab-default-left.x-tab-rotate-right { + margin: 1px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3126 */ +.x-keyboard-mode .x-tab-default-left.x-tab-focus { + -webkit-box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; + -moz-box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; + box-shadow: #dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3157 */ +.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-over { + -webkit-box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; + -moz-box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; + box-shadow: #dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3188 */ +.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-active { + -webkit-box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; + -moz-box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; + box-shadow: #3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3215 */ +.x-tab-button-default { + height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3220 */ +.x-tab-inner-default { + font: bold 13px/16px tahoma, verdana, sans-serif; + color: #fff; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3236 */ +.x-tab-icon-right > .x-tab-inner-default, +.x-tab-icon-left > .x-tab-inner-default { + max-width: calc(100% - 16px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3244 */ +.x-tab-icon-el-default { + min-height: 16px; + background-position: center center; + font-size: 16px; + line-height: 16px; + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3245 */ +.x-tab-icon-left > .x-tab-icon-el-default, +.x-tab-icon-right > .x-tab-icon-el-default { + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3250 */ +.x-tab-icon-top > .x-tab-icon-el-default, +.x-tab-icon-bottom > .x-tab-icon-el-default { + min-width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3266 */ +.x-tab-icon-el-default.x-tab-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3279 */ +.x-ie8 .x-tab-icon-el-default.x-tab-glyph { + color: #a5ceeb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3286 */ +.x-tab-text.x-tab-icon-left > .x-tab-icon-el-default { + margin-right: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3297 */ +.x-tab-text.x-tab-icon-right > .x-tab-icon-el-default { + margin-left: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3308 */ +.x-tab-text.x-tab-icon-top > .x-tab-icon-el-default { + margin-bottom: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3312 */ +.x-tab-text.x-tab-icon-bottom > .x-tab-icon-el-default { + margin-top: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3318 */ +.x-keyboard-mode .x-tab-focus.x-tab-default { + border-color: #4c9dd8; + background-color: #4c9dd8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3454 */ +.x-tab-over.x-tab-default { + border-color: #60a8dc; + background-color: #60a8dc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3567 */ +.x-keyboard-mode .x-tab-focus.x-tab-over.x-tab-default { + border-color: #60a8dc; + background-color: #60a8dc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3685 */ +.x-tab.x-tab-active.x-tab-default { + border-color: #add2ed; + background-color: #add2ed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3741 */ +.x-tab.x-tab-active.x-tab-default .x-tab-inner-default { + color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3761 */ +.x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3769 */ +.x-ie8 .x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #61a9dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3797 */ +.x-keyboard-mode .x-tab-focus.x-tab-active.x-tab-default { + border-color: #add2ed; + background-color: #add2ed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3916 */ +.x-tab.x-tab-disabled.x-tab-default { + border-color: #4c9dd8; + background-color: #4c9dd8; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3976 */ +.x-tab.x-tab-disabled.x-tab-default .x-tab-inner-default { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4000 */ +.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el-default { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4005 */ +.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el { + color: #fff; + opacity: 0.3; + filter: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4020 */ +.x-ie8 .x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el { + color: #82bae4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4046 */ +.x-nbr .x-tab-default { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-over .x-tab-default-top-tl, +.x-tab-over .x-tab-default-top-bl, +.x-tab-over .x-tab-default-top-tr, +.x-tab-over .x-tab-default-top-br, +.x-tab-over .x-tab-default-top-tc, +.x-tab-over .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-over .x-tab-default-top-ml, +.x-tab-over .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-over .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus .x-tab-default-top-tl, +.x-tab-focus .x-tab-default-top-bl, +.x-tab-focus .x-tab-default-top-tr, +.x-tab-focus .x-tab-default-top-br, +.x-tab-focus .x-tab-default-top-tc, +.x-tab-focus .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus .x-tab-default-top-ml, +.x-tab-focus .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-over .x-tab-default-top-tl, +.x-tab-focus.x-tab-over .x-tab-default-top-bl, +.x-tab-focus.x-tab-over .x-tab-default-top-tr, +.x-tab-focus.x-tab-over .x-tab-default-top-br, +.x-tab-focus.x-tab-over .x-tab-default-top-tc, +.x-tab-focus.x-tab-over .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-over .x-tab-default-top-ml, +.x-tab-focus.x-tab-over .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-over .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-active .x-tab-default-top-tl, +.x-tab.x-tab-active .x-tab-default-top-bl, +.x-tab.x-tab-active .x-tab-default-top-tr, +.x-tab.x-tab-active .x-tab-default-top-br, +.x-tab.x-tab-active .x-tab-default-top-tc, +.x-tab.x-tab-active .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-active .x-tab-default-top-ml, +.x-tab.x-tab-active .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-active .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-active .x-tab-default-top-tl, +.x-tab-focus.x-tab-active .x-tab-default-top-bl, +.x-tab-focus.x-tab-active .x-tab-default-top-tr, +.x-tab-focus.x-tab-active .x-tab-default-top-br, +.x-tab-focus.x-tab-active .x-tab-default-top-tc, +.x-tab-focus.x-tab-active .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-active .x-tab-default-top-ml, +.x-tab-focus.x-tab-active .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-active .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-disabled .x-tab-default-top-tl, +.x-tab.x-tab-disabled .x-tab-default-top-bl, +.x-tab.x-tab-disabled .x-tab-default-top-tr, +.x-tab.x-tab-disabled .x-tab-default-top-br, +.x-tab.x-tab-disabled .x-tab-default-top-tc, +.x-tab.x-tab-disabled .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-disabled .x-tab-default-top-ml, +.x-tab.x-tab-disabled .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-disabled .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-over .x-tab-default-right-tl, +.x-tab-over .x-tab-default-right-bl, +.x-tab-over .x-tab-default-right-tr, +.x-tab-over .x-tab-default-right-br, +.x-tab-over .x-tab-default-right-tc, +.x-tab-over .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-over .x-tab-default-right-ml, +.x-tab-over .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-over .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus .x-tab-default-right-tl, +.x-tab-focus .x-tab-default-right-bl, +.x-tab-focus .x-tab-default-right-tr, +.x-tab-focus .x-tab-default-right-br, +.x-tab-focus .x-tab-default-right-tc, +.x-tab-focus .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus .x-tab-default-right-ml, +.x-tab-focus .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-over .x-tab-default-right-tl, +.x-tab-focus.x-tab-over .x-tab-default-right-bl, +.x-tab-focus.x-tab-over .x-tab-default-right-tr, +.x-tab-focus.x-tab-over .x-tab-default-right-br, +.x-tab-focus.x-tab-over .x-tab-default-right-tc, +.x-tab-focus.x-tab-over .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-over .x-tab-default-right-ml, +.x-tab-focus.x-tab-over .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-over .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-active .x-tab-default-right-tl, +.x-tab.x-tab-active .x-tab-default-right-bl, +.x-tab.x-tab-active .x-tab-default-right-tr, +.x-tab.x-tab-active .x-tab-default-right-br, +.x-tab.x-tab-active .x-tab-default-right-tc, +.x-tab.x-tab-active .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-active .x-tab-default-right-ml, +.x-tab.x-tab-active .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-active .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-active .x-tab-default-right-tl, +.x-tab-focus.x-tab-active .x-tab-default-right-bl, +.x-tab-focus.x-tab-active .x-tab-default-right-tr, +.x-tab-focus.x-tab-active .x-tab-default-right-br, +.x-tab-focus.x-tab-active .x-tab-default-right-tc, +.x-tab-focus.x-tab-active .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-active .x-tab-default-right-ml, +.x-tab-focus.x-tab-active .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-active .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-disabled .x-tab-default-right-tl, +.x-tab.x-tab-disabled .x-tab-default-right-bl, +.x-tab.x-tab-disabled .x-tab-default-right-tr, +.x-tab.x-tab-disabled .x-tab-default-right-br, +.x-tab.x-tab-disabled .x-tab-default-right-tc, +.x-tab.x-tab-disabled .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-disabled .x-tab-default-right-ml, +.x-tab.x-tab-disabled .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-disabled .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-over .x-tab-default-bottom-tl, +.x-tab-over .x-tab-default-bottom-bl, +.x-tab-over .x-tab-default-bottom-tr, +.x-tab-over .x-tab-default-bottom-br, +.x-tab-over .x-tab-default-bottom-tc, +.x-tab-over .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-over .x-tab-default-bottom-ml, +.x-tab-over .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-over .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus .x-tab-default-bottom-tl, +.x-tab-focus .x-tab-default-bottom-bl, +.x-tab-focus .x-tab-default-bottom-tr, +.x-tab-focus .x-tab-default-bottom-br, +.x-tab-focus .x-tab-default-bottom-tc, +.x-tab-focus .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus .x-tab-default-bottom-ml, +.x-tab-focus .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-over .x-tab-default-bottom-tl, +.x-tab-focus.x-tab-over .x-tab-default-bottom-bl, +.x-tab-focus.x-tab-over .x-tab-default-bottom-tr, +.x-tab-focus.x-tab-over .x-tab-default-bottom-br, +.x-tab-focus.x-tab-over .x-tab-default-bottom-tc, +.x-tab-focus.x-tab-over .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-over .x-tab-default-bottom-ml, +.x-tab-focus.x-tab-over .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-over .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-active .x-tab-default-bottom-tl, +.x-tab.x-tab-active .x-tab-default-bottom-bl, +.x-tab.x-tab-active .x-tab-default-bottom-tr, +.x-tab.x-tab-active .x-tab-default-bottom-br, +.x-tab.x-tab-active .x-tab-default-bottom-tc, +.x-tab.x-tab-active .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-active .x-tab-default-bottom-ml, +.x-tab.x-tab-active .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-active .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-active .x-tab-default-bottom-tl, +.x-tab-focus.x-tab-active .x-tab-default-bottom-bl, +.x-tab-focus.x-tab-active .x-tab-default-bottom-tr, +.x-tab-focus.x-tab-active .x-tab-default-bottom-br, +.x-tab-focus.x-tab-active .x-tab-default-bottom-tc, +.x-tab-focus.x-tab-active .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-active .x-tab-default-bottom-ml, +.x-tab-focus.x-tab-active .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-active .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-disabled .x-tab-default-bottom-tl, +.x-tab.x-tab-disabled .x-tab-default-bottom-bl, +.x-tab.x-tab-disabled .x-tab-default-bottom-tr, +.x-tab.x-tab-disabled .x-tab-default-bottom-br, +.x-tab.x-tab-disabled .x-tab-default-bottom-tc, +.x-tab.x-tab-disabled .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-disabled .x-tab-default-bottom-ml, +.x-tab.x-tab-disabled .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-disabled .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-over .x-tab-default-left-tl, +.x-tab-over .x-tab-default-left-bl, +.x-tab-over .x-tab-default-left-tr, +.x-tab-over .x-tab-default-left-br, +.x-tab-over .x-tab-default-left-tc, +.x-tab-over .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-over .x-tab-default-left-ml, +.x-tab-over .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-over .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus .x-tab-default-left-tl, +.x-tab-focus .x-tab-default-left-bl, +.x-tab-focus .x-tab-default-left-tr, +.x-tab-focus .x-tab-default-left-br, +.x-tab-focus .x-tab-default-left-tc, +.x-tab-focus .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus .x-tab-default-left-ml, +.x-tab-focus .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-over .x-tab-default-left-tl, +.x-tab-focus.x-tab-over .x-tab-default-left-bl, +.x-tab-focus.x-tab-over .x-tab-default-left-tr, +.x-tab-focus.x-tab-over .x-tab-default-left-br, +.x-tab-focus.x-tab-over .x-tab-default-left-tc, +.x-tab-focus.x-tab-over .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-over .x-tab-default-left-ml, +.x-tab-focus.x-tab-over .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-over .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-active .x-tab-default-left-tl, +.x-tab.x-tab-active .x-tab-default-left-bl, +.x-tab.x-tab-active .x-tab-default-left-tr, +.x-tab.x-tab-active .x-tab-default-left-br, +.x-tab.x-tab-active .x-tab-default-left-tc, +.x-tab.x-tab-active .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-active .x-tab-default-left-ml, +.x-tab.x-tab-active .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-active .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-active .x-tab-default-left-tl, +.x-tab-focus.x-tab-active .x-tab-default-left-bl, +.x-tab-focus.x-tab-active .x-tab-default-left-tr, +.x-tab-focus.x-tab-active .x-tab-default-left-br, +.x-tab-focus.x-tab-active .x-tab-default-left-tc, +.x-tab-focus.x-tab-active .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-focus-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-active .x-tab-default-left-ml, +.x-tab-focus.x-tab-active .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-focus-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-active .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-focus-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-disabled .x-tab-default-left-tl, +.x-tab.x-tab-disabled .x-tab-default-left-bl, +.x-tab.x-tab-disabled .x-tab-default-left-tr, +.x-tab.x-tab-disabled .x-tab-default-left-br, +.x-tab.x-tab-disabled .x-tab-default-left-tc, +.x-tab.x-tab-disabled .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-disabled .x-tab-default-left-ml, +.x-tab.x-tab-disabled .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-disabled .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4089 */ +.x-tab-default-tl, +.x-tab-default-bl, +.x-tab-default-tr, +.x-tab-default-br { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#00FFFFFF,endColorstr=#00FFFFFF)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4099 */ +.x-tab-default .x-tab-close-btn { + top: 2px; + right: 2px; + width: 12px; + height: 12px; + background: url(images/tab/tab-default-close.png) 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4121 */ +.x-tab-default .x-tab-close-btn-over { + background-position: -12px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4131 */ +.x-tab-default .x-tab-close-btn-pressed { + background-position: -24px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4198 */ +.x-tab-default.x-tab-active .x-tab-close-btn { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4203 */ +.x-tab-default.x-tab-active .x-tab-close-btn-over { + background-position: -12px -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4209 */ +.x-tab-default.x-tab-active .x-tab-close-btn-pressed { + background-position: -24px -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4235 */ +.x-tab-default.x-tab-disabled .x-tab-close-btn { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4262 */ +.x-tab-closable.x-tab-default .x-tab-button { + padding-right: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:389 */ +.x-tab-bar-default { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:428 */ +.x-tab-bar-default-top > .x-tab-bar-body-default { + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:432 */ +.x-tab-bar-default-bottom > .x-tab-bar-body-default { + padding: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:436 */ +.x-tab-bar-default-left > .x-tab-bar-body-default { + padding: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:446 */ +.x-tab-bar-default-right > .x-tab-bar-body-default { + padding: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:490 */ +.x-tab-bar-plain.x-tab-bar-default-horizontal { + border-top-color: transparent; + border-bottom-color: transparent; + border-left-width: 0; + border-right-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:497 */ +.x-tab-bar-plain.x-tab-bar-default-vertical { + border-right-color: transparent; + border-left-color: transparent; + border-top-width: 0; + border-bottom-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:509 */ +.x-tab-bar-top > .x-tab-bar-body-default { + padding-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:513 */ +.x-tab-bar-bottom > .x-tab-bar-body-default { + padding-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:517 */ +.x-tab-bar-left > .x-tab-bar-body-default { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:528 */ +.x-tab-bar-right > .x-tab-bar-body-default { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:540 */ +.x-tab-bar-strip-default { + border-style: solid; + border-color: #157fcc; + background-color: #add2ed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:547 */ +.x-tab-bar-top > .x-tab-bar-strip-default { + border-width: 0 0; + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:551 */ +.x-tab-bar-top.x-tab-bar-plain > .x-tab-bar-strip-default { + border-width: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:557 */ +.x-tab-bar-bottom > .x-tab-bar-strip-default { + border-width: 0 0 0 0; + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:561 */ +.x-tab-bar-bottom.x-tab-bar-plain > .x-tab-bar-strip-default { + border-width: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:567 */ +.x-tab-bar-left > .x-tab-bar-strip-default { + border-width: 0 0 0 0; + width: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:576 */ +.x-tab-bar-left.x-tab-bar-plain > .x-tab-bar-strip-default { + border-width: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:587 */ +.x-tab-bar-right > .x-tab-bar-strip-default { + border-width: 0 0 0 0; + width: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:596 */ +.x-tab-bar-right.x-tab-bar-plain > .x-tab-bar-strip-default { + border-width: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:611 */ +.x-tab-bar-horizontal > .x-tab-bar-body-default { + min-height: 34px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:614 */ +.x-ie8m .x-tab-bar-horizontal > .x-tab-bar-body-default { + min-height: 29px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:621 */ +.x-tab-bar-vertical > .x-tab-bar-body-default { + min-width: 34px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:624 */ +.x-ie8m .x-tab-bar-vertical > .x-tab-bar-body-default { + min-width: 29px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-tab-bar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-tab-bar-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-tab-bar-default { + cursor: pointer; + color: #fff; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-tab-bar-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-tab-bar-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-tab-bar-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:232 */ +.x-box-scroller-tab-bar-default.x-box-scroller-left, +.x-box-scroller-tab-bar-default.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:259 */ +.x-box-scroller-tab-bar-default.x-box-scroller-left { + margin-left: 0; + margin-right: 0; + margin-bottom: 0; + background-image: url(images/tab-bar/default-scroll-left.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:284 */ +.x-box-scroller-tab-bar-default.x-box-scroller-right { + margin-left: 0; + margin-right: 0; + margin-bottom: 0; + background-image: url(images/tab-bar/default-scroll-right.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:311 */ +.x-box-scroller-tab-bar-default.x-box-scroller-top, +.x-box-scroller-tab-bar-default.x-box-scroller-bottom { + height: 24px; + width: 24px; + left: 50%; + margin-left: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:338 */ +.x-box-scroller-tab-bar-default.x-box-scroller-top { + margin-top: 0; + margin-right: 0; + margin-bottom: 0; + background-image: url(images/tab-bar/default-scroll-top.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:363 */ +.x-box-scroller-tab-bar-default.x-box-scroller-bottom { + margin-top: 0; + margin-right: 0; + margin-bottom: 0; + background-image: url(images/tab-bar/default-scroll-bottom.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:704 */ +.x-tab-bar-more-icon { + background-image: url(images/tab-bar/default-more.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:721 */ +.x-tab-bar-plain.x-tab-bar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:727 */ +.x-tab-bar-plain.x-tab-bar-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:732 */ +.x-tab-bar-plain .x-box-scroller-tab-bar-default { + color: #b0b0b0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:780 */ +.x-tab-bar-default-top .x-box-scroller-tab-bar-default { + margin-top: -14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:784 */ +.x-tab-bar-default-right .x-box-scroller-tab-bar-default { + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:788 */ +.x-tab-bar-default-bottom .x-box-scroller-tab-bar-default { + margin-top: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:792 */ +.x-tab-bar-default-left .x-box-scroller-tab-bar-default { + margin-left: -14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:801 */ +.x-box-scroller-tab-bar-default { + background-color: #157fcc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:807 */ +.x-box-scroller-tab-bar-default .x-ie8 .x-box-scroller-plain { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:819 */ +.x-box-scroller-plain.x-box-scroller-tab-bar-default.x-box-scroller-left { + background-image: url(images/tab-bar/default-plain-scroll-left.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:825 */ +.x-box-scroller-plain.x-box-scroller-tab-bar-default.x-box-scroller-right { + background-image: url(images/tab-bar/default-plain-scroll-right.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:831 */ +.x-box-scroller-plain.x-box-scroller-tab-bar-default.x-box-scroller-top { + background-image: url(images/tab-bar/default-plain-scroll-top.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:837 */ +.x-box-scroller-plain.x-box-scroller-tab-bar-default.x-box-scroller-bottom { + background-image: url(images/tab-bar/default-plain-scroll-bottom.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:406 */ +.x-breadcrumb-btn-default { + margin: 0 0 0 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:410 */ +.x-breadcrumb-icon-folder-default { + background-image: url(images/tree/folder.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:418 */ +.x-btn-menu-active .x-breadcrumb-icon-folder-default { + background-image: url(images/tree/folder-open.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:428 */ +.x-breadcrumb-icon-leaf-default { + background-image: url(images/tree/leaf.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:438 */ +.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-arrow:after { + width: 20px; + background-image: url(images/breadcrumb/default-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:450 */ +.x-btn-menu-active.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-arrow:after { + background-image: url(images/breadcrumb/default-arrow-open.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:463 */ +.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after { + width: 20px; + background-image: url(images/breadcrumb/default-split-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:488 */ +.x-btn-over.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after { + background-image: url(images/breadcrumb/default-split-arrow-over.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:500 */ +.x-btn-menu-active.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after { + background-image: url(images/breadcrumb/default-split-arrow-open.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-breadcrumb-default-scroller .x-box-scroller-body-horizontal { + margin-left: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-breadcrumb-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-breadcrumb-default { + cursor: pointer; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:232 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-left, +.x-box-scroller-breadcrumb-default.x-box-scroller-right { + width: 16px; + height: 16px; + top: 50%; + margin-top: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:259 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + background-image: url(images/breadcrumb/default-scroll-left.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:284 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + background-image: url(images/breadcrumb/default-scroll-right.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:1 */ +.x-tree-expander { + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:23 */ +.x-tree-arrows .x-tree-expander { + background-image: url(images/tree/arrows.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:27 */ +.x-tree-arrows .x-tree-expander-over .x-tree-expander { + background-position: -36px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:31 */ +.x-tree-arrows .x-grid-tree-node-expanded .x-tree-expander { + background-position: -18px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:35 */ +.x-tree-arrows .x-grid-tree-node-expanded .x-tree-expander-over .x-tree-expander { + background-position: -54px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:77 */ +.x-tree-lines .x-tree-elbow { + background-image: url(images/tree/elbow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:81 */ +.x-tree-lines .x-tree-elbow-end { + background-image: url(images/tree/elbow-end.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:85 */ +.x-tree-lines .x-tree-elbow-plus { + background-image: url(images/tree/elbow-plus.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:89 */ +.x-tree-lines .x-tree-elbow-end-plus { + background-image: url(images/tree/elbow-end-plus.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:93 */ +.x-tree-lines .x-grid-tree-node-expanded .x-tree-elbow-plus { + background-image: url(images/tree/elbow-minus.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:97 */ +.x-tree-lines .x-grid-tree-node-expanded .x-tree-elbow-end-plus { + background-image: url(images/tree/elbow-end-minus.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:101 */ +.x-tree-lines .x-tree-elbow-line { + background-image: url(images/tree/elbow-line.png); +} \ No newline at end of file diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all-debug_2.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all-debug_2.css new file mode 100644 index 0000000..030650b --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all-debug_2.css @@ -0,0 +1,3492 @@ +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:137 */ +.x-tree-no-lines .x-tree-expander { + background-image: url(images/tree/elbow-plus-nl.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:141 */ +.x-tree-no-lines .x-grid-tree-node-expanded .x-tree-expander { + background-image: url(images/tree/elbow-minus-nl.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:157 */ +.x-tree-icon { + width: 16px; + height: 24px; + line-height: 24px; + color: #b0b0b0; + font-size: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:165 */ +.x-tree-elbow-img { + width: 18px; + height: 24px; + line-height: 24px; + margin-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:179 */ +.x-tree-icon, +.x-tree-elbow-img, +.x-tree-checkbox { + margin-top: -5px; + margin-bottom: -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:189 */ +.x-tree-icon-leaf { + background-image: url(images/tree/leaf.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:204 */ +.x-tree-icon-parent { + background-image: url(images/tree/folder.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:225 */ +.x-tree-icon-parent-expanded { + background-image: url(images/tree/folder-open.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:236 */ +.x-tree-icon-custom { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:252 */ +.x-tree-checkbox { + margin-right: 4px; + top: 5px; + width: 15px; + height: 15px; + background-image: url(images/form/checkbox.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:272 */ +.x-tree-checkbox-checked { + background-position: 0 -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:280 */ +.x-grid-tree-loading .x-tree-icon { + background-image: url(images/tree/loading.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:290 */ +.x-tree-node-text { + padding-left: 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:302 */ +.x-grid-cell-inner-treecolumn { + padding: 5px 10px 4px 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/ViewDropZone.scss:9 */ +.x-tree-drop-ok-append .x-dd-drop-icon { + background-image: url(images/tree/drop-append.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/ViewDropZone.scss:13 */ +.x-tree-drop-ok-above .x-dd-drop-icon { + background-image: url(images/tree/drop-above.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/ViewDropZone.scss:17 */ +.x-tree-drop-ok-below .x-dd-drop-icon { + background-image: url(images/tree/drop-below.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/ViewDropZone.scss:21 */ +.x-tree-drop-ok-between .x-dd-drop-icon { + background-image: url(images/tree/drop-between.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/ViewDropZone.scss:26 */ +.x-tree-ddindicator { + height: 1px; + border-width: 1px 0px 0px; + border-style: dotted; + border-color: green; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/MultiSelector.scss:1 */ +.x-multiselector-remove { + font-size: 110%; + color: #e1e1e1; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/MultiSelector.scss:6 */ +.x-multiselector-remove .x-grid-cell-inner { + padding: 5px 4px 4px 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/MultiSelector.scss:11 */ +.x-grid-item-over .x-multiselector-remove { + color: red; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/MultiSelector.scss:16 */ +.x-multiselector-search-input .x-form-text::-ms-clear { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:1 */ +.x-toast-icon-information { + background-image: url(images/window/toast/icon16_info.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:5 */ +.x-toast-icon-error { + background-image: url(images/window/toast/icon16_error.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:11 */ +.x-toast-window .x-window-body { + /* Using standard theme */ + padding: 15px 5px 15px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:17 */ +.x-toast-light .x-window-header { + /* Custom styling */ + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:21 */ +.x-toast-light .x-tool-img { + background-color: #3892d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:25 */ +.x-toast-light { + background-image: url(images/window/toast/fader.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:29 */ +.x-toast-light .x-window-body { + padding: 15px 5px 20px 5px; + background-color: transparent; + border: 0px solid white; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-plain-toolbar-small { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-plain-toolbar-small-mc { + background-image: url(images/btn/btn-plain-toolbar-small-fbg.gif); + background-position: 0 top; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-plain-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-plain-toolbar-small-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-plain-toolbar-small-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-plain-toolbar-small-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-plain-toolbar-small-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-plain-toolbar-small-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-plain-toolbar-small-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-plain-toolbar-small-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-plain-toolbar-small-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-plain-toolbar-small-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-plain-toolbar-small-tr, +.x-btn-plain-toolbar-small-br, +.x-btn-plain-toolbar-small-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-plain-toolbar-small-tl, +.x-btn-plain-toolbar-small-bl, +.x-btn-plain-toolbar-small-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-plain-toolbar-small-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-plain-toolbar-small-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-plain-toolbar-small-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-plain-toolbar-small { + border-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-plain-toolbar-small { + min-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-plain-toolbar-small { + min-height: auto; + height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-plain-toolbar-small { + font: bold 12px/16px tahoma, verdana, sans-serif; + color: #666; + padding: 0 5px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-small { + max-width: calc(100% - 16px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-small { + max-width: calc(100% - 15px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-plain-toolbar-small { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-plain-toolbar-small { + font-size: 16px; + height: 16px; + color: #666; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small { + min-width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-plain-toolbar-small.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-plain-toolbar-small.x-btn-glyph { + color: #b3b3b3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small { + margin-right: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + margin-left: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-small, +.x-btn-split-bottom > .x-btn-button-plain-toolbar-small { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-plain-toolbar-small.x-btn-arrow-right:after { + width: 16px; + background-image: url(images/button/plain-toolbar-small-arrow.png); + padding-right: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-plain-toolbar-small.x-btn-arrow-bottom:after { + height: 13px; + background-image: url(images/button/plain-toolbar-small-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-plain-toolbar-small.x-btn-split-right:after { + width: 20px; + background-image: url(images/button/plain-toolbar-small-s-arrow.png); + padding-right: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom:after { + height: 15px; + background-image: url(images/button/plain-toolbar-small-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-small { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-plain-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 23px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-plain-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-plain-toolbar-small { + border-color: #d8d8d8; + background-image: none; + background-color: #ececec; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec)); + background-image: -webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-small { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-plain-toolbar-small, +.x-btn.x-btn-pressed.x-btn-plain-toolbar-small { + border-color: #cfcfcf; + background-image: none; + background-color: #e2e2e2; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5)); + background-image: -webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-plain-toolbar-small { + background-image: none; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mc { + background-color: transparent; + background-image: url(images/btn/btn-plain-toolbar-small-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-plain-toolbar-small-tl, +.x-btn-over .x-btn-plain-toolbar-small-bl, +.x-btn-over .x-btn-plain-toolbar-small-tr, +.x-btn-over .x-btn-plain-toolbar-small-br, +.x-btn-over .x-btn-plain-toolbar-small-tc, +.x-btn-over .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-plain-toolbar-small-ml, +.x-btn-over .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-plain-toolbar-small-mc { + background-color: #ececec; + background-image: url(images/btn/btn-plain-toolbar-small-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mc { + background-color: #ececec; + background-image: url(images/btn/btn-plain-toolbar-small-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-plain-toolbar-small-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-plain-toolbar-small-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mc { + background-color: transparent; + background-image: url(images/btn/btn-plain-toolbar-small-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-plain-toolbar-small { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-plain-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first .x-btn-plain-toolbar-small-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle .x-btn-plain-toolbar-small-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last .x-btn-plain-toolbar-small-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first .x-btn-plain-toolbar-small-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle .x-btn-plain-toolbar-small-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last .x-btn-plain-toolbar-small-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-small:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-small:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-small:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-plain-toolbar-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-plain-toolbar-small-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-small { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-plain-toolbar-medium { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-plain-toolbar-medium-mc { + background-image: url(images/btn/btn-plain-toolbar-medium-fbg.gif); + background-position: 0 top; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-plain-toolbar-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-plain-toolbar-medium-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-plain-toolbar-medium-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-plain-toolbar-medium-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-plain-toolbar-medium-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-plain-toolbar-medium-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-plain-toolbar-medium-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-plain-toolbar-medium-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-plain-toolbar-medium-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-plain-toolbar-medium-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-plain-toolbar-medium-tr, +.x-btn-plain-toolbar-medium-br, +.x-btn-plain-toolbar-medium-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-plain-toolbar-medium-tl, +.x-btn-plain-toolbar-medium-bl, +.x-btn-plain-toolbar-medium-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-plain-toolbar-medium-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-plain-toolbar-medium-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-plain-toolbar-medium-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-plain-toolbar-medium { + border-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-plain-toolbar-medium { + min-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-plain-toolbar-medium { + min-height: auto; + height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-plain-toolbar-medium { + font: bold 14px/18px tahoma, verdana, sans-serif; + color: #666; + padding: 0 8px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium { + max-width: calc(100% - 24px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium { + max-width: calc(100% - 23px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-plain-toolbar-medium { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-plain-toolbar-medium { + font-size: 24px; + height: 24px; + color: #666; + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium, +.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium, +.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium { + min-width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-plain-toolbar-medium.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-plain-toolbar-medium.x-btn-glyph { + color: #b3b3b3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium { + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-medium, +.x-btn-split-bottom > .x-btn-button-plain-toolbar-medium { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-right:after { + width: 24px; + background-image: url(images/button/plain-toolbar-medium-arrow.png); + padding-right: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-bottom:after { + height: 18px; + background-image: url(images/button/plain-toolbar-medium-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-split-right:after { + width: 28px; + background-image: url(images/button/plain-toolbar-medium-s-arrow.png); + padding-right: 28px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom:after { + height: 24px; + background-image: url(images/button/plain-toolbar-medium-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-medium { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-plain-toolbar-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 31px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-plain-toolbar-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-plain-toolbar-medium { + border-color: #d8d8d8; + background-image: none; + background-color: #ececec; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec)); + background-image: -webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-plain-toolbar-medium, +.x-btn.x-btn-pressed.x-btn-plain-toolbar-medium { + border-color: #cfcfcf; + background-image: none; + background-color: #e2e2e2; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5)); + background-image: -webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-plain-toolbar-medium { + background-image: none; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mc { + background-color: transparent; + background-image: url(images/btn/btn-plain-toolbar-medium-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-plain-toolbar-medium-tl, +.x-btn-over .x-btn-plain-toolbar-medium-bl, +.x-btn-over .x-btn-plain-toolbar-medium-tr, +.x-btn-over .x-btn-plain-toolbar-medium-br, +.x-btn-over .x-btn-plain-toolbar-medium-tc, +.x-btn-over .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-plain-toolbar-medium-ml, +.x-btn-over .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-plain-toolbar-medium-mc { + background-color: #ececec; + background-image: url(images/btn/btn-plain-toolbar-medium-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mc { + background-color: #ececec; + background-image: url(images/btn/btn-plain-toolbar-medium-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tr, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-br, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tc, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-br, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-ml, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-ml, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-plain-toolbar-medium-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-plain-toolbar-medium-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tr, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-br, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tc, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-ml, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mc { + background-color: transparent; + background-image: url(images/btn/btn-plain-toolbar-medium-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-plain-toolbar-medium { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-plain-toolbar-medium { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first .x-btn-plain-toolbar-medium-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle .x-btn-plain-toolbar-medium-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last .x-btn-plain-toolbar-medium-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first .x-btn-plain-toolbar-medium-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle .x-btn-plain-toolbar-medium-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last .x-btn-plain-toolbar-medium-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-medium:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-medium:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-plain-toolbar-medium-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-plain-toolbar-medium-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-medium { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-plain-toolbar-large { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + -ms-border-radius: 3px; + -o-border-radius: 3px; + border-radius: 3px; + padding: 3px 3px 3px 3px; + border-width: 1px; + border-style: solid; + background-image: none; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-plain-toolbar-large-mc { + background-image: url(images/btn/btn-plain-toolbar-large-fbg.gif); + background-position: 0 top; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-plain-toolbar-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + background-image: none; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-plain-toolbar-large-frameInfo { + font-family: th-3-3-3-3-1-1-1-1-3-3-3-3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-plain-toolbar-large-tl { + background-position: 0 -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-plain-toolbar-large-tr { + background-position: right -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-plain-toolbar-large-bl { + background-position: 0 -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-plain-toolbar-large-br { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-plain-toolbar-large-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-plain-toolbar-large-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-plain-toolbar-large-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-plain-toolbar-large-bc { + background-position: 0 -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-plain-toolbar-large-tr, +.x-btn-plain-toolbar-large-br, +.x-btn-plain-toolbar-large-mr { + padding-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-plain-toolbar-large-tl, +.x-btn-plain-toolbar-large-bl, +.x-btn-plain-toolbar-large-ml { + padding-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-plain-toolbar-large-tc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-plain-toolbar-large-bc { + height: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-plain-toolbar-large-mc { + padding: 1px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-plain-toolbar-large { + border-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-plain-toolbar-large { + min-height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-plain-toolbar-large { + min-height: auto; + height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-plain-toolbar-large { + font: bold 16px/20px tahoma, verdana, sans-serif; + color: #666; + padding: 0 10px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-large { + max-width: calc(100% - 32px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-large { + max-width: calc(100% - 31px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-plain-toolbar-large { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-plain-toolbar-large { + font-size: 32px; + height: 32px; + color: #666; + line-height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large, +.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + width: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large, +.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large { + min-width: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2537 */ +.x-btn-icon-el-plain-toolbar-large.x-btn-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-plain-toolbar-large.x-btn-glyph { + color: #b3b3b3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large { + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large { + margin-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large { + margin-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-large, +.x-btn-split-bottom > .x-btn-button-plain-toolbar-large { + padding-bottom: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-plain-toolbar-large.x-btn-arrow-right:after { + width: 28px; + background-image: url(images/button/plain-toolbar-large-arrow.png); + padding-right: 28px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-plain-toolbar-large.x-btn-arrow-bottom:after { + height: 20px; + background-image: url(images/button/plain-toolbar-large-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-plain-toolbar-large.x-btn-split-right:after { + width: 35px; + background-image: url(images/button/plain-toolbar-large-s-arrow.png); + padding-right: 35px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom:after { + height: 29px; + background-image: url(images/button/plain-toolbar-large-s-arrow-b.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-large { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-plain-toolbar-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 38px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-plain-toolbar-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-plain-toolbar-large { + border-color: #d8d8d8; + background-image: none; + background-color: #ececec; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec)); + background-image: -webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: -ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); + background-image: linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-large { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-plain-toolbar-large, +.x-btn.x-btn-pressed.x-btn-plain-toolbar-large { + border-color: #cfcfcf; + background-image: none; + background-color: #e2e2e2; + background-image: -webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5)); + background-image: -webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: -ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); + background-image: linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large { + -webkit-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + -moz-box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; + box-shadow: #4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-plain-toolbar-large { + background-image: none; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mc { + background-color: transparent; + background-image: url(images/btn/btn-plain-toolbar-large-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-plain-toolbar-large-tl, +.x-btn-over .x-btn-plain-toolbar-large-bl, +.x-btn-over .x-btn-plain-toolbar-large-tr, +.x-btn-over .x-btn-plain-toolbar-large-br, +.x-btn-over .x-btn-plain-toolbar-large-tc, +.x-btn-over .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-plain-toolbar-large-ml, +.x-btn-over .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-plain-toolbar-large-mc { + background-color: #ececec; + background-image: url(images/btn/btn-plain-toolbar-large-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mc { + background-color: #ececec; + background-image: url(images/btn/btn-plain-toolbar-large-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tr, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-br, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tc, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-br, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-ml, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-ml, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-plain-toolbar-large-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mc { + background-color: #e2e2e2; + background-image: url(images/btn/btn-plain-toolbar-large-focus-pressed-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tr, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-br, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tc, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-ml, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mc { + background-color: transparent; + background-image: url(images/btn/btn-plain-toolbar-large-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-plain-toolbar-large { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-plain-toolbar-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first .x-btn-plain-toolbar-large-mc { + padding-right: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle .x-btn-plain-toolbar-large-mc { + padding-right: 3px !important; + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last .x-btn-plain-toolbar-large-mc { + padding-left: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first .x-btn-plain-toolbar-large-mc { + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle .x-btn-plain-toolbar-large-mc { + padding-top: 3px !important; + padding-bottom: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last .x-btn-plain-toolbar-large-mc { + padding-top: 3px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-large:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-large:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-large:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large:after { + border-width: 1px; + border-color: #4297d4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-plain-toolbar-large-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-plain-toolbar-large-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-large { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/button/Button.scss:220 */ +.x-btn-plain-toolbar-small-disabled .x-btn-icon-el, +.x-btn-plain-toolbar-medium-disabled .x-btn-icon-el, +.x-btn-plain-toolbar-large-disabled .x-btn-icon-el { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/button/Button.scss:223 */ +.x-ie8 .x-btn-plain-toolbar-small-disabled .x-btn-icon-el, +.x-ie8 .x-btn-plain-toolbar-medium-disabled .x-btn-icon-el, +.x-ie8 .x-btn-plain-toolbar-large-disabled .x-btn-icon-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:799 */ +.x-panel-light { + border-color: #e0ebf3; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:802 */ +.x-panel-light.x-masked { + border-color: #f6f9fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:810 */ +.x-panel-header-light { + font-size: 13px; + border: 1px solid #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:819 */ +.x-panel-header-light .x-tool-tool-el { + color: #666; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:825 */ +.x-panel-header-light .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:836 */ +.x-panel-header-light .x-tool-tool-el { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:842 */ +.x-panel-header-light-horizontal { + padding: 9px 9px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:846 */ +.x-panel-header-light-horizontal .x-panel-header-light-tab-bar { + margin-top: -9px; + margin-bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:854 */ +.x-panel-header-light-horizontal.x-header-noborder { + padding: 10px 10px 10px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:858 */ +.x-panel-header-light-horizontal.x-header-noborder .x-panel-header-light-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:866 */ +.x-panel-header-light-vertical { + padding: 9px 9px 9px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:870 */ +.x-panel-header-light-vertical .x-panel-header-light-tab-bar { + margin-right: -9px; + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:878 */ +.x-panel-header-light-vertical.x-header-noborder { + padding: 10px 10px 10px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:882 */ +.x-panel-header-light-vertical.x-header-noborder .x-panel-header-light-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:916 */ +.x-panel-header-title-light { + color: #666; + font-size: 13px; + font-weight: bold; + font-family: tahoma, verdana, sans-serif; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:929 */ +.x-keyboard-mode .x-panel-header-title-light.x-title-focus { + outline: 1px solid #157fcc; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #157fcc; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:950 */ +.x-panel-header-title-light > .x-title-text-light { + text-transform: none; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:997 */ +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-top { + height: 22px; + padding-bottom: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1002 */ +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-right { + width: 22px; + padding-left: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1014 */ +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-bottom { + height: 22px; + padding-top: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1019 */ +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-left { + width: 22px; + padding-right: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1031 */ +.x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light { + width: 16px; + height: 16px; + font-size: 16px; + color: #666; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1038 */ +.x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light.x-title-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1051 */ +.x-ie8 .x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light.x-title-glyph { + color: #a3a8ac; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1062 */ +.x-panel-body-light { + background: #fff; + border-color: #e0ebf3; + color: #000; + font-size: 13px; + font-weight: normal; + font-family: tahoma, verdana, sans-serif; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1226 */ +.x-panel-header-light { + background-image: none; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1230 */ +.x-panel-header-light-vertical { + background-image: none; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1288 */ +.x-panel .x-panel-header-light-collapsed-border-top { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1292 */ +.x-panel .x-panel-header-light-collapsed-border-right { + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1296 */ +.x-panel .x-panel-header-light-collapsed-border-bottom { + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1300 */ +.x-panel .x-panel-header-light-collapsed-border-left { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1336 */ +.x-panel-header-light-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1346 */ +.x-panel-header-light-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1358 */ +.x-panel-header-light-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1368 */ +.x-panel-header-light-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1381 */ +.x-keyboard-mode .x-panel-header-light .x-tool-focus { + outline: 1px solid #157fcc; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #157fcc; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1429 */ +.x-panel-light-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-panel-light-outer-border-l { + border-left-color: #e0ebf3 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-panel-light-outer-border-b { + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-panel-light-outer-border-bl { + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 1px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-panel-light-outer-border-r { + border-right-color: #e0ebf3 !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-panel-light-outer-border-rl { + border-right-color: #e0ebf3 !important; + border-right-width: 1px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-panel-light-outer-border-rb { + border-right-color: #e0ebf3 !important; + border-right-width: 1px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-panel-light-outer-border-rbl { + border-right-color: #e0ebf3 !important; + border-right-width: 1px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 1px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-panel-light-outer-border-t { + border-top-color: #e0ebf3 !important; + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-panel-light-outer-border-tl { + border-top-color: #e0ebf3 !important; + border-top-width: 1px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-panel-light-outer-border-tb { + border-top-color: #e0ebf3 !important; + border-top-width: 1px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-panel-light-outer-border-tbl { + border-top-color: #e0ebf3 !important; + border-top-width: 1px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 1px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-panel-light-outer-border-tr { + border-top-color: #e0ebf3 !important; + border-top-width: 1px !important; + border-right-color: #e0ebf3 !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-panel-light-outer-border-trl { + border-top-color: #e0ebf3 !important; + border-top-width: 1px !important; + border-right-color: #e0ebf3 !important; + border-right-width: 1px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-panel-light-outer-border-trb { + border-top-color: #e0ebf3 !important; + border-top-width: 1px !important; + border-right-color: #e0ebf3 !important; + border-right-width: 1px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-panel-light-outer-border-trbl { + border-color: #e0ebf3 !important; + border-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:799 */ +.x-panel-light-framed { + border-color: #e0ebf3; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:802 */ +.x-panel-light-framed.x-masked { + border-color: #f6f9fb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:810 */ +.x-panel-header-light-framed { + font-size: 13px; + border: 5px solid #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:819 */ +.x-panel-header-light-framed .x-tool-tool-el { + color: #666; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:825 */ +.x-panel-header-light-framed .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:836 */ +.x-panel-header-light-framed .x-tool-tool-el { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:842 */ +.x-panel-header-light-framed-horizontal { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:846 */ +.x-panel-header-light-framed-horizontal .x-panel-header-light-framed-tab-bar { + margin-top: -5px; + margin-bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:854 */ +.x-panel-header-light-framed-horizontal.x-header-noborder { + padding: 10px 10px 5px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:858 */ +.x-panel-header-light-framed-horizontal.x-header-noborder .x-panel-header-light-framed-tab-bar { + margin-top: -10px; + margin-bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:866 */ +.x-panel-header-light-framed-vertical { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:870 */ +.x-panel-header-light-framed-vertical .x-panel-header-light-framed-tab-bar { + margin-right: -5px; + margin-left: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:878 */ +.x-panel-header-light-framed-vertical.x-header-noborder { + padding: 10px 10px 10px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:882 */ +.x-panel-header-light-framed-vertical.x-header-noborder .x-panel-header-light-framed-tab-bar { + margin-right: -10px; + margin-left: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:916 */ +.x-panel-header-title-light-framed { + color: #666; + font-size: 13px; + font-weight: bold; + font-family: tahoma, verdana, sans-serif; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:929 */ +.x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus { + outline: 1px solid #157fcc; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #157fcc; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:950 */ +.x-panel-header-title-light-framed > .x-title-text-light-framed { + text-transform: none; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:997 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-top { + height: 22px; + padding-bottom: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1002 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-right { + width: 22px; + padding-left: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1014 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-bottom { + height: 22px; + padding-top: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1019 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-left { + width: 22px; + padding-right: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1031 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed { + width: 16px; + height: 16px; + font-size: 16px; + color: #666; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1038 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed.x-title-glyph { + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1051 */ +.x-ie8 .x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed.x-title-glyph { + color: #a3a8ac; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1062 */ +.x-panel-body-light-framed { + background: #fff; + border-color: #e0ebf3; + color: #000; + font-size: 13px; + font-weight: normal; + font-family: tahoma, verdana, sans-serif; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-light-framed { + -webkit-border-radius: 4px; + -moz-border-radius: 4px; + -ms-border-radius: 4px; + -o-border-radius: 4px; + border-radius: 4px; + padding: 0px 0px 0px 0px; + border-width: 5px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-light-framed-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-light-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-light-framed-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-0-0-0-0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-light-framed-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-light-framed-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-light-framed-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-light-framed-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-light-framed-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-light-framed-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-light-framed-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-light-framed-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-light-framed-tr, +.x-panel-light-framed-br, +.x-panel-light-framed-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-light-framed-tl, +.x-panel-light-framed-bl, +.x-panel-light-framed-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-light-framed-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-light-framed-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-light-framed-tl, +.x-panel-light-framed-bl, +.x-panel-light-framed-tr, +.x-panel-light-framed-br, +.x-panel-light-framed-tc, +.x-panel-light-framed-bc, +.x-panel-light-framed-ml, +.x-panel-light-framed-mr { + background-image: url(images/panel/panel-light-framed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-light-framed-ml, +.x-panel-light-framed-mr { + background-image: url(images/panel/panel-light-framed-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-light-framed-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-top { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 5px 5px 5px 5px; + border-width: 5px 5px 0 5px; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-top-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-top-frameInfo { + font-family: dh-5-5-0-5-5-5-0-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-top-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-top-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-top-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-top-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-top-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-top-tr, +.x-panel-header-light-framed-top-br, +.x-panel-header-light-framed-top-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-top-tl, +.x-panel-header-light-framed-top-bl, +.x-panel-header-light-framed-top-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-top-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-top-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-top-tl, +.x-panel-header-light-framed-top-bl, +.x-panel-header-light-framed-top-tr, +.x-panel-header-light-framed-top-br, +.x-panel-header-light-framed-top-tc, +.x-panel-header-light-framed-top-bc, +.x-panel-header-light-framed-top-ml, +.x-panel-header-light-framed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-top-ml, +.x-panel-header-light-framed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-top-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 5px 5px 5px 5px; + border-width: 5px 5px 5px 0; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-right-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-right-frameInfo { + font-family: dh-5-5-5-0-5-5-5-0-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-right-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-right-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-right-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-right-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-right-ml { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-right-mr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-right-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-right-tr, +.x-panel-header-light-framed-right-br, +.x-panel-header-light-framed-right-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-right-tl, +.x-panel-header-light-framed-right-bl, +.x-panel-header-light-framed-right-ml { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-right-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-right-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-right-tl, +.x-panel-header-light-framed-right-bl, +.x-panel-header-light-framed-right-tr, +.x-panel-header-light-framed-right-br, +.x-panel-header-light-framed-right-tc, +.x-panel-header-light-framed-right-bc, +.x-panel-header-light-framed-right-ml, +.x-panel-header-light-framed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-right-ml, +.x-panel-header-light-framed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-right-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 0 5px 5px 5px; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-bottom-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-bottom-frameInfo { + font-family: dh-0-5-5-5-0-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-bottom-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-bottom-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-bottom-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-bottom-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-bottom-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-bottom-tr, +.x-panel-header-light-framed-bottom-br, +.x-panel-header-light-framed-bottom-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-bottom-tl, +.x-panel-header-light-framed-bottom-bl, +.x-panel-header-light-framed-bottom-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-bottom-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-bottom-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-bottom-tl, +.x-panel-header-light-framed-bottom-bl, +.x-panel-header-light-framed-bottom-tr, +.x-panel-header-light-framed-bottom-br, +.x-panel-header-light-framed-bottom-tc, +.x-panel-header-light-framed-bottom-bc, +.x-panel-header-light-framed-bottom-ml, +.x-panel-header-light-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-bottom-ml, +.x-panel-header-light-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-bottom-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-left { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px 0 5px 5px; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-left-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-left-frameInfo { + font-family: dh-5-0-5-5-5-0-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-left-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-left-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-left-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-left-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-left-ml { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-left-mr { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-left-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-left-tr, +.x-panel-header-light-framed-left-br, +.x-panel-header-light-framed-left-mr { + padding-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-left-tl, +.x-panel-header-light-framed-left-bl, +.x-panel-header-light-framed-left-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-left-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-left-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-left-tl, +.x-panel-header-light-framed-left-bl, +.x-panel-header-light-framed-left-tr, +.x-panel-header-light-framed-left-br, +.x-panel-header-light-framed-left-tc, +.x-panel-header-light-framed-left-bc, +.x-panel-header-light-framed-left-ml, +.x-panel-header-light-framed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-left-ml, +.x-panel-header-light-framed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-left-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-collapsed-top { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-collapsed-top-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-collapsed-top-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-collapsed-top-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-collapsed-top-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-collapsed-top-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-collapsed-top-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-collapsed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-collapsed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-collapsed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-collapsed-top-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-collapsed-top-tr, +.x-panel-header-light-framed-collapsed-top-br, +.x-panel-header-light-framed-collapsed-top-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-collapsed-top-tl, +.x-panel-header-light-framed-collapsed-top-bl, +.x-panel-header-light-framed-collapsed-top-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-collapsed-top-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-collapsed-top-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-collapsed-top-tl, +.x-panel-header-light-framed-collapsed-top-bl, +.x-panel-header-light-framed-collapsed-top-tr, +.x-panel-header-light-framed-collapsed-top-br, +.x-panel-header-light-framed-collapsed-top-tc, +.x-panel-header-light-framed-collapsed-top-bc, +.x-panel-header-light-framed-collapsed-top-ml, +.x-panel-header-light-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-collapsed-top-ml, +.x-panel-header-light-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-collapsed-top-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-collapsed-right { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-collapsed-right-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-collapsed-right-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-collapsed-right-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-collapsed-right-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-collapsed-right-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-collapsed-right-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-collapsed-right-ml { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-collapsed-right-mr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-collapsed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-collapsed-right-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-collapsed-right-tr, +.x-panel-header-light-framed-collapsed-right-br, +.x-panel-header-light-framed-collapsed-right-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-collapsed-right-tl, +.x-panel-header-light-framed-collapsed-right-bl, +.x-panel-header-light-framed-collapsed-right-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-collapsed-right-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-collapsed-right-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-collapsed-right-tl, +.x-panel-header-light-framed-collapsed-right-bl, +.x-panel-header-light-framed-collapsed-right-tr, +.x-panel-header-light-framed-collapsed-right-br, +.x-panel-header-light-framed-collapsed-right-tc, +.x-panel-header-light-framed-collapsed-right-bc, +.x-panel-header-light-framed-collapsed-right-ml, +.x-panel-header-light-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-collapsed-right-ml, +.x-panel-header-light-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-collapsed-right-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-collapsed-bottom { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-collapsed-bottom-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-collapsed-bottom-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-collapsed-bottom-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-collapsed-bottom-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-collapsed-bottom-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-collapsed-bottom-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-collapsed-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-collapsed-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-collapsed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-collapsed-bottom-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-collapsed-bottom-tr, +.x-panel-header-light-framed-collapsed-bottom-br, +.x-panel-header-light-framed-collapsed-bottom-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-collapsed-bottom-tl, +.x-panel-header-light-framed-collapsed-bottom-bl, +.x-panel-header-light-framed-collapsed-bottom-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-collapsed-bottom-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-collapsed-bottom-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-collapsed-bottom-tl, +.x-panel-header-light-framed-collapsed-bottom-bl, +.x-panel-header-light-framed-collapsed-bottom-tr, +.x-panel-header-light-framed-collapsed-bottom-br, +.x-panel-header-light-framed-collapsed-bottom-tc, +.x-panel-header-light-framed-collapsed-bottom-bc, +.x-panel-header-light-framed-collapsed-bottom-ml, +.x-panel-header-light-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-collapsed-bottom-ml, +.x-panel-header-light-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-collapsed-bottom-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-collapsed-left { + -moz-border-radius-topleft: 4px; + -webkit-border-top-left-radius: 4px; + border-top-left-radius: 4px; + -moz-border-radius-topright: 4px; + -webkit-border-top-right-radius: 4px; + border-top-right-radius: 4px; + -moz-border-radius-bottomright: 4px; + -webkit-border-bottom-right-radius: 4px; + border-bottom-right-radius: 4px; + -moz-border-radius-bottomleft: 4px; + -webkit-border-bottom-left-radius: 4px; + border-bottom-left-radius: 4px; + padding: 5px 5px 5px 5px; + border-width: 5px; + border-style: solid; + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-collapsed-left-mc { + background-color: #e0ebf3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-collapsed-left-frameInfo { + font-family: dh-5-5-5-5-5-5-5-5-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-collapsed-left-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-collapsed-left-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-collapsed-left-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-collapsed-left-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-collapsed-left-ml { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-collapsed-left-mr { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-collapsed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-collapsed-left-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-collapsed-left-tr, +.x-panel-header-light-framed-collapsed-left-br, +.x-panel-header-light-framed-collapsed-left-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-collapsed-left-tl, +.x-panel-header-light-framed-collapsed-left-bl, +.x-panel-header-light-framed-collapsed-left-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-collapsed-left-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-collapsed-left-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-collapsed-left-tl, +.x-panel-header-light-framed-collapsed-left-bl, +.x-panel-header-light-framed-collapsed-left-tr, +.x-panel-header-light-framed-collapsed-left-br, +.x-panel-header-light-framed-collapsed-left-tc, +.x-panel-header-light-framed-collapsed-left-bc, +.x-panel-header-light-framed-collapsed-left-ml, +.x-panel-header-light-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-collapsed-left-ml, +.x-panel-header-light-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-collapsed-left-mc { + padding: 5px 5px 5px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1188 */ +.x-panel .x-panel-header-light-framed-top { + border-bottom-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1192 */ +.x-panel .x-panel-header-light-framed-right { + border-left-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1196 */ +.x-panel .x-panel-header-light-framed-bottom { + border-top-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1200 */ +.x-panel .x-panel-header-light-framed-left { + border-right-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1206 */ +.x-nbr .x-panel-header-light-framed-collapsed-top { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1210 */ +.x-nbr .x-panel-header-light-framed-collapsed-right { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1214 */ +.x-nbr .x-panel-header-light-framed-collapsed-bottom { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1218 */ +.x-nbr .x-panel-header-light-framed-collapsed-left { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1336 */ +.x-panel-header-light-framed-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1346 */ +.x-panel-header-light-framed-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1358 */ +.x-panel-header-light-framed-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1368 */ +.x-panel-header-light-framed-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1381 */ +.x-keyboard-mode .x-panel-header-light-framed .x-tool-focus { + outline: 1px solid #157fcc; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #157fcc; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1426 */ +.x-panel-light-framed-resizable { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1429 */ +.x-panel-light-framed-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1438 */ +.x-panel-light-framed-resizable .x-panel-handle-north-br { + top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1441 */ +.x-panel-light-framed-resizable .x-panel-handle-south-br { + bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1444 */ +.x-panel-light-framed-resizable .x-panel-handle-east-br { + right: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1447 */ +.x-panel-light-framed-resizable .x-panel-handle-west-br { + left: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1450 */ +.x-panel-light-framed-resizable .x-panel-handle-northwest-br { + left: -5px; + top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1454 */ +.x-panel-light-framed-resizable .x-panel-handle-northeast-br { + right: -5px; + top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1458 */ +.x-panel-light-framed-resizable .x-panel-handle-southeast-br { + right: -5px; + bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1462 */ +.x-panel-light-framed-resizable .x-panel-handle-southwest-br { + left: -5px; + bottom: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-panel-light-framed-outer-border-l { + border-left-color: #e0ebf3 !important; + border-left-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-panel-light-framed-outer-border-b { + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-panel-light-framed-outer-border-bl { + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 5px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-panel-light-framed-outer-border-r { + border-right-color: #e0ebf3 !important; + border-right-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-panel-light-framed-outer-border-rl { + border-right-color: #e0ebf3 !important; + border-right-width: 5px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-panel-light-framed-outer-border-rb { + border-right-color: #e0ebf3 !important; + border-right-width: 5px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-panel-light-framed-outer-border-rbl { + border-right-color: #e0ebf3 !important; + border-right-width: 5px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 5px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-panel-light-framed-outer-border-t { + border-top-color: #e0ebf3 !important; + border-top-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-panel-light-framed-outer-border-tl { + border-top-color: #e0ebf3 !important; + border-top-width: 5px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-panel-light-framed-outer-border-tb { + border-top-color: #e0ebf3 !important; + border-top-width: 5px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-panel-light-framed-outer-border-tbl { + border-top-color: #e0ebf3 !important; + border-top-width: 5px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 5px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-panel-light-framed-outer-border-tr { + border-top-color: #e0ebf3 !important; + border-top-width: 5px !important; + border-right-color: #e0ebf3 !important; + border-right-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-panel-light-framed-outer-border-trl { + border-top-color: #e0ebf3 !important; + border-top-width: 5px !important; + border-right-color: #e0ebf3 !important; + border-right-width: 5px !important; + border-left-color: #e0ebf3 !important; + border-left-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-panel-light-framed-outer-border-trb { + border-top-color: #e0ebf3 !important; + border-top-width: 5px !important; + border-right-color: #e0ebf3 !important; + border-right-width: 5px !important; + border-bottom-color: #e0ebf3 !important; + border-bottom-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-panel-light-framed-outer-border-trbl { + border-color: #e0ebf3 !important; + border-width: 5px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/form/field/File.scss:3 */ +.x-form-file-wrap .x-form-trigger-wrap { + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/form/field/File.scss:7 */ +.x-form-file-wrap .x-form-trigger-wrap .x-form-text { + border: 1px solid; + border-color: #c2c2c2 #dadada #dadada; + height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/form/field/File.scss:12 */ +.x-form-file-wrap .x-form-trigger-wrap .x-form-text.x-form-invalid-field { + border-color: #cf4c35; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/form/field/HtmlEditor.scss:1 */ +.x-html-editor-container { + border: 1px solid; + border-color: #c2c2c2 #dadada #dadada; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/grid/header/Container.scss:1 */ +.x-grid-header-ct { + border: 1px solid #c2c2c2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/grid/column/Column.scss:6 */ +.x-column-header-trigger { + background-color: #eff6fb; + border-left: 1px solid #c2c2c2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/grid/column/Column.scss:18 */ +.x-column-header-last { + border-right-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/grid/column/Column.scss:20 */ +.x-column-header-last .x-column-header-over .x-column-header-trigger { + border-right: 1px solid #c2c2c2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:1 */ +.x-resizable-handle { + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:6 */ +.x-resizable-handle-east-over, +.x-resizable-handle-west-over { + background-position: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:11 */ +.x-resizable-handle-south-over, +.x-resizable-handle-north-over { + background-position: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:16 */ +.x-resizable-handle-southeast-over { + background-position: -2px -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:20 */ +.x-resizable-handle-northwest-over { + background-position: 2px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:24 */ +.x-resizable-handle-northeast-over { + background-position: -2px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:28 */ +.x-resizable-handle-southwest-over { + background-position: 2px -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:33 */ +.x-resizable-pinned .x-resizable-handle-east, +.x-resizable-pinned .x-resizable-handle-west { + background-position: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:38 */ +.x-resizable-pinned .x-resizable-handle-south, +.x-resizable-pinned .x-resizable-handle-north { + background-position: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:43 */ +.x-resizable-pinned .x-resizable-handle-southeast { + background-position: -2px -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:47 */ +.x-resizable-pinned .x-resizable-handle-northwest { + background-position: 2px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:51 */ +.x-resizable-pinned .x-resizable-handle-northeast { + background-position: -2px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:55 */ +.x-resizable-pinned .x-resizable-handle-southwest { + background-position: 2px -2px; +} \ No newline at end of file diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all.css new file mode 100644 index 0000000..6ace102 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all.css @@ -0,0 +1,2 @@ +@import 'theme-neptune-all_1.css'; +@import 'theme-neptune-all_2.css'; diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all_1.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all_1.css new file mode 100644 index 0000000..f56dbc7 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all_1.css @@ -0,0 +1 @@ +.x-size-monitored{position:relative}.x-size-monitors{position:absolute;left:0;top:0;width:100%;height:100%;visibility:hidden;overflow:hidden}.x-size-monitors > *{width:100%;height:100%;overflow:hidden}.x-size-monitors.scroll > *.shrink::after{content:'';display:block;width:200%;height:200%;min-width:1px;min-height:1px}.x-size-monitors.scroll > *.expand::after{content:'';display:block;width:100000px;height:100000px}.x-size-monitors.overflowchanged > *.shrink > *{width:100%;height:100%}.x-size-monitors.overflowchanged > *.expand > *{width:200%;height:200%}.x-size-change-detector{visibility:hidden;position:absolute;left:0;top:0;z-index:-1;width:100%;height:100%;overflow:hidden}.x-size-change-detector > *{visibility:hidden}.x-size-change-detector-shrink > *{width:200%;height:200%}.x-size-change-detector-expand > *{width:100000px;height:100000px}@-webkit-keyframes x-paint-monitor-helper{from{zoom:1}to{zoom:1}}@keyframes x-paint-monitor-helper{from{zoom:1}to{zoom:1}}.x-paint-monitored{position:relative}.x-paint-monitor{width:0 !important;height:0 !important;visibility:hidden}.x-paint-monitor.cssanimation{-webkit-animation-duration:0.0001ms;-webkit-animation-name:x-paint-monitor-helper;animation-duration:0.0001ms;animation-name:x-paint-monitor-helper}.x-paint-monitor.overflowchange{overflow:hidden}.x-paint-monitor.overflowchange::after{content:'';display:block;width:1px !important;height:1px !important}.x-unselectable{user-select:none;-o-user-select:none;-ms-user-select:none;-moz-user-select:-moz-none;-webkit-user-select:none;-webkit-tap-highlight-color:transparent;-webkit-user-drag:none;cursor:default}.x-hidden-clip{position:absolute !important;clip:rect(0,0,0,0)}.x-hidden-display{display:none !important}.x-hidden-offsets,.x-hidden{display:block !important;visibility:hidden !important;position:absolute !important;top:-10000px !important}.x-hidden-opacity{opacity:0 !important;pointer-events:none}.x-hidden-visibility{visibility:hidden !important}.x-pressed .x-ripple-transition,.x-pressing .x-ripple-transition{transition:background-color 0.15s 0.2s cubic-bezier(0.4,0,0.2,1), color 0.15s 0.2s cubic-bezier(0.4,0,0.2,1)}.x-pressed .x-ripple-transition .x-icon-el,.x-pressed .x-ripple-transition .x-arrow-el,.x-pressing .x-ripple-transition .x-icon-el,.x-pressing .x-ripple-transition .x-arrow-el{transition:background-color 0.15s 0.2s cubic-bezier(0.4,0,0.2,1), color 0.15s 0.2s cubic-bezier(0.4,0,0.2,1)}.x-rippling{position:relative}.x-rippling.x-component-confirm .x-ripple{background-color:green}.x-rippling.x-component-decline .x-ripple{background-color:red}.x-rippling.x-rippling-unbound{overflow:visible !important}.x-rippling.x-rippling-unbound .x-ripple-container{overflow:visible;position:absolute}.x-safari .x-rippling:not(.x-rippling-unbound) .x-ripple-container{-webkit-transform:rotate(0);-moz-transform:rotate(0);-ms-transform:rotate(0);-o-transform:rotate(0);transform:rotate(0)}.x-ripple-container{overflow:hidden;position:absolute;top:0;bottom:0;left:0;right:0;pointer-events:none}.x-ripple-wrapper{z-index:1000}.x-button-fab .x-ripple-container,.x-button-round .x-ripple-container{border-radius:10000px}.x-splitButton-fab .x-ripple-container,.x-splitButton-round .x-ripple-container{border-radius:10000px}.x-ripple{position:absolute;border-radius:50%;background-color:white;-webkit-transform:scale(1,1);-moz-transform:scale(1,1);-ms-transform:scale(1,1);-o-transform:scale(1,1);transform:scale(1,1);opacity:0.4;pointer-events:none}.x-rippling.x-rippling-unbound .x-ripple{-webkit-animation:x-ripple-unbound-animation 0.3s ease-out forwards;animation:x-ripple-unbound-animation 0.3s ease-out forwards}.x-rippling:not(.x-rippling-unbound) .x-ripple{-webkit-animation:x-ripple-animation 0.35s ease-out forwards;animation:x-ripple-animation 0.35s ease-out forwards}@-webkit-keyframes x-ripple-animation{0%{-webkit-transform:scale(0,0);-moz-transform:scale(0,0);-ms-transform:scale(0,0);-o-transform:scale(0,0);transform:scale(0,0);opacity:0.4}75%{-webkit-transform:scale(2,2);-moz-transform:scale(2,2);-ms-transform:scale(2,2);-o-transform:scale(2,2);transform:scale(2,2);opacity:0.2}100%{-webkit-transform:scale(2.35,2.35);-moz-transform:scale(2.35,2.35);-ms-transform:scale(2.35,2.35);-o-transform:scale(2.35,2.35);transform:scale(2.35,2.35);opacity:0}}@keyframes x-ripple-animation{0%{-webkit-transform:scale(0,0);-moz-transform:scale(0,0);-ms-transform:scale(0,0);-o-transform:scale(0,0);transform:scale(0,0);opacity:0.4}75%{-webkit-transform:scale(2,2);-moz-transform:scale(2,2);-ms-transform:scale(2,2);-o-transform:scale(2,2);transform:scale(2,2);opacity:0.2}100%{-webkit-transform:scale(2.35,2.35);-moz-transform:scale(2.35,2.35);-ms-transform:scale(2.35,2.35);-o-transform:scale(2.35,2.35);transform:scale(2.35,2.35);opacity:0}}@-webkit-keyframes x-ripple-unbound-animation{0%{-webkit-transform:scale(0,0);-moz-transform:scale(0,0);-ms-transform:scale(0,0);-o-transform:scale(0,0);transform:scale(0,0);opacity:0.4}75%{-webkit-transform:scale(1.75,1.75);-moz-transform:scale(1.75,1.75);-ms-transform:scale(1.75,1.75);-o-transform:scale(1.75,1.75);transform:scale(1.75,1.75);opacity:0.2}100%{-webkit-transform:scale(2,2);-moz-transform:scale(2,2);-ms-transform:scale(2,2);-o-transform:scale(2,2);transform:scale(2,2);opacity:0}}@keyframes x-ripple-unbound-animation{0%{-webkit-transform:scale(0,0);-moz-transform:scale(0,0);-ms-transform:scale(0,0);-o-transform:scale(0,0);transform:scale(0,0);opacity:0.4}75%{-webkit-transform:scale(1.75,1.75);-moz-transform:scale(1.75,1.75);-ms-transform:scale(1.75,1.75);-o-transform:scale(1.75,1.75);transform:scale(1.75,1.75);opacity:0.2}100%{-webkit-transform:scale(2,2);-moz-transform:scale(2,2);-ms-transform:scale(2,2);-o-transform:scale(2,2);transform:scale(2,2);opacity:0}}.x-progress{overflow:hidden;position:relative}.x-progress-bar{height:100%;width:0}.x-progress-text{overflow:hidden}.x-progress-bar{overflow:hidden;position:absolute;top:0;right:0;bottom:0;left:0}.x-scroller{-webkit-overflow-scrolling:touch;overflow-anchor:none}.x-scroller-spacer{position:absolute;top:0;overflow:hidden;height:1px;width:1px;font-size:0;line-height:0;pointer-events:none}.x-scroller-snappable{-ms-scroll-snap-type:mandatory;-webkit-scroll-snap-type:mandatory;scroll-snap-type:mandatory}.x-no-scrollbars{-ms-overflow-style:none}.x-no-scrollbars::-webkit-scrollbar{width:0}.x-touch-action-pan-y{overflow-x:hidden !important}.x-touch-action-pan-x{overflow-y:hidden !important}.x-drag-body{cursor:default}.x-drag-body *{-webkit-user-select:none;-moz-user-select:none;user-select:none}.x-drag-dragging{z-index:1000000!important;pointer-events:none}.x-treelist{background-color:#fff;background-position:16px 0%;overflow:hidden;padding:0 0 0 0}.x-treelist-container,.x-treelist-root-container{width:100%}.x-treelist-toolstrip{display:none}.x-treelist-micro > .x-treelist-toolstrip{display:inline-block}.x-treelist-micro > .x-treelist-root-container{display:none}.x-treelist-item,.x-treelist-container,.x-treelist-root-container{position:relative;overflow:hidden;list-style:none;padding:0;margin:0}.x-treelist-item-tool,.x-treelist-row,.x-treelist-item-wrap{position:relative}.x-treelist-item-icon,.x-treelist-item-expander{display:none;position:absolute;top:0}.x-treelist-item-expander{right:0;cursor:pointer}.x-treelist-expander-only .x-treelist-item-expandable > * > .x-treelist-item-wrap > *{cursor:pointer}.x-treelist-item-text{cursor:pointer;white-space:nowrap;overflow:hidden}.x-treelist-item-collapsed > .x-treelist-container{display:none}.x-treelist-item-expandable > * > * > .x-treelist-item-expander,.x-treelist-item-icon{display:block}.x-treelist-item-floated > * > * > .x-treelist-item-expander,.x-treelist-item-floated > * > * > .x-treelist-item-icon{display:none}.x-treelist-expander-first .x-treelist-item-expander{left:0;right:auto}.x-treelist-toolstrip{background-color:#f8f8f8}.x-treelist-item-selected > .x-treelist-row{background-color:#c2ddf2}.x-treelist-item-selected > .x-treelist-row-over{background-color:#c2ddf2}.x-treelist-item-tool{padding-left:6px;padding-right:10px}.x-treelist-item-icon:before,.x-treelist-item-tool:before,.x-treelist-item-expander{line-height:24px}.x-treelist-item-icon,.x-treelist-item-tool,.x-treelist-item-expander{text-align:center;background-repeat:no-repeat;background-position:0 center}.x-treelist-item-loading .x-treelist-item-icon{background-image:url(images/tree/loading.gif);color:transparent}.x-treelist-item-icon,.x-treelist-item-tool{color:#b0b0b0;font-size:16px;width:16px}.x-treelist-item-tool{width:32px}.x-treelist-item-expander{color:#b0b0b0;font-size:16px;width:18px}.x-treelist-item-expander:after{content:"\f0da";font:16px/24px FontAwesome}.x-treelist-item-expanded > * > * > .x-treelist-item-expander:after{content:"\f0d7";font:16px/24px FontAwesome}.x-treelist-item-text{color:#000;margin-left:20px;margin-right:18px;font-size:13px;line-height:24px;text-overflow:ellipsis}.x-treelist-row{padding-left:6px;padding-right:10px}.x-treelist-item-floated .x-treelist-container{width:auto}.x-treelist-item-floated > .x-treelist-row{background-color:#f8f8f8}.x-treelist-item-floated > .x-treelist-container{margin-left:-6px}.x-big .x-treelist-item-floated > .x-treelist-container{margin-left:-6px}.x-treelist-item-floated > * > * > .x-treelist-item-text{margin-left:0}.x-treelist-item-floated > * .x-treelist-row{cursor:pointer;padding-left:0}.x-treelist-item-floated .x-treelist-row:before{width:0}.x-treelist-item-floated > .x-treelist-row-over{background-color:#f8f8f8}.x-treelist-item-floated > .x-treelist-row-over > * > .x-treelist-item-text{color:#000}.x-treelist-item-expanded > .x-treelist-item-expander:after{content:"\f0d7";font:16px/1 FontAwesome}.x-treelist-item-collapsed > * > .x-treelist-item-expander:after{content:"\f0da";font:16px/1 FontAwesome}.x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-icon{color:#b0b0b0;transition:color 0.5s}.x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-text{color:#000;transition:color 0.5s}.x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-expander{color:#b0b0b0;transition:color 0.5s}.x-treelist-row-over{background-color:#e2eff9;}.x-treelist-row-over > * > .x-treelist-item-icon{color:#b0b0b0;transition:color 0.5s}.x-treelist-row-over > * > .x-treelist-item-text{color:#000;transition:color 0.5s}.x-treelist-row-over > * > .x-treelist-item-expander{color:#b0b0b0;transition:color 0.5s}.x-treelist-expander-first .x-treelist-item-icon{left:18px}.x-treelist-expander-first .x-treelist-item-text{margin-left:38px;margin-right:0}.x-treelist-expander-first .x-treelist-item-hide-icon > * > * > .x-treelist-item-text{margin-left:20px}.x-treelist-item-hide-icon > * > * > .x-treelist-item-text{margin-left:2px}.x-treelist-nav{background-color:#32404e;background-position:24px 0%;padding:0 0 0 0}.x-treelist-nav .x-treelist-toolstrip{background-color:#32404e}.x-treelist-nav .x-treelist-item-selected.x-treelist-item-tool{color:#f0f0f0;background-color:#5fa2dd}.x-treelist-nav .x-treelist-item-selected > .x-treelist-row{background-color:#3f505f}.x-treelist-nav .x-treelist-item-tool{padding-left:10px;padding-right:10px}.x-treelist-nav .x-treelist-item-tool-floated:after{height:44px;position:absolute;top:0;left:0;content:" ";width:4px;background-color:#5fa2dd}.x-treelist-nav .x-treelist-item-icon:before,.x-treelist-nav .x-treelist-item-tool:before,.x-treelist-nav .x-treelist-item-expander{line-height:44px}.x-treelist-nav .x-treelist-item-icon,.x-treelist-nav .x-treelist-item-tool,.x-treelist-nav .x-treelist-item-expander{text-align:center;background-repeat:no-repeat;background-position:0 center}.x-treelist-nav .x-treelist-item-loading .x-treelist-item-icon{background-image:url(images/tree/loading.gif);color:transparent}.x-treelist-nav .x-treelist-item-icon,.x-treelist-nav .x-treelist-item-tool{color:#adb3b8;font-size:18px;width:24px}.x-treelist-nav .x-treelist-item-tool{width:44px}.x-treelist-nav .x-treelist-item-expander{color:#adb3b8;font-size:16px;width:24px}.x-treelist-nav .x-treelist-item-text{color:#adb3b8;margin-left:28px;margin-right:24px;font-size:16px;line-height:44px}.x-treelist-nav .x-treelist-row{padding-left:10px;padding-right:10px}.x-treelist-nav .x-treelist-row-over:before,.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before{content:" ";position:absolute;display:block;left:0;top:0;width:6px;height:100%}.x-treelist-nav .x-treelist-row-over:before{background-color:#2b99e9}.x-treelist-nav .x-treelist-item-selected > .x-treelist-row-over:before{background-color:#2b99e9}.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before{background-color:#157fcc}.x-treelist-nav .x-treelist-item-floated .x-treelist-container{width:auto}.x-treelist-nav .x-treelist-item-floated > .x-treelist-row{background-color:#32404e}.x-treelist-nav .x-treelist-item-floated > .x-treelist-container{margin-left:-10px}.x-big .x-treelist-nav .x-treelist-item-floated > .x-treelist-container{margin-left:-10px}.x-treelist-nav .x-treelist-item-floated > * > * > .x-treelist-item-text{margin-left:0}.x-treelist-nav .x-treelist-item-floated > * .x-treelist-row{cursor:pointer;padding-left:0}.x-treelist-nav .x-treelist-item-floated .x-treelist-row:before{width:0}.x-treelist-nav .x-treelist-item-floated > .x-treelist-row-over{background-color:#32404e}.x-treelist-nav .x-treelist-item-floated > .x-treelist-row-over > * > .x-treelist-item-text{color:#adb3b8}.x-treelist-nav .x-treelist-item-expanded{background-color:#2c3845}.x-treelist-nav .x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-icon{color:#fff}.x-treelist-nav .x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-text{color:#fff}.x-treelist-nav .x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-expander{color:#fff}.x-treelist-nav .x-treelist-row-over{background-color:#4f606f}.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-icon{color:#fff}.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-text{color:#fff}.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-expander{color:#fff}.x-treelist-nav .x-treelist-expander-first .x-treelist-item-icon{left:24px}.x-treelist-nav .x-treelist-expander-first .x-treelist-item-text{margin-left:52px;margin-right:0}.x-treelist-nav .x-treelist-expander-first .x-treelist-item-hide-icon > * > * > .x-treelist-item-text{margin-left:26px}.x-treelist-nav .x-treelist-item-hide-icon > * > * > .x-treelist-item-text{margin-left:2px}.x-body{margin:0;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}@-ms-viewport{width:device-width}img{border:0}.x-border-box,.x-border-box *{box-sizing:border-box;-moz-box-sizing:border-box;-ms-box-sizing:border-box;-webkit-box-sizing:border-box}.x-ltr{direction:ltr}.x-clear{overflow:hidden;clear:both;font-size:0;line-height:0;display:table}.x-layer{position:absolute !important;top:0;left:0;overflow:hidden}.x-fixed-layer{position:fixed !important;overflow:hidden}.x-shim{position:absolute;left:0;top:0;overflow:hidden;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-hidden-clip{position:absolute !important;clip:rect(0,0,0,0)}.x-masked-relative{position:relative}.x-ie-shadow{background-color:#777;position:absolute;overflow:hidden}.x-selectable{cursor:auto;-moz-user-select:text;-webkit-user-select:text;-ms-user-select:text;user-select:text;-o-user-select:text}.x-list-plain{list-style-type:none;margin:0;padding:0}.x-table-plain{border-collapse:collapse;border-spacing:0;font-size:1em}.x-frame-tl,.x-frame-tr,.x-frame-tc,.x-frame-bl,.x-frame-br,.x-frame-bc{overflow:hidden;background-repeat:no-repeat}.x-frame-tc,.x-frame-bc{background-repeat:repeat-x}td.x-frame-tl,td.x-frame-tr,td.x-frame-bl,td.x-frame-br{width:1px}.x-frame-mc{background-repeat:repeat-x;overflow:hidden}.x-proxy-el{position:absolute;background:#b4b4b4;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=80)";opacity:0.8}.x-css-shadow{position:absolute;-webkit-border-radius:5px;-moz-border-radius:5px;-ms-border-radius:5px;-o-border-radius:5px;border-radius:5px}.x-item-disabled,.x-item-disabled *{cursor:default;pointer-events:none}.x-component,.x-container{position:relative}:focus{outline:none}.x-body .x-sync-repaint:before,.x-body .x-sync-repaint:after{content:none !important}.x-position-relative{position:relative !important}.x-tab-guard{position:absolute;clip:rect(0,0,0,0)}.x-box-item{position:absolute !important;left:0;top:0}.x-autocontainer-outerCt{display:table}.x-mobile-safari .x-autocontainer-outerCt{transform:translateZ(0)}.x-clipped .x-autocontainer-outerCt{transform:initial}.x-autocontainer-innerCt{display:table-cell;height:100%;vertical-align:top}.x-mask{z-index:100;position:absolute;top:0;left:0;width:100%;height:100%;outline:none !important}.x-ie8 .x-mask{background-image:url(data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7)}.x-mask-fixed{position:fixed}.x-mask-msg{position:absolute}.x-progress{border-style:solid}.x-btn{display:inline-block;outline:0;cursor:pointer;white-space:nowrap;text-decoration:none;vertical-align:top;overflow:hidden;position:relative}.x-btn > .x-frame{height:100%;width:100%}.x-btn-wrap{height:100%;width:100%;display:-webkit-box;display:-ms-flexbox;display:flex;-webkit-box-align:stretch;-ms-flex-align:stretch;align-items:stretch}.x-btn-wrap.x-btn-arrow-bottom,.x-btn-wrap.x-btn-split-bottom{-webkit-box-orient:vertical;-ms-flex-direction:column;flex-direction:column}.x-ie9m .x-btn-wrap{display:table;border-spacing:0}.x-btn-button{white-space:nowrap;line-height:0;position:relative;display:-webkit-box;display:-ms-flexbox;display:flex;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-box-flex:1;-ms-flex:1 1 auto;flex:1 1 auto;min-width:0}.x-btn-button.x-btn-icon-top,.x-btn-button.x-btn-icon-bottom{-webkit-box-orient:vertical;-ms-flex-direction:column;flex-direction:column;-webkit-box-align:stretch;-ms-flex-align:stretch;align-items:stretch;-webkit-box-pack:center;-ms-flex-pack:center;justify-content:center}.x-ie10p .x-btn-button.x-btn-icon-top,.x-ie10p .x-btn-button.x-btn-icon-bottom{overflow:hidden}.x-ie9m .x-btn-button{display:table-cell;vertical-align:middle}.x-btn-inner{overflow:hidden;text-overflow:ellipsis;-ms-flex-negative:1;display:block}.x-ie9m .x-btn-inner{display:inline-block;vertical-align:middle}.x-btn-icon.x-btn-no-text > .x-btn-inner{display:none}.x-btn-icon-el{display:none;vertical-align:middle;text-align:center;background-position:center center;background-repeat:no-repeat;flex-shrink:0}.x-btn-icon > .x-btn-icon-el{display:block}.x-ie9m .x-btn-icon-left > .x-btn-icon-el,.x-ie9m .x-btn-icon-right > .x-btn-icon-el{display:inline-block}.x-btn-button-center{-webkit-box-pack:center;-ms-flex-pack:center;justify-content:center}.x-ie9m .x-btn-button-center{text-align:center}.x-btn-button-center.x-btn-icon-top,.x-btn-button-center.x-btn-icon-bottom{text-align:center}.x-btn-button-left{text-align:left;-webkit-box-pack:start;-ms-flex-pack:start;justify-content:flex-start}.x-btn-button-right{text-align:right;-webkit-box-pack:end;-ms-flex-pack:end;justify-content:flex-end}.x-btn-arrow:after,.x-btn-split:after{display:block;background-repeat:no-repeat;content:'';box-sizing:border-box;-moz-box-sizing:border-box;-ms-box-sizing:border-box;-webkit-box-sizing:border-box;text-align:center}.x-btn-arrow-right:after,.x-btn-split-right:after{background-position:right center;display:-webkit-box;display:-ms-flexbox;display:flex;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-box-pack:center;-ms-flex-pack:center;justify-content:center}.x-ie9m .x-btn-arrow-right:after,.x-ie9m .x-btn-split-right:after{display:table-cell;vertical-align:middle}.x-btn-arrow-bottom:after,.x-btn-split-bottom:after{background-position:center bottom;content:'\00a0';line-height:0}.x-ie9m .x-btn-arrow-bottom:after,.x-ie9m .x-btn-split-bottom:after{display:table-row}.x-btn-split-right > .x-btn-button:after{position:absolute;display:block;top:-100%;right:0;height:300%;content:''}.x-btn-split-bottom > .x-btn-button:after{position:absolute;display:block;bottom:0;left:-100%;font-size:0;width:300%;content:''}.x-btn-mc{overflow:visible}.x-segmented-button{display:table;table-layout:fixed}.x-segmented-button-item{display:table-cell;vertical-align:top}.x-segmented-button-item > .x-frame{width:100%;height:100%}.x-segmented-button-item .x-btn-mc{width:100%}.x-segmented-button-item-horizontal{display:table-cell;height:100%}.x-segmented-button-item-horizontal.x-segmented-button-first{border-top-right-radius:0;border-bottom-right-radius:0}.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-tr,.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-mr,.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-br{display:none}.x-segmented-button-item-horizontal.x-segmented-button-middle{border-radius:0;border-left:0}.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tl,.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tr,.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-ml,.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-mr,.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-bl,.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-br{display:none}.x-segmented-button-item-horizontal.x-segmented-button-last{border-left:0;border-top-left-radius:0;border-bottom-left-radius:0}.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-tl,.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-ml,.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-bl{display:none}.x-segmented-button-row{display:table-row}.x-segmented-button-item-vertical.x-segmented-button-first{border-bottom-right-radius:0;border-bottom-left-radius:0}.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bl,.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bc,.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-br{display:none}.x-segmented-button-item-vertical.x-segmented-button-middle{border-radius:0;border-top:0}.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tl,.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tc,.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tr,.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bl,.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bc,.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-br{display:none}.x-segmented-button-item-vertical.x-segmented-button-last{border-top:0;border-top-right-radius:0;border-top-left-radius:0}.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tl,.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tc,.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tr{display:none}.x-title-icon{background-repeat:no-repeat;background-position:0 0;vertical-align:middle;line-height:1;text-align:center}.x-title{display:table;table-layout:fixed}.x-title-text{display:table-cell;overflow:hidden;white-space:nowrap;-o-text-overflow:ellipsis;text-overflow:ellipsis;vertical-align:middle}.x-title-align-left{text-align:left}.x-title-align-center{text-align:center}.x-title-align-right{text-align:right}.x-title-rotate-right{-webkit-transform:rotate(90deg);-webkit-transform-origin:0 0;-moz-transform:rotate(90deg);-moz-transform-origin:0 0;-ms-transform:rotate(90deg);-ms-transform-origin:0 0;transform:rotate(90deg);transform-origin:0 0}.x-ie8 .x-title-rotate-right{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"}.x-title-rotate-left{-webkit-transform:rotate(270deg);-webkit-transform-origin:100% 0;-moz-transform:rotate(270deg);-moz-transform-origin:100% 0;-ms-transform:rotate(270deg);-ms-transform-origin:100% 0;transform:rotate(270deg);transform-origin:100% 0}.x-ie8 .x-title-rotate-left{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"}.x-horizontal.x-header .x-title-rotate-right.x-title-align-left > .x-title-item{vertical-align:bottom}.x-horizontal.x-header .x-title-rotate-right.x-title-align-center > .x-title-item{vertical-align:middle}.x-horizontal.x-header .x-title-rotate-right.x-title-align-right > .x-title-item{vertical-align:top}.x-horizontal.x-header .x-title-rotate-left.x-title-align-left > .x-title-item{vertical-align:top}.x-horizontal.x-header .x-title-rotate-left.x-title-align-center > .x-title-item{vertical-align:middle}.x-horizontal.x-header .x-title-rotate-left.x-title-align-right > .x-title-item{vertical-align:bottom}.x-vertical.x-header .x-title-rotate-none.x-title-align-left > .x-title-item{vertical-align:top}.x-vertical.x-header .x-title-rotate-none.x-title-align-center > .x-title-item{vertical-align:middle}.x-vertical.x-header .x-title-rotate-none.x-title-align-right > .x-title-item{vertical-align:bottom}.x-title-icon-wrap{display:table-cell;text-align:center;vertical-align:middle;line-height:0}.x-title-icon-wrap.x-title-icon-top,.x-title-icon-wrap.x-title-icon-bottom{display:table-row}.x-title-icon{display:inline-block;vertical-align:middle;background-position:center;background-repeat:no-repeat}.x-tool{font-size:16px;line-height:1}.x-header > .x-box-inner,.x-panel-header-mc > .x-box-inner,.x-window-header-mc > .x-box-inner{overflow:visible}.x-splitter{font-size:1px}.x-splitter-horizontal{cursor:e-resize;cursor:row-resize}.x-splitter-vertical{cursor:e-resize;cursor:col-resize}.x-splitter-collapsed,.x-splitter-horizontal-noresize,.x-splitter-vertical-noresize{cursor:default}.x-splitter-active{z-index:4}.x-collapse-el{position:absolute;background-repeat:no-repeat}.x-splitter-focus{z-index:4}.x-box-layout-ct{overflow:hidden}.x-box-target{position:absolute;width:20000px;top:0;left:0;min-height:1px}.x-box-inner{overflow:hidden;position:relative;left:0;top:0}.x-box-scroller{position:absolute;background-repeat:no-repeat;background-position:center;line-height:0;font-size:0;text-align:center}.x-box-scroller-top{top:0}.x-box-scroller-right{right:0}.x-box-scroller-bottom{bottom:0}.x-box-scroller-left{left:0}.x-box-menu-body-horizontal{float:left}.x-box-menu-after{position:relative;float:left}.x-box-scroller-body-vertical,.x-box-scroller-body-horizontal{-ms-overflow-style:none}.x-box-scroller-body-vertical .x-scroller,.x-box-scroller-body-horizontal .x-scroller{-ms-overflow-style:auto}.x-box-scroller-body-vertical :not(.x-scroller)::-webkit-scrollbar,.x-box-scroller-body-horizontal :not(.x-scroller)::-webkit-scrollbar{display:none}.x-toolbar-text{white-space:nowrap}.x-toolbar-separator{display:block;font-size:1px;overflow:hidden;cursor:default;border:0;width:0;height:0;line-height:0px}.x-toolbar-scroller{padding-left:0}.x-toolbar-plain{border:0}.x-dd-drag-proxy,.x-dd-drag-current{z-index:1000000!important;pointer-events:none}.x-dd-drag-proxy{display:table}.x-dd-drag-repair .x-dd-drag-ghost{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-dd-drag-repair .x-dd-drop-icon{display:none}.x-dd-drag-ghost,.x-dd-drop-icon{display:table-cell;vertical-align:middle}.x-dd-drag-ghost{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=85)";opacity:0.85;white-space:nowrap}.x-dd-drop-icon{height:26px;width:26px;background-color:transparent;background-position:center;background-repeat:no-repeat}.x-docked{position:absolute !important;z-index:2}.x-docked-vertical{position:static}.x-docked-top{border-bottom-width:0 !important}.x-docked-bottom{border-top-width:0 !important}.x-docked-left{border-right-width:0 !important}.x-docked-right{border-left-width:0 !important}.x-docked-noborder-top{border-top-width:0 !important}.x-docked-noborder-right{border-right-width:0 !important}.x-docked-noborder-bottom{border-bottom-width:0 !important}.x-docked-noborder-left{border-left-width:0 !important}.x-noborder-l{border-left-width:0 !important}.x-noborder-b{border-bottom-width:0 !important}.x-noborder-bl{border-bottom-width:0 !important;border-left-width:0 !important}.x-noborder-r{border-right-width:0 !important}.x-noborder-rl{border-right-width:0 !important;border-left-width:0 !important}.x-noborder-rb{border-right-width:0 !important;border-bottom-width:0 !important}.x-noborder-rbl{border-right-width:0 !important;border-bottom-width:0 !important;border-left-width:0 !important}.x-noborder-t{border-top-width:0 !important}.x-noborder-tl{border-top-width:0 !important;border-left-width:0 !important}.x-noborder-tb{border-top-width:0 !important;border-bottom-width:0 !important}.x-noborder-tbl{border-top-width:0 !important;border-bottom-width:0 !important;border-left-width:0 !important}.x-noborder-tr{border-top-width:0 !important;border-right-width:0 !important}.x-noborder-trl{border-top-width:0 !important;border-right-width:0 !important;border-left-width:0 !important}.x-noborder-trb{border-top-width:0 !important;border-right-width:0 !important;border-bottom-width:0 !important}.x-noborder-trbl{border-width:0 !important}.x-panel,.x-plain{overflow:hidden;position:relative}.x-panel{outline:none}td.x-frame-mc{vertical-align:top}.x-panel-bodyWrap{overflow:hidden;position:static;height:100%;width:100%}.x-panel-body{overflow:hidden;position:relative}.x-panel-header-plain,.x-panel-body-plain{border:0;padding:0}.x-panel-collapsed-mini{visibility:hidden}.x-viewport > .x-body.x-panel > .x-panel-bodyWrap{position:absolute;top:0;right:0;bottom:0;left:0}.x-table-layout{font-size:1em}.x-btn-group{position:relative;overflow:hidden}.x-btn-group-body{position:relative}.x-btn-group-body .x-table-layout-cell{vertical-align:top}.x-viewport,.x-viewport > .x-body{margin:0;padding:0;border:0 none}.x-viewport{width:100%;height:100%;position:static}.x-viewport > .x-body{position:fixed;top:0;left:0;min-width:100%;min-height:100%}@media print{.x-viewport > .x-body{position:static}}.x-column{float:left}.x-resizable-overlay{position:absolute;left:0;top:0;width:100%;height:100%;display:none;z-index:200000;background-color:#fff;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-window{outline:none;overflow:hidden}.x-window .x-window-wrap{position:relative}.x-window-body{position:relative;overflow:hidden}.x-form-item{display:table;table-layout:fixed;border-spacing:0;border-collapse:separate}.x-form-item-label{overflow:hidden}.x-form-item.x-form-item-no-label > .x-form-item-label{display:none}.x-form-item-label,.x-form-item-body{display:table-cell}.x-form-item-body{vertical-align:middle;height:100%}.x-form-item-label-inner{display:inline-block}.x-form-item-label-top{display:table-row;height:1px}.x-form-item-label-top > .x-form-item-label-inner{display:table-cell}.x-form-item-label-top-side-error:after{display:table-cell;content:''}.x-form-item-label-right{text-align:right}.x-form-error-wrap-side{display:table-cell;vertical-align:middle}.x-form-error-wrap-under{display:table-row;height:1px}.x-form-error-wrap-under > .x-form-error-msg{display:table-cell}.x-form-error-wrap-under-side-label:before{display:table-cell;content:'';pointer-events:none}.x-form-invalid-icon{overflow:hidden}.x-form-invalid-icon ul{display:none}.x-form-trigger-wrap{display:table;width:100%}.x-form-text-heighted .x-form-trigger-wrap{height:100%}.x-gecko .x-form-trigger-wrap{display:-moz-inline-box;display:inline-flex;vertical-align:top}.x-form-type-text.x-has-min-height{height:1px}.x-form-type-text.x-has-min-height .x-form-text-field-body,.x-form-type-text.x-has-min-height .x-form-trigger-wrap,.x-form-type-text.x-has-min-height .x-form-text-wrap{min-height:inherit}.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-field-body,.x-ie8 .x-form-type-text.x-has-min-height .x-form-trigger-wrap,.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-wrap{min-height:inherit}.x-ie8 .x-form-type-text.x-has-min-height .x-form-text{min-height:inherit}.x-form-type-text.x-has-min-height .x-form-text{height:100%}.x-form-text-wrap{display:table-cell;overflow:hidden;height:100%;position:relative}.x-gecko .x-form-text-wrap{display:block;-moz-box-flex:1;flex:1}.x-form-text-wrap .x-placeholder-label{position:absolute;top:0;left:0;cursor:text;white-space:nowrap;overflow:hidden}.x-form-item-body.x-form-text-grow{min-width:inherit;max-width:inherit}.x-form-text{border:0;margin:0;-webkit-border-radius:0;-moz-border-radius:0;-ms-border-radius:0;-o-border-radius:0;border-radius:0;display:block;background:repeat-x 0 0;width:100%;height:100%}.x-form-trigger{display:table-cell;vertical-align:top;cursor:pointer;overflow:hidden;background-repeat:no-repeat;text-align:center;line-height:0;white-space:nowrap}.x-item-disabled .x-form-trigger{cursor:default}.x-form-trigger.x-form-trigger-cmp{background:none;border:0}.x-gecko .x-form-trigger{display:block}.x-form-textarea-body.x-form-text-grow > .x-form-trigger-wrap{height:100%}.x-form-textarea{overflow:auto;resize:none}div.x-form-text-grow .x-form-textarea{min-height:inherit}.x-message-box .x-form-display-field{height:auto}.x-safari .x-form-fieldcontainer{table-layout:auto}.x-ie8 .x-form-fieldcontainer > .x-form-item-body.x-field-container-body-vertical{display:table-row}.x-form-cb-wrap{vertical-align:top}.x-form-cb-wrap-inner{position:relative}.x-form-cb{position:absolute;left:0;right:auto;vertical-align:top;overflow:hidden;padding:0;border:0}.x-form-cb::-moz-focus-inner{padding:0;border:0}.x-form-cb-input{position:absolute;margin:0;padding:0;border:0;top:0;left:0;width:100%;height:100%;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-form-cb-after{left:auto;right:0}.x-form-cb-label{display:inline-block}.x-form-cb-label.x-form-cb-no-box-label{display:none}.x-fieldset{display:block;position:relative;overflow:hidden}.x-fieldset-header{overflow:hidden}.x-fieldset-header .x-form-item,.x-fieldset-header .x-tool{float:left}.x-fieldset-header .x-fieldset-header-text{float:left}.x-fieldset-header .x-form-cb-wrap{font-size:0;line-height:0;min-height:0;height:auto}.x-fieldset-header .x-form-cb{margin:0;position:static;display:inherit}.x-fieldset-body{overflow:hidden}.x-fieldset-collapsed{padding-bottom:0 !important}.x-fieldset-collapsed > .x-fieldset-body{display:none}.x-fieldset-header-text-collapsible{cursor:pointer}.x-keyboard-mode .x-view-item-focused{outline:1px dashed #157fcc !important;outline-offset:-1px}.x-ie9 .x-boundlist-list-ct{min-height:0%}.x-datepicker{position:relative}.x-datepicker .x-monthpicker{left:0;top:0;display:block}.x-datepicker .x-monthpicker-months,.x-datepicker .x-monthpicker-years{height:100%}.x-datepicker-inner{table-layout:fixed;width:100%;border-collapse:separate}.x-datepicker-cell{padding:0}.x-datepicker-header{position:relative}.x-datepicker-arrow{position:absolute;outline:none;font-size:0}.x-datepicker-column-header{padding:0}.x-datepicker-date{display:block;text-decoration:none}.x-monthpicker{display:table}.x-monthpicker-body{height:100%;position:relative}.x-monthpicker-months,.x-monthpicker-years{float:left}.x-monthpicker-item{float:left}.x-monthpicker-item-inner{display:block;text-decoration:none}.x-monthpicker-yearnav-button-ct{float:left;text-align:center}.x-monthpicker-yearnav-button{display:inline-block;outline:none;font-size:0}.x-monthpicker-buttons{width:100%}.x-datepicker .x-monthpicker-buttons{position:absolute;bottom:0}.x-datepicker-month .x-btn-split > .x-btn-button:after{content:none}.x-form-display-field-body{vertical-align:top}.x-form-display-field-body .x-form-display-field{overflow-wrap:break-word;word-wrap:break-word;-ms-word-break:break-all;word-break:break-all;word-break:break-word;-ms-hyphens:auto;-moz-hyphens:auto;-webkit-hyphens:auto;hyphens:auto}.x-form-file-btn{overflow:hidden;position:relative}.x-form-file-input{border:0;position:absolute;cursor:pointer;top:0;right:0;width:100%;height:100%;overflow:hidden;text-indent:-10000px;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0;font-size:1000px}.x-form-item-hidden{margin:0}.x-tip{position:absolute;overflow:visible}.x-tip-body{overflow:hidden;position:relative}.x-tip-anchor{position:absolute;border-style:solid;height:0;width:0}.x-color-picker-item{float:left;text-decoration:none}.x-color-picker-item-inner{display:block;font-size:1px}.x-html-editor-tb .x-toolbar{position:static !important}.x-htmleditor-iframe,.x-htmleditor-textarea{display:block;overflow:auto;width:100%;height:100%;border:0}.x-tagfield-body{vertical-align:top}.x-tagfield{height:auto!important;cursor:text;overflow-y:auto}.x-tagfield .x-tagfield-list{padding:0;margin:0}.x-tagfield-list.x-tagfield-singleselect{white-space:nowrap;overflow:hidden}.x-tagfield-input,.x-tagfield-item{vertical-align:top;display:inline-block;position:relative}.x-tagfield-input-field{font:inherit;border:0;margin:0;background:none;width:100%}.x-tagfield-stacked .x-tagfield-item{display:block}.x-tagfield-item{cursor:default}.x-tagfield-item-close{cursor:pointer;position:absolute}.x-tagfield-arialist{list-style-type:none;position:absolute;clip:rect(0,0,0,0)}.x-tagfield-arialist-item{list-style-type:none}.x-fit-item{position:relative}.x-grid-view{overflow:hidden;position:relative}.x-grid-row-table{width:0;table-layout:fixed;border:0 none;border-collapse:separate;border-spacing:0}.x-grid-item{table-layout:fixed;outline:none;position:relative}.x-ie10 .x-grid-item{transform:translateZ(0)}.x-grid-row{outline:none}.x-grid-td{overflow:hidden;border-width:0;vertical-align:top}.x-grid-cell-inner{overflow:hidden;white-space:nowrap}.x-wrap-cell .x-grid-cell-inner{white-space:normal}.x-grid-resize-marker{position:absolute;z-index:5;top:0}.x-grid-item-container{min-height:1px;position:relative}.x-col-move-top,.x-col-move-bottom{position:absolute;top:0;line-height:0;font-size:0;overflow:hidden;z-index:20000;background:no-repeat center top transparent}.x-grid-header-ct{cursor:default}.x-column-header{position:absolute;overflow:hidden;background-repeat:repeat-x}.x-column-header-inner{white-space:nowrap;position:relative;overflow:hidden}.x-leaf-column-header{height:100%}.x-leaf-column-header .x-column-header-text-container{height:100%}.x-column-header-text-container{width:100%;display:table;table-layout:fixed}.x-column-header-text-container.x-column-header-text-container-auto{table-layout:auto}.x-column-header-text-wrapper{display:table-cell;vertical-align:middle}.x-column-header-text{display:block;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.x-column-header-sort-DESC .x-column-header-text,.x-column-header-sort-ASC .x-column-header-text{overflow:visible}.x-column-header-text-inner{background-repeat:no-repeat}.x-column-header-inner-empty .x-column-header-text-inner{display:none}.x-column-header-inner-empty .x-column-header-text-container{line-height:0}.x-column-header-trigger{display:none;height:100%;background-repeat:no-repeat;position:absolute;right:0;top:0;text-align:center}.x-ie9m .x-column-header-trigger{z-index:6}.x-column-header-over .x-column-header-trigger,.x-column-header-open .x-column-header-trigger{display:block}.x-column-header-align-right{text-align:right}.x-column-header-align-left{text-align:left}.x-column-header-align-center{text-align:center}.x-grid-cell-inner-action-col{line-height:0;font-size:0}.x-keyboard-mode .x-grid-cell-inner-action-col :focus{outline:1px solid #3d92cf}.x-action-col-icon{display:inline-block;line-height:1}.x-column-header-checkbox .x-column-header-text{margin-bottom:0.4em}.x-column-header-checkbox .x-column-header-inner-empty .x-column-header-text{margin-bottom:0}.x-grid-checkcolumn-cell-inner{line-height:0}.x-keyboard-mode .x-grid-checkcolumn-cell-inner :focus{outline:1px solid #3d92cf}.x-group-hd-container{overflow:hidden}.x-grid-group-hd{white-space:nowrap;outline:none}.x-grid-group-title{position:relative}.x-grid-row-body-hidden,.x-grid-group-collapsed{display:none}.x-grid-row-body-hidden{display:none}.x-menu{outline:none}.x-menu-body{position:relative}.x-menu-item{white-space:nowrap;overflow:hidden;border-color:transparent;border-style:solid}.x-menu-item-cmp{margin:2px}.x-menu-item-cmp .x-field-label-cell{vertical-align:middle}.x-menu-icon-separator{position:absolute;top:0px;z-index:0;height:100%;overflow:hidden}.x-menu-plain .x-menu-icon-separator{display:none}.x-menu-item-link{-webkit-tap-highlight-color:transparent;-webkit-touch-callout:none;text-decoration:none;outline:0;display:block}.x-menu-item-link-href{-webkit-touch-callout:default}.x-menu-item-text{display:inline-block}.x-menu-item-icon,.x-menu-item-icon-right,.x-menu-item-arrow{font-size:0;position:absolute;text-align:center;background-repeat:no-repeat}.x-grid-scroll-container{position:absolute;z-index:1}.x-grid-scrollbar-clipper-floated,.x-grid-scrollbar-floated{z-index:2}.x-grid-scroll-body{width:100%;position:relative}.x-grid-scrollbar-clipper{overflow:hidden;position:absolute;top:0;left:0}.x-grid-scrollbar-clipper > .x-grid-view,.x-grid-scrollbar-clipper > .x-tree-view{overflow-y:hidden !important}.x-grid-with-col-lines .x-grid-scrollbar-clipper-locked .x-grid-cell-last{border-right-width:0}.x-grid-scrollbar{position:absolute;bottom:0;left:0;display:none}.x-grid-scrollbar-visible{display:block}.x-grid-locking-body > .x-grid{z-index:2;pointer-events:none}.x-grid-locking-body > .x-grid .x-docked{pointer-events:auto}.x-grid-locking-body .x-grid-body{background:transparent}.x-grid-locking-body > .x-splitter{z-index:2}.x-grid-locking-body > .x-splitter-active{z-index:4}.x-grid-locking-body > .x-splitter-focus{z-index:4}.x-grid-inner-locked.x-border-region-slide-in{z-index:3}.x-grid-inner-locked.x-border-region-slide-in > .x-panel-bodyWrap > .x-grid-body > .x-grid-view,.x-grid-inner-locked.x-border-region-slide-in > .x-panel-bodyWrap > .x-grid-body > .x-tree-view{overflow-y:hidden !important}.x-grid-editor .x-form-cb-wrap{text-align:center}.x-grid-editor .x-form-cb{position:static;display:inline-block}.x-grid-editor .x-form-display-field{margin:0;white-space:nowrap;overflow:hidden}.x-grid-editor div.x-form-action-col-field{line-height:0}.x-grid-row-editor-wrap{position:absolute;overflow:visible;z-index:2}.x-grid-row-editor{position:absolute;z-index:0}.x-grid-row-editor-buttons{position:absolute;white-space:nowrap}.x-grid-row-expander{font-size:0;line-height:0;text-align:center}.x-keyboard-mode .x-grid-row-expander:focus{outline:1px solid #3d92cf}.x-grid-hide-row-expander-spacer .x-grid-row-expander-spacer{display:none}.x-grid-row-expander-spacer{border:0 none}.x-ssm-row-numberer-hd{cursor:se-resize!important}.x-ssm-row-numberer-cell{cursor:e-resize}.x-ssm-column-select .x-column-header{cursor:s-resize}.x-ssm-extender-drag-handle{position:absolute;z-index:1;cursor:crosshair}.x-ssm-extender-mask{position:absolute;z-index:1;pointer-events:none}.x-abs-layout-ct{position:relative}.x-abs-layout-item{position:absolute !important}.x-border-layout-ct{overflow:hidden}.x-border-layout-ct{position:relative}.x-border-region-slide-in{z-index:6}.x-region-collapsed-placeholder{z-index:4}.x-center-layout-item{position:absolute}.x-center-target{position:relative}.x-form-layout-wrap{display:table;width:100%;border-collapse:separate}.x-form-layout-colgroup{display:table-column-group}.x-form-layout-column{display:table-column}.x-form-layout-auto-label > * > .x-form-item-label{width:auto !important}.x-form-layout-auto-label > * > .x-form-item-label > .x-form-item-label-inner{width:auto !important;white-space:nowrap}.x-form-layout-auto-label > * > .x-form-layout-label-column{width:1px}.x-form-layout-sized-label > * > .x-form-item-label{width:auto !important}.x-form-form-item{display:table-row}.x-form-form-item > .x-form-item-label{padding-left:0 !important;padding-right:0 !important;padding-bottom:0 !important}.x-form-form-item > .x-form-item-body{max-width:none}.x-form-form-item.x-form-item-no-label:before{content:' ';display:table-cell;pointer-events:none}.x-resizable-wrapped{box-sizing:border-box;-moz-box-sizing:border-box;-ms-box-sizing:border-box;-webkit-box-sizing:border-box}.x-slider{outline:none;position:relative}.x-slider-inner{position:relative;left:0;top:0;overflow:visible}.x-slider-vert .x-slider-inner{background:repeat-y 0 0}.x-slider-thumb{position:absolute;background:no-repeat 0 0;cursor:default;-webkit-user-callout:none}.x-slider-horz .x-slider-thumb{left:0}.x-slider-vert .x-slider-thumb{bottom:0}.x-tab{display:block;outline:0;cursor:pointer;white-space:nowrap;text-decoration:none;vertical-align:top;overflow:hidden;position:relative}.x-tab > .x-frame{height:100%;width:100%}.x-tab-wrap{height:100%;width:100%;display:table;border-spacing:0}.x-tab-button{white-space:nowrap;line-height:0;position:relative;display:table-cell;vertical-align:middle}.x-tab-inner{overflow:hidden;text-overflow:ellipsis;display:inline-block;vertical-align:middle}.x-tab-icon.x-tab-no-text > .x-tab-inner{display:none}.x-tab-icon-el{display:none;vertical-align:middle;text-align:center;background-position:center center;background-repeat:no-repeat}.x-tab-icon > .x-tab-icon-el{display:inline-block}.x-tab-icon-top > .x-tab-icon-el,.x-tab-icon-bottom > .x-tab-icon-el{display:block}.x-ie9m .x-tab-button-center{text-align:center}.x-tab-button-center.x-tab-icon-top,.x-tab-button-center.x-tab-icon-bottom{text-align:center}.x-tab-button-left{text-align:left}.x-tab-button-right{text-align:right}.x-tab-mc{overflow:visible}.x-tab{z-index:1}.x-tab-active{z-index:3}.x-tab-button{position:relative}.x-tab-close-btn{display:block;position:absolute;overflow:hidden;font-size:0;line-height:0}.x-tab-rotate-left{-webkit-transform:rotate(270deg);-webkit-transform-origin:100% 0;-moz-transform:rotate(270deg);-moz-transform-origin:100% 0;-ms-transform:rotate(270deg);-ms-transform-origin:100% 0;transform:rotate(270deg);transform-origin:100% 0}.x-ie8 .x-tab-rotate-left{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"}.x-tab-rotate-right{-webkit-transform:rotate(90deg);-webkit-transform-origin:0 0;-moz-transform:rotate(90deg);-moz-transform-origin:0 0;-ms-transform:rotate(90deg);-ms-transform-origin:0 0;transform:rotate(90deg);transform-origin:0 0}.x-ie8 .x-tab-rotate-right{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"}.x-tab-tr,.x-tab-br,.x-tab-mr,.x-tab-tl,.x-tab-bl,.x-tab-ml{width:1px}.x-tab-bar{z-index:0;position:relative}.x-tab-bar-strip{position:absolute;line-height:0;font-size:0;z-index:2}.x-tab-bar-top > .x-tab-bar-strip{bottom:0}.x-tab-bar-bottom > .x-tab-bar-strip{top:0}.x-tab-bar-left > .x-tab-bar-strip{right:0}.x-tab-bar-right > .x-tab-bar-strip{left:0}.x-tab-bar-horizontal .x-tab-bar-strip{width:100%;left:0}.x-tab-bar-vertical{display:table-cell}.x-tab-bar-vertical .x-tab-bar-strip{height:100%;top:0}.x-tab-bar-plain{background:transparent !important}.x-box-scroller-plain{background-color:transparent !important}.x-breadcrumb-btn .x-box-target:first-child{margin:0}.x-breadcrumb-btn > .x-btn-split-right > .x-btn-button:after{content:none}.x-breadcrumb-btn.x-btn-over > .x-btn-split-right > .x-btn-button:after,.x-breadcrumb-btn.x-btn-menu-active > .x-btn-split-right > .x-btn-button:after{content:''}.x-autowidth-table .x-grid-item-container{overflow:visible}.x-autowidth-table .x-grid-item{table-layout:auto;width:auto !important}.x-tree-view{overflow:hidden}.x-tree-elbow-img,.x-tree-icon{display:inline-block;text-align:center;background-repeat:no-repeat;background-position:0 center;vertical-align:top}.x-tree-checkbox{display:inline-block;vertical-align:top;position:relative}.x-tree-animator-wrap{overflow:hidden}.x-body{color:#000;font-size:13px;line-height:17px;font-family: tahoma, verdana, sans-serif;background:#f5f5f5}.x-animating-size,.x-collapsed{overflow:hidden!important}.x-animating-size{z-index:10000}.x-editor .x-form-item-body{padding-bottom:0}.x-mask{background-image:none;background-color:rgba(255, 255, 255, 0.7);cursor:default;border-style:solid;border-width:1px;border-color:transparent}.x-ie8 .x-mask{-ms-filter:"progid:DXImageTransform.Microsoft.gradient(startColorstr=#b3ffffff, endColorstr=#b3ffffff)";zoom:1}.x-keyboard-mode .x-mask.x-focus{border-style:solid;border-width:1px;border-color:#157fcc}.x-mask-msg{padding:8px;-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;background:#e5e5e5}.x-mask-msg-inner{padding:0;background-color:transparent;color:#666;font:normal 13px tahoma, verdana, sans-serif}.x-mask-msg-text{padding:21px 0 0;background-image:url(images/loadmask/loading.gif);background-repeat:no-repeat;background-position:center 0}.x-progress-default{background-color:#f5f5f5;border-width:0;height:20px;border-color:#157fcc;border-style:solid}.x-progress-default .x-progress-bar-default{background-image:none;background-color:#c2ddf2}.x-progress-default .x-progress-text{color:#666;font-weight:bold;font-size:13px;font-family: tahoma, verdana, sans-serif;text-align:center;line-height:20px}.x-progress-default .x-progress-text-back{color:#666;line-height:20px}.x-keyboard-mode .x-progress-default.x-progress-focus:after{position:absolute;content:' ';top:0;right:0;bottom:0;left:0;border:0 solid #157fcc;pointer-events:none}.x-progressbar-default-cell > .x-grid-cell-inner,.x-progress-default-cell > .x-grid-cell-inner,.x-progressbarwidget-default-cell > .x-grid-cell-inner{padding-top:2px;padding-bottom:2px}.x-progressbar-default-cell > .x-grid-cell-inner .x-progress-default,.x-progress-default-cell > .x-grid-cell-inner .x-progress-default,.x-progressbarwidget-default-cell > .x-grid-cell-inner .x-progress-default{height:20px}.x-btn-default-small{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4)}.x-btn-default-small-mc{background-image:url(images/btn/btn-default-small-fbg.gif);background-position:0 top;background-color:#3892d4}.x-nbr .x-btn-default-small{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-default-small-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-default-small-tl{background-position:0 -6px}.x-btn-default-small-tr{background-position:right -9px}.x-btn-default-small-bl{background-position:0 -12px}.x-btn-default-small-br{background-position:right -15px}.x-btn-default-small-ml{background-position:0 top}.x-btn-default-small-mr{background-position:right top}.x-btn-default-small-tc{background-position:0 0}.x-btn-default-small-bc{background-position:0 -3px}.x-btn-default-small-tr,.x-btn-default-small-br,.x-btn-default-small-mr{padding-right:3px}.x-btn-default-small-tl,.x-btn-default-small-bl,.x-btn-default-small-ml{padding-left:3px}.x-btn-default-small-tc{height:3px}.x-btn-default-small-bc{height:3px}.x-btn-default-small-tl,.x-btn-default-small-bl,.x-btn-default-small-tr,.x-btn-default-small-br,.x-btn-default-small-tc,.x-btn-default-small-bc,.x-btn-default-small-ml,.x-btn-default-small-mr{background-image:url(images/btn/btn-default-small-corners.gif)}.x-btn-default-small-ml,.x-btn-default-small-mr{background-image:url(images/btn/btn-default-small-sides.gif)}.x-btn-default-small-mc{padding:1px 1px 1px 1px}.x-btn-default-small{border-color:#126daf}.x-btn-button-default-small{min-height:16px}.x-ie9m .x-btn-button-default-small{min-height:auto;height:16px}.x-btn-inner-default-small{font:bold 12px/16px tahoma, verdana, sans-serif;color:#fff;padding:0 5px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-default-small,.x-ie9 .x-btn-icon-left > .x-btn-inner-default-small{max-width:calc(100% - 16px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-default-small,.x-safari8m .x-btn-icon-left > .x-btn-inner-default-small{max-width:calc(100% - 15px)}.x-ie10p .x-btn-inner-default-small{max-width:none}.x-btn-icon-el-default-small{font-size:16px;height:16px;color:#fff;line-height:16px}.x-btn-icon-left > .x-btn-icon-el-default-small,.x-btn-icon-right > .x-btn-icon-el-default-small{width:16px}.x-btn-icon-top > .x-btn-icon-el-default-small,.x-btn-icon-bottom > .x-btn-icon-el-default-small{min-width:16px}.x-btn-icon-el-default-small.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-default-small.x-btn-glyph{color:#9cc9e9}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-small{margin-right:0px}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small{margin-left:0px}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-small{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-small{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small{margin-right:5px}.x-btn-arrow-bottom > .x-btn-button-default-small,.x-btn-split-bottom > .x-btn-button-default-small{padding-bottom:3px}.x-btn-wrap-default-small.x-btn-arrow-right:after{width:16px;background-image:url(images/button/default-small-arrow.png);padding-right:16px}.x-btn-wrap-default-small.x-btn-arrow-bottom:after{height:13px;background-image:url(images/button/default-small-arrow.png)}.x-btn-wrap-default-small.x-btn-split-right:after{width:20px;background-image:url(images/button/default-small-s-arrow.png);padding-right:20px}.x-btn-wrap-default-small.x-btn-split-bottom:after{height:15px;background-image:url(images/button/default-small-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small{margin-right:5px}.x-keyboard-mode .x-btn-focus.x-btn-default-small{background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);-webkit-box-shadow:#d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset;-moz-box-shadow:#d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset;box-shadow:#d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset}.x-btn-default-small .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:23px;pointer-events:none}.x-keyboard-mode .x-btn-default-small.x-arrow-focus .x-btn-arrow-el{border:1px solid #d7e9f6}.x-btn-over.x-btn-default-small{border-color:#1164a1;background-image:none;background-color:#3487c3;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4893c9), color-stop(50%, #3487c3), color-stop(51%, #3180b9), color-stop(0%, #3487c3));background-image:-webkit-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-moz-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-o-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-ms-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:linear-gradient(top,#4893c9, #3487c3 50%, #3180b9 51%, #3487c3)}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-small{-webkit-box-shadow:#d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset;-moz-box-shadow:#d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset;box-shadow:#d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-default-small,.x-btn.x-btn-pressed.x-btn-default-small{border-color:#0e5284;background-image:none;background-color:#2a6e9f;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #2a6e9f), color-stop(50%, #286897), color-stop(51%, #2a6e9f), color-stop(0%, #3f7ca8));background-image:-webkit-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-moz-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-o-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-ms-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:linear-gradient(top,#2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-small,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-small{-webkit-box-shadow:#d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset;-moz-box-shadow:#d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset;box-shadow:#d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-default-small{background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4)}.x-keyboard-mode .x-btn-focus .x-btn-default-small-tl,.x-keyboard-mode .x-btn-focus .x-btn-default-small-bl,.x-keyboard-mode .x-btn-focus .x-btn-default-small-tr,.x-keyboard-mode .x-btn-focus .x-btn-default-small-br,.x-keyboard-mode .x-btn-focus .x-btn-default-small-tc,.x-keyboard-mode .x-btn-focus .x-btn-default-small-bc{background-image:url(images/btn/btn-default-small-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-small-ml,.x-keyboard-mode .x-btn-focus .x-btn-default-small-mr{background-image:url(images/btn/btn-default-small-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-small-mc{background-color:#3892d4;background-image:url(images/btn/btn-default-small-focus-fbg.gif)}.x-btn-over .x-btn-default-small-tl,.x-btn-over .x-btn-default-small-bl,.x-btn-over .x-btn-default-small-tr,.x-btn-over .x-btn-default-small-br,.x-btn-over .x-btn-default-small-tc,.x-btn-over .x-btn-default-small-bc{background-image:url(images/btn/btn-default-small-over-corners.gif)}.x-btn-over .x-btn-default-small-ml,.x-btn-over .x-btn-default-small-mr{background-image:url(images/btn/btn-default-small-over-sides.gif)}.x-btn-over .x-btn-default-small-mc{background-color:#3487c3;background-image:url(images/btn/btn-default-small-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bc{background-image:url(images/btn/btn-default-small-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mr{background-image:url(images/btn/btn-default-small-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mc{background-color:#3487c3;background-image:url(images/btn/btn-default-small-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-default-small-tl,.x-btn.x-btn-menu-active .x-btn-default-small-bl,.x-btn.x-btn-menu-active .x-btn-default-small-tr,.x-btn.x-btn-menu-active .x-btn-default-small-br,.x-btn.x-btn-menu-active .x-btn-default-small-tc,.x-btn.x-btn-menu-active .x-btn-default-small-bc,.x-btn.x-btn-pressed .x-btn-default-small-tl,.x-btn.x-btn-pressed .x-btn-default-small-bl,.x-btn.x-btn-pressed .x-btn-default-small-tr,.x-btn.x-btn-pressed .x-btn-default-small-br,.x-btn.x-btn-pressed .x-btn-default-small-tc,.x-btn.x-btn-pressed .x-btn-default-small-bc{background-image:url(images/btn/btn-default-small-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-default-small-ml,.x-btn.x-btn-menu-active .x-btn-default-small-mr,.x-btn.x-btn-pressed .x-btn-default-small-ml,.x-btn.x-btn-pressed .x-btn-default-small-mr{background-image:url(images/btn/btn-default-small-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-default-small-mc,.x-btn.x-btn-pressed .x-btn-default-small-mc{background-color:#2a6e9f;background-image:url(images/btn/btn-default-small-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bc{background-image:url(images/btn/btn-default-small-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mr{background-image:url(images/btn/btn-default-small-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mc{background-color:#2a6e9f;background-image:url(images/btn/btn-default-small-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-default-small-tl,.x-btn.x-btn-disabled .x-btn-default-small-bl,.x-btn.x-btn-disabled .x-btn-default-small-tr,.x-btn.x-btn-disabled .x-btn-default-small-br,.x-btn.x-btn-disabled .x-btn-default-small-tc,.x-btn.x-btn-disabled .x-btn-default-small-bc{background-image:url(images/btn/btn-default-small-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-default-small-ml,.x-btn.x-btn-disabled .x-btn-default-small-mr{background-image:url(images/btn/btn-default-small-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-default-small-mc{background-color:#3892d4;background-image:url(images/btn/btn-default-small-disabled-fbg.gif)}.x-nbr .x-btn-default-small{background-image:none}.x-btn-disabled.x-btn-default-small{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first .x-btn-default-small-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle .x-btn-default-small-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last .x-btn-default-small-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first .x-btn-default-small-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle .x-btn-default-small-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last .x-btn-default-small-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-default-small:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-small:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-small:after{border-width:1px;border-color:#d7e9f6}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-small:after{border-width:1px;border-color:#d6e7f3}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-small:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-small:after{border-width:1px;border-color:#d4e2ec}.x-button-default-small-cell > .x-grid-cell-inner{padding-top:0px;padding-bottom:0px}.x-button-default-small-cell > .x-grid-cell-inner >.x-btn-default-small{vertical-align:top}.x-btn-default-medium{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4)}.x-btn-default-medium-mc{background-image:url(images/btn/btn-default-medium-fbg.gif);background-position:0 top;background-color:#3892d4}.x-nbr .x-btn-default-medium{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-default-medium-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-default-medium-tl{background-position:0 -6px}.x-btn-default-medium-tr{background-position:right -9px}.x-btn-default-medium-bl{background-position:0 -12px}.x-btn-default-medium-br{background-position:right -15px}.x-btn-default-medium-ml{background-position:0 top}.x-btn-default-medium-mr{background-position:right top}.x-btn-default-medium-tc{background-position:0 0}.x-btn-default-medium-bc{background-position:0 -3px}.x-btn-default-medium-tr,.x-btn-default-medium-br,.x-btn-default-medium-mr{padding-right:3px}.x-btn-default-medium-tl,.x-btn-default-medium-bl,.x-btn-default-medium-ml{padding-left:3px}.x-btn-default-medium-tc{height:3px}.x-btn-default-medium-bc{height:3px}.x-btn-default-medium-tl,.x-btn-default-medium-bl,.x-btn-default-medium-tr,.x-btn-default-medium-br,.x-btn-default-medium-tc,.x-btn-default-medium-bc,.x-btn-default-medium-ml,.x-btn-default-medium-mr{background-image:url(images/btn/btn-default-medium-corners.gif)}.x-btn-default-medium-ml,.x-btn-default-medium-mr{background-image:url(images/btn/btn-default-medium-sides.gif)}.x-btn-default-medium-mc{padding:1px 1px 1px 1px}.x-btn-default-medium{border-color:#126daf}.x-btn-button-default-medium{min-height:24px}.x-ie9m .x-btn-button-default-medium{min-height:auto;height:24px}.x-btn-inner-default-medium{font:bold 14px/18px tahoma, verdana, sans-serif;color:#fff;padding:0 8px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-default-medium,.x-ie9 .x-btn-icon-left > .x-btn-inner-default-medium{max-width:calc(100% - 24px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-default-medium,.x-safari8m .x-btn-icon-left > .x-btn-inner-default-medium{max-width:calc(100% - 23px)}.x-ie10p .x-btn-inner-default-medium{max-width:none}.x-btn-icon-el-default-medium{font-size:24px;height:24px;color:#fff;line-height:24px}.x-btn-icon-left > .x-btn-icon-el-default-medium,.x-btn-icon-right > .x-btn-icon-el-default-medium{width:24px}.x-btn-icon-top > .x-btn-icon-el-default-medium,.x-btn-icon-bottom > .x-btn-icon-el-default-medium{min-width:24px}.x-btn-icon-el-default-medium.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-default-medium.x-btn-glyph{color:#9cc9e9}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-medium{margin-right:0}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium{margin-left:0}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-medium{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-medium{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium{margin-right:8px}.x-btn-arrow-bottom > .x-btn-button-default-medium,.x-btn-split-bottom > .x-btn-button-default-medium{padding-bottom:3px}.x-btn-wrap-default-medium.x-btn-arrow-right:after{width:24px;background-image:url(images/button/default-medium-arrow.png);padding-right:24px}.x-btn-wrap-default-medium.x-btn-arrow-bottom:after{height:18px;background-image:url(images/button/default-medium-arrow.png)}.x-btn-wrap-default-medium.x-btn-split-right:after{width:28px;background-image:url(images/button/default-medium-s-arrow.png);padding-right:28px}.x-btn-wrap-default-medium.x-btn-split-bottom:after{height:24px;background-image:url(images/button/default-medium-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium{margin-right:8px}.x-keyboard-mode .x-btn-focus.x-btn-default-medium{background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);-webkit-box-shadow:#d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset;-moz-box-shadow:#d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset;box-shadow:#d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset}.x-btn-default-medium .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:31px;pointer-events:none}.x-keyboard-mode .x-btn-default-medium.x-arrow-focus .x-btn-arrow-el{border:1px solid #d7e9f6}.x-btn-over.x-btn-default-medium{border-color:#1164a1;background-image:none;background-color:#3487c3;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4893c9), color-stop(50%, #3487c3), color-stop(51%, #3180b9), color-stop(0%, #3487c3));background-image:-webkit-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-moz-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-o-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-ms-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:linear-gradient(top,#4893c9, #3487c3 50%, #3180b9 51%, #3487c3)}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-medium{-webkit-box-shadow:#d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset;-moz-box-shadow:#d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset;box-shadow:#d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-default-medium,.x-btn.x-btn-pressed.x-btn-default-medium{border-color:#0e5284;background-image:none;background-color:#2a6e9f;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #2a6e9f), color-stop(50%, #286897), color-stop(51%, #2a6e9f), color-stop(0%, #3f7ca8));background-image:-webkit-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-moz-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-o-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-ms-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:linear-gradient(top,#2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-medium,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-medium{-webkit-box-shadow:#d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset;-moz-box-shadow:#d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset;box-shadow:#d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-default-medium{background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4)}.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tl,.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bl,.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tr,.x-keyboard-mode .x-btn-focus .x-btn-default-medium-br,.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tc,.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bc{background-image:url(images/btn/btn-default-medium-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-medium-ml,.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mr{background-image:url(images/btn/btn-default-medium-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mc{background-color:#3892d4;background-image:url(images/btn/btn-default-medium-focus-fbg.gif)}.x-btn-over .x-btn-default-medium-tl,.x-btn-over .x-btn-default-medium-bl,.x-btn-over .x-btn-default-medium-tr,.x-btn-over .x-btn-default-medium-br,.x-btn-over .x-btn-default-medium-tc,.x-btn-over .x-btn-default-medium-bc{background-image:url(images/btn/btn-default-medium-over-corners.gif)}.x-btn-over .x-btn-default-medium-ml,.x-btn-over .x-btn-default-medium-mr{background-image:url(images/btn/btn-default-medium-over-sides.gif)}.x-btn-over .x-btn-default-medium-mc{background-color:#3487c3;background-image:url(images/btn/btn-default-medium-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bc{background-image:url(images/btn/btn-default-medium-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mr{background-image:url(images/btn/btn-default-medium-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mc{background-color:#3487c3;background-image:url(images/btn/btn-default-medium-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-default-medium-tl,.x-btn.x-btn-menu-active .x-btn-default-medium-bl,.x-btn.x-btn-menu-active .x-btn-default-medium-tr,.x-btn.x-btn-menu-active .x-btn-default-medium-br,.x-btn.x-btn-menu-active .x-btn-default-medium-tc,.x-btn.x-btn-menu-active .x-btn-default-medium-bc,.x-btn.x-btn-pressed .x-btn-default-medium-tl,.x-btn.x-btn-pressed .x-btn-default-medium-bl,.x-btn.x-btn-pressed .x-btn-default-medium-tr,.x-btn.x-btn-pressed .x-btn-default-medium-br,.x-btn.x-btn-pressed .x-btn-default-medium-tc,.x-btn.x-btn-pressed .x-btn-default-medium-bc{background-image:url(images/btn/btn-default-medium-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-default-medium-ml,.x-btn.x-btn-menu-active .x-btn-default-medium-mr,.x-btn.x-btn-pressed .x-btn-default-medium-ml,.x-btn.x-btn-pressed .x-btn-default-medium-mr{background-image:url(images/btn/btn-default-medium-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-default-medium-mc,.x-btn.x-btn-pressed .x-btn-default-medium-mc{background-color:#2a6e9f;background-image:url(images/btn/btn-default-medium-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bc{background-image:url(images/btn/btn-default-medium-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mr{background-image:url(images/btn/btn-default-medium-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mc{background-color:#2a6e9f;background-image:url(images/btn/btn-default-medium-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-default-medium-tl,.x-btn.x-btn-disabled .x-btn-default-medium-bl,.x-btn.x-btn-disabled .x-btn-default-medium-tr,.x-btn.x-btn-disabled .x-btn-default-medium-br,.x-btn.x-btn-disabled .x-btn-default-medium-tc,.x-btn.x-btn-disabled .x-btn-default-medium-bc{background-image:url(images/btn/btn-default-medium-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-default-medium-ml,.x-btn.x-btn-disabled .x-btn-default-medium-mr{background-image:url(images/btn/btn-default-medium-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-default-medium-mc{background-color:#3892d4;background-image:url(images/btn/btn-default-medium-disabled-fbg.gif)}.x-nbr .x-btn-default-medium{background-image:none}.x-btn-disabled.x-btn-default-medium{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first .x-btn-default-medium-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle .x-btn-default-medium-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last .x-btn-default-medium-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first .x-btn-default-medium-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle .x-btn-default-medium-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last .x-btn-default-medium-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-default-medium:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-medium:after{border-width:1px;border-color:#d7e9f6}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-medium:after{border-width:1px;border-color:#d6e7f3}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-medium:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-medium:after{border-width:1px;border-color:#d4e2ec}.x-button-default-medium-cell > .x-grid-cell-inner{padding-top:0;padding-bottom:0}.x-button-default-medium-cell > .x-grid-cell-inner >.x-btn-default-medium{vertical-align:top}.x-btn-default-large{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4)}.x-btn-default-large-mc{background-image:url(images/btn/btn-default-large-fbg.gif);background-position:0 top;background-color:#3892d4}.x-nbr .x-btn-default-large{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-default-large-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-default-large-tl{background-position:0 -6px}.x-btn-default-large-tr{background-position:right -9px}.x-btn-default-large-bl{background-position:0 -12px}.x-btn-default-large-br{background-position:right -15px}.x-btn-default-large-ml{background-position:0 top}.x-btn-default-large-mr{background-position:right top}.x-btn-default-large-tc{background-position:0 0}.x-btn-default-large-bc{background-position:0 -3px}.x-btn-default-large-tr,.x-btn-default-large-br,.x-btn-default-large-mr{padding-right:3px}.x-btn-default-large-tl,.x-btn-default-large-bl,.x-btn-default-large-ml{padding-left:3px}.x-btn-default-large-tc{height:3px}.x-btn-default-large-bc{height:3px}.x-btn-default-large-tl,.x-btn-default-large-bl,.x-btn-default-large-tr,.x-btn-default-large-br,.x-btn-default-large-tc,.x-btn-default-large-bc,.x-btn-default-large-ml,.x-btn-default-large-mr{background-image:url(images/btn/btn-default-large-corners.gif)}.x-btn-default-large-ml,.x-btn-default-large-mr{background-image:url(images/btn/btn-default-large-sides.gif)}.x-btn-default-large-mc{padding:1px 1px 1px 1px}.x-btn-default-large{border-color:#126daf}.x-btn-button-default-large{min-height:32px}.x-ie9m .x-btn-button-default-large{min-height:auto;height:32px}.x-btn-inner-default-large{font:bold 16px/20px tahoma, verdana, sans-serif;color:#fff;padding:0 10px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-default-large,.x-ie9 .x-btn-icon-left > .x-btn-inner-default-large{max-width:calc(100% - 32px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-default-large,.x-safari8m .x-btn-icon-left > .x-btn-inner-default-large{max-width:calc(100% - 31px)}.x-ie10p .x-btn-inner-default-large{max-width:none}.x-btn-icon-el-default-large{font-size:32px;height:32px;color:#fff;line-height:32px}.x-btn-icon-left > .x-btn-icon-el-default-large,.x-btn-icon-right > .x-btn-icon-el-default-large{width:32px}.x-btn-icon-top > .x-btn-icon-el-default-large,.x-btn-icon-bottom > .x-btn-icon-el-default-large{min-width:32px}.x-btn-icon-el-default-large.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-default-large.x-btn-glyph{color:#9cc9e9}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-large{margin-right:0}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large{margin-left:0}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-large{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-large{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large{margin-right:10px}.x-btn-arrow-bottom > .x-btn-button-default-large,.x-btn-split-bottom > .x-btn-button-default-large{padding-bottom:3px}.x-btn-wrap-default-large.x-btn-arrow-right:after{width:28px;background-image:url(images/button/default-large-arrow.png);padding-right:28px}.x-btn-wrap-default-large.x-btn-arrow-bottom:after{height:20px;background-image:url(images/button/default-large-arrow.png)}.x-btn-wrap-default-large.x-btn-split-right:after{width:35px;background-image:url(images/button/default-large-s-arrow.png);padding-right:35px}.x-btn-wrap-default-large.x-btn-split-bottom:after{height:29px;background-image:url(images/button/default-large-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large{margin-right:10px}.x-keyboard-mode .x-btn-focus.x-btn-default-large{background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);-webkit-box-shadow:#d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset;-moz-box-shadow:#d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset;box-shadow:#d7e9f6 0 1px 0px 0 inset, #d7e9f6 0 -1px 0px 0 inset, #d7e9f6 -1px 0 0px 0 inset, #d7e9f6 1px 0 0px 0 inset}.x-btn-default-large .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:38px;pointer-events:none}.x-keyboard-mode .x-btn-default-large.x-arrow-focus .x-btn-arrow-el{border:1px solid #d7e9f6}.x-btn-over.x-btn-default-large{border-color:#1164a1;background-image:none;background-color:#3487c3;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4893c9), color-stop(50%, #3487c3), color-stop(51%, #3180b9), color-stop(0%, #3487c3));background-image:-webkit-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-moz-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-o-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-ms-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:linear-gradient(top,#4893c9, #3487c3 50%, #3180b9 51%, #3487c3)}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-large{-webkit-box-shadow:#d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset;-moz-box-shadow:#d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset;box-shadow:#d6e7f3 0 1px 0px 0 inset, #d6e7f3 0 -1px 0px 0 inset, #d6e7f3 -1px 0 0px 0 inset, #d6e7f3 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-default-large,.x-btn.x-btn-pressed.x-btn-default-large{border-color:#0e5284;background-image:none;background-color:#2a6e9f;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #2a6e9f), color-stop(50%, #286897), color-stop(51%, #2a6e9f), color-stop(0%, #3f7ca8));background-image:-webkit-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-moz-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-o-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-ms-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:linear-gradient(top,#2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-large,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-large{-webkit-box-shadow:#d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset;-moz-box-shadow:#d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset;box-shadow:#d4e2ec 0 1px 0px 0 inset, #d4e2ec 0 -1px 0px 0 inset, #d4e2ec -1px 0 0px 0 inset, #d4e2ec 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-default-large{background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4)}.x-keyboard-mode .x-btn-focus .x-btn-default-large-tl,.x-keyboard-mode .x-btn-focus .x-btn-default-large-bl,.x-keyboard-mode .x-btn-focus .x-btn-default-large-tr,.x-keyboard-mode .x-btn-focus .x-btn-default-large-br,.x-keyboard-mode .x-btn-focus .x-btn-default-large-tc,.x-keyboard-mode .x-btn-focus .x-btn-default-large-bc{background-image:url(images/btn/btn-default-large-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-large-ml,.x-keyboard-mode .x-btn-focus .x-btn-default-large-mr{background-image:url(images/btn/btn-default-large-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-large-mc{background-color:#3892d4;background-image:url(images/btn/btn-default-large-focus-fbg.gif)}.x-btn-over .x-btn-default-large-tl,.x-btn-over .x-btn-default-large-bl,.x-btn-over .x-btn-default-large-tr,.x-btn-over .x-btn-default-large-br,.x-btn-over .x-btn-default-large-tc,.x-btn-over .x-btn-default-large-bc{background-image:url(images/btn/btn-default-large-over-corners.gif)}.x-btn-over .x-btn-default-large-ml,.x-btn-over .x-btn-default-large-mr{background-image:url(images/btn/btn-default-large-over-sides.gif)}.x-btn-over .x-btn-default-large-mc{background-color:#3487c3;background-image:url(images/btn/btn-default-large-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bc{background-image:url(images/btn/btn-default-large-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mr{background-image:url(images/btn/btn-default-large-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mc{background-color:#3487c3;background-image:url(images/btn/btn-default-large-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-default-large-tl,.x-btn.x-btn-menu-active .x-btn-default-large-bl,.x-btn.x-btn-menu-active .x-btn-default-large-tr,.x-btn.x-btn-menu-active .x-btn-default-large-br,.x-btn.x-btn-menu-active .x-btn-default-large-tc,.x-btn.x-btn-menu-active .x-btn-default-large-bc,.x-btn.x-btn-pressed .x-btn-default-large-tl,.x-btn.x-btn-pressed .x-btn-default-large-bl,.x-btn.x-btn-pressed .x-btn-default-large-tr,.x-btn.x-btn-pressed .x-btn-default-large-br,.x-btn.x-btn-pressed .x-btn-default-large-tc,.x-btn.x-btn-pressed .x-btn-default-large-bc{background-image:url(images/btn/btn-default-large-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-default-large-ml,.x-btn.x-btn-menu-active .x-btn-default-large-mr,.x-btn.x-btn-pressed .x-btn-default-large-ml,.x-btn.x-btn-pressed .x-btn-default-large-mr{background-image:url(images/btn/btn-default-large-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-default-large-mc,.x-btn.x-btn-pressed .x-btn-default-large-mc{background-color:#2a6e9f;background-image:url(images/btn/btn-default-large-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bc{background-image:url(images/btn/btn-default-large-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mr{background-image:url(images/btn/btn-default-large-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mc{background-color:#2a6e9f;background-image:url(images/btn/btn-default-large-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-default-large-tl,.x-btn.x-btn-disabled .x-btn-default-large-bl,.x-btn.x-btn-disabled .x-btn-default-large-tr,.x-btn.x-btn-disabled .x-btn-default-large-br,.x-btn.x-btn-disabled .x-btn-default-large-tc,.x-btn.x-btn-disabled .x-btn-default-large-bc{background-image:url(images/btn/btn-default-large-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-default-large-ml,.x-btn.x-btn-disabled .x-btn-default-large-mr{background-image:url(images/btn/btn-default-large-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-default-large-mc{background-color:#3892d4;background-image:url(images/btn/btn-default-large-disabled-fbg.gif)}.x-nbr .x-btn-default-large{background-image:none}.x-btn-disabled.x-btn-default-large{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first .x-btn-default-large-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle .x-btn-default-large-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last .x-btn-default-large-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first .x-btn-default-large-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle .x-btn-default-large-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last .x-btn-default-large-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-default-large:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-large:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-large:after{border-width:1px;border-color:#d7e9f6}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-large:after{border-width:1px;border-color:#d6e7f3}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-large:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-large:after{border-width:1px;border-color:#d4e2ec}.x-button-default-large-cell > .x-grid-cell-inner{padding-top:0;padding-bottom:0}.x-button-default-large-cell > .x-grid-cell-inner >.x-btn-default-large{vertical-align:top}.x-btn-default-toolbar-small{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:#f5f5f5;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5));background-image:-webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:linear-gradient(top,#f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5)}.x-btn-default-toolbar-small-mc{background-image:url(images/btn/btn-default-toolbar-small-fbg.gif);background-position:0 top;background-color:#f5f5f5}.x-nbr .x-btn-default-toolbar-small{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-default-toolbar-small-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-default-toolbar-small-tl{background-position:0 -6px}.x-btn-default-toolbar-small-tr{background-position:right -9px}.x-btn-default-toolbar-small-bl{background-position:0 -12px}.x-btn-default-toolbar-small-br{background-position:right -15px}.x-btn-default-toolbar-small-ml{background-position:0 top}.x-btn-default-toolbar-small-mr{background-position:right top}.x-btn-default-toolbar-small-tc{background-position:0 0}.x-btn-default-toolbar-small-bc{background-position:0 -3px}.x-btn-default-toolbar-small-tr,.x-btn-default-toolbar-small-br,.x-btn-default-toolbar-small-mr{padding-right:3px}.x-btn-default-toolbar-small-tl,.x-btn-default-toolbar-small-bl,.x-btn-default-toolbar-small-ml{padding-left:3px}.x-btn-default-toolbar-small-tc{height:3px}.x-btn-default-toolbar-small-bc{height:3px}.x-btn-default-toolbar-small-tl,.x-btn-default-toolbar-small-bl,.x-btn-default-toolbar-small-tr,.x-btn-default-toolbar-small-br,.x-btn-default-toolbar-small-tc,.x-btn-default-toolbar-small-bc,.x-btn-default-toolbar-small-ml,.x-btn-default-toolbar-small-mr{background-image:url(images/btn/btn-default-toolbar-small-corners.gif)}.x-btn-default-toolbar-small-ml,.x-btn-default-toolbar-small-mr{background-image:url(images/btn/btn-default-toolbar-small-sides.gif)}.x-btn-default-toolbar-small-mc{padding:1px 1px 1px 1px}.x-btn-default-toolbar-small{border-color:#e1e1e1}.x-btn-button-default-toolbar-small{min-height:16px}.x-ie9m .x-btn-button-default-toolbar-small{min-height:auto;height:16px}.x-btn-inner-default-toolbar-small{font:bold 12px/16px tahoma, verdana, sans-serif;color:#666;padding:0 5px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-small,.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-small{max-width:calc(100% - 16px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-small,.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-small{max-width:calc(100% - 15px)}.x-ie10p .x-btn-inner-default-toolbar-small{max-width:none}.x-btn-icon-el-default-toolbar-small{font-size:16px;height:16px;color:#666;line-height:16px}.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small,.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small{width:16px}.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small,.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small{min-width:16px}.x-btn-icon-el-default-toolbar-small.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-default-toolbar-small.x-btn-glyph{color:#aeaeae}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small{margin-right:0px}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small{margin-left:0px}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small{margin-right:5px}.x-btn-arrow-bottom > .x-btn-button-default-toolbar-small,.x-btn-split-bottom > .x-btn-button-default-toolbar-small{padding-bottom:3px}.x-btn-wrap-default-toolbar-small.x-btn-arrow-right:after{width:16px;background-image:url(images/button/default-toolbar-small-arrow.png);padding-right:16px}.x-btn-wrap-default-toolbar-small.x-btn-arrow-bottom:after{height:13px;background-image:url(images/button/default-toolbar-small-arrow.png)}.x-btn-wrap-default-toolbar-small.x-btn-split-right:after{width:20px;background-image:url(images/button/default-toolbar-small-s-arrow.png);padding-right:20px}.x-btn-wrap-default-toolbar-small.x-btn-split-bottom:after{height:15px;background-image:url(images/button/default-toolbar-small-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small{margin-right:5px}.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-small{background-image:none;background-color:#f5f5f5;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5));background-image:-webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:linear-gradient(top,#f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn-default-toolbar-small .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:23px;pointer-events:none}.x-keyboard-mode .x-btn-default-toolbar-small.x-arrow-focus .x-btn-arrow-el{border:1px solid #4297d4}.x-btn-over.x-btn-default-toolbar-small{border-color:#d8d8d8;background-image:none;background-color:#ececec;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec));background-image:-webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:linear-gradient(top,#eee, #ececec 50%, #e0e0e0 51%, #ececec)}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-small{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-default-toolbar-small,.x-btn.x-btn-pressed.x-btn-default-toolbar-small{border-color:#cfcfcf;background-image:none;background-color:#e2e2e2;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5));background-image:-webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:linear-gradient(top,#e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-default-toolbar-small{background-image:none;background-color:#f5f5f5;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5));background-image:-webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:linear-gradient(top,#f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5)}.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tl,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bl,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tr,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-br,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tc,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bc{background-image:url(images/btn/btn-default-toolbar-small-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-ml,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mr{background-image:url(images/btn/btn-default-toolbar-small-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mc{background-color:#f5f5f5;background-image:url(images/btn/btn-default-toolbar-small-focus-fbg.gif)}.x-btn-over .x-btn-default-toolbar-small-tl,.x-btn-over .x-btn-default-toolbar-small-bl,.x-btn-over .x-btn-default-toolbar-small-tr,.x-btn-over .x-btn-default-toolbar-small-br,.x-btn-over .x-btn-default-toolbar-small-tc,.x-btn-over .x-btn-default-toolbar-small-bc{background-image:url(images/btn/btn-default-toolbar-small-over-corners.gif)}.x-btn-over .x-btn-default-toolbar-small-ml,.x-btn-over .x-btn-default-toolbar-small-mr{background-image:url(images/btn/btn-default-toolbar-small-over-sides.gif)}.x-btn-over .x-btn-default-toolbar-small-mc{background-color:#ececec;background-image:url(images/btn/btn-default-toolbar-small-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bc{background-image:url(images/btn/btn-default-toolbar-small-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mr{background-image:url(images/btn/btn-default-toolbar-small-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mc{background-color:#ececec;background-image:url(images/btn/btn-default-toolbar-small-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tl,.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bl,.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tr,.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-br,.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tc,.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bc,.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tl,.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bl,.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tr,.x-btn.x-btn-pressed .x-btn-default-toolbar-small-br,.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tc,.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bc{background-image:url(images/btn/btn-default-toolbar-small-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-ml,.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mr,.x-btn.x-btn-pressed .x-btn-default-toolbar-small-ml,.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mr{background-image:url(images/btn/btn-default-toolbar-small-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mc,.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-default-toolbar-small-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bc{background-image:url(images/btn/btn-default-toolbar-small-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mr{background-image:url(images/btn/btn-default-toolbar-small-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-default-toolbar-small-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tl,.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bl,.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tr,.x-btn.x-btn-disabled .x-btn-default-toolbar-small-br,.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tc,.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bc{background-image:url(images/btn/btn-default-toolbar-small-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-default-toolbar-small-ml,.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mr{background-image:url(images/btn/btn-default-toolbar-small-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mc{background-color:#f5f5f5;background-image:url(images/btn/btn-default-toolbar-small-disabled-fbg.gif)}.x-nbr .x-btn-default-toolbar-small{background-image:none}.x-btn-disabled.x-btn-default-toolbar-small{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first .x-btn-default-toolbar-small-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle .x-btn-default-toolbar-small-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last .x-btn-default-toolbar-small-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first .x-btn-default-toolbar-small-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle .x-btn-default-toolbar-small-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last .x-btn-default-toolbar-small-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-default-toolbar-small:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-small:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-small:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small:after{border-width:1px;border-color:#4297d4}.x-button-default-toolbar-small-cell > .x-grid-cell-inner{padding-top:0px;padding-bottom:0px}.x-button-default-toolbar-small-cell > .x-grid-cell-inner >.x-btn-default-toolbar-small{vertical-align:top}.x-btn-default-toolbar-medium{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:#f5f5f5;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5));background-image:-webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:linear-gradient(top,#f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5)}.x-btn-default-toolbar-medium-mc{background-image:url(images/btn/btn-default-toolbar-medium-fbg.gif);background-position:0 top;background-color:#f5f5f5}.x-nbr .x-btn-default-toolbar-medium{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-default-toolbar-medium-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-default-toolbar-medium-tl{background-position:0 -6px}.x-btn-default-toolbar-medium-tr{background-position:right -9px}.x-btn-default-toolbar-medium-bl{background-position:0 -12px}.x-btn-default-toolbar-medium-br{background-position:right -15px}.x-btn-default-toolbar-medium-ml{background-position:0 top}.x-btn-default-toolbar-medium-mr{background-position:right top}.x-btn-default-toolbar-medium-tc{background-position:0 0}.x-btn-default-toolbar-medium-bc{background-position:0 -3px}.x-btn-default-toolbar-medium-tr,.x-btn-default-toolbar-medium-br,.x-btn-default-toolbar-medium-mr{padding-right:3px}.x-btn-default-toolbar-medium-tl,.x-btn-default-toolbar-medium-bl,.x-btn-default-toolbar-medium-ml{padding-left:3px}.x-btn-default-toolbar-medium-tc{height:3px}.x-btn-default-toolbar-medium-bc{height:3px}.x-btn-default-toolbar-medium-tl,.x-btn-default-toolbar-medium-bl,.x-btn-default-toolbar-medium-tr,.x-btn-default-toolbar-medium-br,.x-btn-default-toolbar-medium-tc,.x-btn-default-toolbar-medium-bc,.x-btn-default-toolbar-medium-ml,.x-btn-default-toolbar-medium-mr{background-image:url(images/btn/btn-default-toolbar-medium-corners.gif)}.x-btn-default-toolbar-medium-ml,.x-btn-default-toolbar-medium-mr{background-image:url(images/btn/btn-default-toolbar-medium-sides.gif)}.x-btn-default-toolbar-medium-mc{padding:1px 1px 1px 1px}.x-btn-default-toolbar-medium{border-color:#e1e1e1}.x-btn-button-default-toolbar-medium{min-height:24px}.x-ie9m .x-btn-button-default-toolbar-medium{min-height:auto;height:24px}.x-btn-inner-default-toolbar-medium{font:bold 14px/18px tahoma, verdana, sans-serif;color:#666;padding:0 8px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-medium,.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-medium{max-width:calc(100% - 24px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-medium,.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-medium{max-width:calc(100% - 23px)}.x-ie10p .x-btn-inner-default-toolbar-medium{max-width:none}.x-btn-icon-el-default-toolbar-medium{font-size:24px;height:24px;color:#666;line-height:24px}.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium,.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium{width:24px}.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium,.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium{min-width:24px}.x-btn-icon-el-default-toolbar-medium.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-default-toolbar-medium.x-btn-glyph{color:#aeaeae}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium{margin-right:0}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium{margin-left:0}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium{margin-right:8px}.x-btn-arrow-bottom > .x-btn-button-default-toolbar-medium,.x-btn-split-bottom > .x-btn-button-default-toolbar-medium{padding-bottom:3px}.x-btn-wrap-default-toolbar-medium.x-btn-arrow-right:after{width:24px;background-image:url(images/button/default-toolbar-medium-arrow.png);padding-right:24px}.x-btn-wrap-default-toolbar-medium.x-btn-arrow-bottom:after{height:18px;background-image:url(images/button/default-toolbar-medium-arrow.png)}.x-btn-wrap-default-toolbar-medium.x-btn-split-right:after{width:28px;background-image:url(images/button/default-toolbar-medium-s-arrow.png);padding-right:28px}.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom:after{height:24px;background-image:url(images/button/default-toolbar-medium-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium{margin-right:8px}.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-medium{background-image:none;background-color:#f5f5f5;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5));background-image:-webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:linear-gradient(top,#f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn-default-toolbar-medium .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:31px;pointer-events:none}.x-keyboard-mode .x-btn-default-toolbar-medium.x-arrow-focus .x-btn-arrow-el{border:1px solid #4297d4}.x-btn-over.x-btn-default-toolbar-medium{border-color:#d8d8d8;background-image:none;background-color:#ececec;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec));background-image:-webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:linear-gradient(top,#eee, #ececec 50%, #e0e0e0 51%, #ececec)}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-medium{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-default-toolbar-medium,.x-btn.x-btn-pressed.x-btn-default-toolbar-medium{border-color:#cfcfcf;background-image:none;background-color:#e2e2e2;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5));background-image:-webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:linear-gradient(top,#e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-default-toolbar-medium{background-image:none;background-color:#f5f5f5;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5));background-image:-webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:linear-gradient(top,#f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5)}.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-br,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bc{background-image:url(images/btn/btn-default-toolbar-medium-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mr{background-image:url(images/btn/btn-default-toolbar-medium-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mc{background-color:#f5f5f5;background-image:url(images/btn/btn-default-toolbar-medium-focus-fbg.gif)}.x-btn-over .x-btn-default-toolbar-medium-tl,.x-btn-over .x-btn-default-toolbar-medium-bl,.x-btn-over .x-btn-default-toolbar-medium-tr,.x-btn-over .x-btn-default-toolbar-medium-br,.x-btn-over .x-btn-default-toolbar-medium-tc,.x-btn-over .x-btn-default-toolbar-medium-bc{background-image:url(images/btn/btn-default-toolbar-medium-over-corners.gif)}.x-btn-over .x-btn-default-toolbar-medium-ml,.x-btn-over .x-btn-default-toolbar-medium-mr{background-image:url(images/btn/btn-default-toolbar-medium-over-sides.gif)}.x-btn-over .x-btn-default-toolbar-medium-mc{background-color:#ececec;background-image:url(images/btn/btn-default-toolbar-medium-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bc{background-image:url(images/btn/btn-default-toolbar-medium-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mr{background-image:url(images/btn/btn-default-toolbar-medium-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mc{background-color:#ececec;background-image:url(images/btn/btn-default-toolbar-medium-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tl,.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bl,.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tr,.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-br,.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tc,.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bc,.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tl,.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bl,.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tr,.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-br,.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tc,.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bc{background-image:url(images/btn/btn-default-toolbar-medium-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-ml,.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mr,.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-ml,.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mr{background-image:url(images/btn/btn-default-toolbar-medium-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mc,.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-default-toolbar-medium-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bc{background-image:url(images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mr{background-image:url(images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-default-toolbar-medium-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tl,.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bl,.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tr,.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-br,.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tc,.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bc{background-image:url(images/btn/btn-default-toolbar-medium-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-ml,.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mr{background-image:url(images/btn/btn-default-toolbar-medium-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mc{background-color:#f5f5f5;background-image:url(images/btn/btn-default-toolbar-medium-disabled-fbg.gif)}.x-nbr .x-btn-default-toolbar-medium{background-image:none}.x-btn-disabled.x-btn-default-toolbar-medium{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first .x-btn-default-toolbar-medium-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle .x-btn-default-toolbar-medium-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last .x-btn-default-toolbar-medium-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first .x-btn-default-toolbar-medium-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle .x-btn-default-toolbar-medium-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last .x-btn-default-toolbar-medium-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-default-toolbar-medium:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-medium:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-medium:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium:after{border-width:1px;border-color:#4297d4}.x-button-default-toolbar-medium-cell > .x-grid-cell-inner{padding-top:0;padding-bottom:0}.x-button-default-toolbar-medium-cell > .x-grid-cell-inner >.x-btn-default-toolbar-medium{vertical-align:top}.x-btn-default-toolbar-large{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:#f5f5f5;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5));background-image:-webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:linear-gradient(top,#f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5)}.x-btn-default-toolbar-large-mc{background-image:url(images/btn/btn-default-toolbar-large-fbg.gif);background-position:0 top;background-color:#f5f5f5}.x-nbr .x-btn-default-toolbar-large{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-default-toolbar-large-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-default-toolbar-large-tl{background-position:0 -6px}.x-btn-default-toolbar-large-tr{background-position:right -9px}.x-btn-default-toolbar-large-bl{background-position:0 -12px}.x-btn-default-toolbar-large-br{background-position:right -15px}.x-btn-default-toolbar-large-ml{background-position:0 top}.x-btn-default-toolbar-large-mr{background-position:right top}.x-btn-default-toolbar-large-tc{background-position:0 0}.x-btn-default-toolbar-large-bc{background-position:0 -3px}.x-btn-default-toolbar-large-tr,.x-btn-default-toolbar-large-br,.x-btn-default-toolbar-large-mr{padding-right:3px}.x-btn-default-toolbar-large-tl,.x-btn-default-toolbar-large-bl,.x-btn-default-toolbar-large-ml{padding-left:3px}.x-btn-default-toolbar-large-tc{height:3px}.x-btn-default-toolbar-large-bc{height:3px}.x-btn-default-toolbar-large-tl,.x-btn-default-toolbar-large-bl,.x-btn-default-toolbar-large-tr,.x-btn-default-toolbar-large-br,.x-btn-default-toolbar-large-tc,.x-btn-default-toolbar-large-bc,.x-btn-default-toolbar-large-ml,.x-btn-default-toolbar-large-mr{background-image:url(images/btn/btn-default-toolbar-large-corners.gif)}.x-btn-default-toolbar-large-ml,.x-btn-default-toolbar-large-mr{background-image:url(images/btn/btn-default-toolbar-large-sides.gif)}.x-btn-default-toolbar-large-mc{padding:1px 1px 1px 1px}.x-btn-default-toolbar-large{border-color:#e1e1e1}.x-btn-button-default-toolbar-large{min-height:32px}.x-ie9m .x-btn-button-default-toolbar-large{min-height:auto;height:32px}.x-btn-inner-default-toolbar-large{font:bold 16px/20px tahoma, verdana, sans-serif;color:#666;padding:0 10px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-large,.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-large{max-width:calc(100% - 32px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-large,.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-large{max-width:calc(100% - 31px)}.x-ie10p .x-btn-inner-default-toolbar-large{max-width:none}.x-btn-icon-el-default-toolbar-large{font-size:32px;height:32px;color:#666;line-height:32px}.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large,.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large{width:32px}.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large,.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large{min-width:32px}.x-btn-icon-el-default-toolbar-large.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-default-toolbar-large.x-btn-glyph{color:#aeaeae}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large{margin-right:0}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large{margin-left:0}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large{margin-right:10px}.x-btn-arrow-bottom > .x-btn-button-default-toolbar-large,.x-btn-split-bottom > .x-btn-button-default-toolbar-large{padding-bottom:3px}.x-btn-wrap-default-toolbar-large.x-btn-arrow-right:after{width:28px;background-image:url(images/button/default-toolbar-large-arrow.png);padding-right:28px}.x-btn-wrap-default-toolbar-large.x-btn-arrow-bottom:after{height:20px;background-image:url(images/button/default-toolbar-large-arrow.png)}.x-btn-wrap-default-toolbar-large.x-btn-split-right:after{width:35px;background-image:url(images/button/default-toolbar-large-s-arrow.png);padding-right:35px}.x-btn-wrap-default-toolbar-large.x-btn-split-bottom:after{height:29px;background-image:url(images/button/default-toolbar-large-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large{margin-right:10px}.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-large{background-image:none;background-color:#f5f5f5;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5));background-image:-webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:linear-gradient(top,#f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn-default-toolbar-large .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:38px;pointer-events:none}.x-keyboard-mode .x-btn-default-toolbar-large.x-arrow-focus .x-btn-arrow-el{border:1px solid #4297d4}.x-btn-over.x-btn-default-toolbar-large{border-color:#d8d8d8;background-image:none;background-color:#ececec;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec));background-image:-webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:linear-gradient(top,#eee, #ececec 50%, #e0e0e0 51%, #ececec)}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-large{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-default-toolbar-large,.x-btn.x-btn-pressed.x-btn-default-toolbar-large{border-color:#cfcfcf;background-image:none;background-color:#e2e2e2;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5));background-image:-webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:linear-gradient(top,#e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-default-toolbar-large{background-image:none;background-color:#f5f5f5;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #f6f6f6), color-stop(50%, #f5f5f5), color-stop(51%, #e9e9e9), color-stop(0%, #f5f5f5));background-image:-webkit-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-moz-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-o-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:-ms-linear-gradient(top, #f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5);background-image:linear-gradient(top,#f6f6f6, #f5f5f5 50%, #e9e9e9 51%, #f5f5f5)}.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tl,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bl,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tr,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-br,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tc,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bc{background-image:url(images/btn/btn-default-toolbar-large-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-ml,.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mr{background-image:url(images/btn/btn-default-toolbar-large-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mc{background-color:#f5f5f5;background-image:url(images/btn/btn-default-toolbar-large-focus-fbg.gif)}.x-btn-over .x-btn-default-toolbar-large-tl,.x-btn-over .x-btn-default-toolbar-large-bl,.x-btn-over .x-btn-default-toolbar-large-tr,.x-btn-over .x-btn-default-toolbar-large-br,.x-btn-over .x-btn-default-toolbar-large-tc,.x-btn-over .x-btn-default-toolbar-large-bc{background-image:url(images/btn/btn-default-toolbar-large-over-corners.gif)}.x-btn-over .x-btn-default-toolbar-large-ml,.x-btn-over .x-btn-default-toolbar-large-mr{background-image:url(images/btn/btn-default-toolbar-large-over-sides.gif)}.x-btn-over .x-btn-default-toolbar-large-mc{background-color:#ececec;background-image:url(images/btn/btn-default-toolbar-large-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bc{background-image:url(images/btn/btn-default-toolbar-large-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mr{background-image:url(images/btn/btn-default-toolbar-large-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mc{background-color:#ececec;background-image:url(images/btn/btn-default-toolbar-large-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tl,.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bl,.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tr,.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-br,.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tc,.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bc,.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tl,.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bl,.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tr,.x-btn.x-btn-pressed .x-btn-default-toolbar-large-br,.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tc,.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bc{background-image:url(images/btn/btn-default-toolbar-large-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-ml,.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mr,.x-btn.x-btn-pressed .x-btn-default-toolbar-large-ml,.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mr{background-image:url(images/btn/btn-default-toolbar-large-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mc,.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-default-toolbar-large-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bc{background-image:url(images/btn/btn-default-toolbar-large-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mr{background-image:url(images/btn/btn-default-toolbar-large-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-default-toolbar-large-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tl,.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bl,.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tr,.x-btn.x-btn-disabled .x-btn-default-toolbar-large-br,.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tc,.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bc{background-image:url(images/btn/btn-default-toolbar-large-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-default-toolbar-large-ml,.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mr{background-image:url(images/btn/btn-default-toolbar-large-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mc{background-color:#f5f5f5;background-image:url(images/btn/btn-default-toolbar-large-disabled-fbg.gif)}.x-nbr .x-btn-default-toolbar-large{background-image:none}.x-btn-disabled.x-btn-default-toolbar-large{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first .x-btn-default-toolbar-large-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle .x-btn-default-toolbar-large-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last .x-btn-default-toolbar-large-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first .x-btn-default-toolbar-large-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle .x-btn-default-toolbar-large-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last .x-btn-default-toolbar-large-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-default-toolbar-large:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-large:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-large:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large:after{border-width:1px;border-color:#4297d4}.x-button-default-toolbar-large-cell > .x-grid-cell-inner{padding-top:0;padding-bottom:0}.x-button-default-toolbar-large-cell > .x-grid-cell-inner >.x-btn-default-toolbar-large{vertical-align:top}.x-tool{cursor:pointer}.x-tool-tool-el{overflow:hidden;width:16px;height:16px;margin:0;color:#fff;text-align:center;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-tool-over .x-tool-tool-el{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-tool-pressed .x-tool-tool-el{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=70)";opacity:0.7}.x-keyboard-mode .x-tool-focus{outline:1px solid #157fcc;outline-offset:2px}.x-ie .x-keyboard-mode .x-tool-focus,.x-ie10p .x-keyboard-mode .x-tool-focus,.x-edge .x-keyboard-mode .x-tool-focus{outline:none}.x-ie .x-keyboard-mode .x-tool-focus:after,.x-ie10p .x-keyboard-mode .x-tool-focus:after,.x-edge .x-keyboard-mode .x-tool-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #157fcc;pointer-events:none}.x-tool-img{background-image:url(images/tools/tool-sprites.png)}.x-tool-placeholder{visibility:hidden}.x-tool-close{background-position:0 0}.x-tool-minimize{background-position:0 -16px}.x-tool-maximize{background-position:0 -32px}.x-tool-restore{background-position:0 -48px}.x-tool-toggle{background-position:0 -64px}.x-panel-collapsed .x-tool-toggle{background-position:0 -80px}.x-tool-gear{background-position:0 -96px}.x-tool-prev{background-position:0 -112px}.x-tool-next{background-position:0 -128px}.x-tool-pin{background-position:0 -144px}.x-tool-unpin{background-position:0 -160px}.x-tool-right{background-position:0 -176px}.x-tool-left{background-position:0 -192px}.x-tool-down{background-position:0 -208px}.x-tool-up{background-position:0 -224px}.x-tool-refresh{background-position:0 -240px}.x-tool-plus{background-position:0 -256px}.x-tool-minus{background-position:0 -272px}.x-tool-search{background-position:0 -288px}.x-tool-save{background-position:0 -304px}.x-tool-help{background-position:0 -320px}.x-tool-print{background-position:0 -336px}.x-tool-expand{background-position:0 -352px}.x-tool-collapse{background-position:0 -368px}.x-tool-resize{background-position:0 -384px}.x-tool-move{background-position:0 -400px}.x-tool-expand-bottom{background-position:0 -208px}.x-tool-collapse-bottom{background-position:0 -208px}.x-tool-expand-top{background-position:0 -224px}.x-tool-collapse-top{background-position:0 -224px}.x-tool-expand-left{background-position:0 -192px}.x-tool-collapse-left{background-position:0 -192px}.x-tool-expand-right{background-position:0 -176px}.x-tool-collapse-right{background-position:0 -176px}.x-header-draggable,.x-header-ghost{cursor:move}.x-header-text{white-space:nowrap}.x-collapse-el{cursor:pointer}.x-layout-split-left{background-image:url(images/util/splitter/mini-left.png)}.x-layout-split-right{background-image:url(images/util/splitter/mini-right.png)}.x-layout-split-top{background-image:url(images/util/splitter/mini-top.png)}.x-layout-split-bottom{background-image:url(images/util/splitter/mini-bottom.png)}.x-splitter-collapsed .x-layout-split-left{background-image:url(images/util/splitter/mini-right.png)}.x-splitter-collapsed .x-layout-split-right{background-image:url(images/util/splitter/mini-left.png)}.x-splitter-collapsed .x-layout-split-top{background-image:url(images/util/splitter/mini-bottom.png)}.x-splitter-collapsed .x-layout-split-bottom{background-image:url(images/util/splitter/mini-top.png)}.x-splitter-active{background-color:#b4b4b4;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=80)";opacity:0.8}.x-splitter-active .x-collapse-el{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=30)";opacity:0.3}.x-layout-split-left,.x-layout-split-right{top:50%;margin-top:-24px;width:100%;height:48px}.x-layout-split-top,.x-layout-split-bottom{left:50%;width:48px;height:100%;margin-left:-24px}.x-keyboard-mode .x-splitter-focus:after{position:absolute;content:' ';top:1px;right:1px;bottom:1px;left:1px;border:1px solid #fff;pointer-events:none}.x-toolbar-default{padding:6px 0 6px 8px;border-style:solid;border-color:#c2c2c2;border-width:1px;background-image:none;background-color:#fff}.x-toolbar-default .x-tool-img{background-image:url(images/tools/tool-sprites-dark.png);background-color:#fff}.x-toolbar-default .x-toolbar-item{margin:0 8px 0 0}.x-toolbar-default .x-toolbar-separator-horizontal{margin:0 8px 0 0;height:14px;border-style:solid;border-width:0 0 0 1px;border-left-color:#e1e1e1;border-right-color:#fff}.x-toolbar-default .x-box-menu-after{margin:0 8px}.x-toolbar-default-vertical{padding:6px 8px 0}.x-toolbar-default-vertical .x-toolbar-item{margin:0 0 6px 0}.x-toolbar-default-vertical .x-toolbar-separator-vertical{margin:0 5px 6px;border-style:solid none;border-width:1px 0 0;border-top-color:#e1e1e1;border-bottom-color:#fff}.x-toolbar-default-vertical .x-box-menu-after{margin:6px 0}.x-toolbar-text-default{padding:0 4px;color:#334049;font:normal 13px/16px tahoma, verdana, sans-serif}.x-toolbar-spacer-default{width:2px}.x-toolbar-default-scroller .x-box-scroller-body-horizontal{margin-left:16px}.x-toolbar-default-vertical-scroller .x-box-scroller-body-vertical{margin-top:18px}.x-box-scroller-toolbar-default{cursor:pointer;color:#b0b0b0;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-box-scroller-toolbar-default.x-box-scroller-hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=80)";opacity:0.8}.x-box-scroller-toolbar-default.x-box-scroller-pressed{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";opacity:1}.x-box-scroller-toolbar-default.x-box-scroller-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=25)";opacity:0.25;cursor:default}.x-box-scroller-toolbar-default.x-box-scroller-left,.x-box-scroller-toolbar-default.x-box-scroller-right{width:16px;height:16px;top:50%;margin-top:-8px}.x-box-scroller-toolbar-default.x-box-scroller-left{margin-left:4px;margin-right:4px;margin-bottom:0;background-image:url(images/toolbar/default-scroll-left.png)}.x-box-scroller-toolbar-default.x-box-scroller-right{margin-left:4px;margin-right:4px;margin-bottom:0;background-image:url(images/toolbar/default-scroll-right.png)}.x-box-scroller-toolbar-default.x-box-scroller-top,.x-box-scroller-toolbar-default.x-box-scroller-bottom{height:16px;width:16px;left:50%;margin-left:-8px}.x-box-scroller-toolbar-default.x-box-scroller-top{margin-top:4px;margin-right:0;margin-bottom:4px;background-image:url(images/toolbar/default-scroll-top.png)}.x-box-scroller-toolbar-default.x-box-scroller-bottom{margin-top:4px;margin-right:0;margin-bottom:4px;background-image:url(images/toolbar/default-scroll-bottom.png)}.x-ie8 .x-box-scroller-toolbar-default{background-color:#fff}.x-toolbar-more-icon{background-image:url(images/toolbar/default-more.png)}.x-toolbar-footer{padding:6px 0 6px 6px;border-style:solid;border-color:#c2c2c2;border-width:0;background-image:none;background-color:#e0ebf3}.x-toolbar-footer .x-tool-img{background-image:url(images/tools/tool-sprites-dark.png);background-color:#e0ebf3}.x-toolbar-footer .x-toolbar-item{margin:0 6px 0 0}.x-toolbar-footer .x-toolbar-separator-horizontal{margin:0 8px 0 0;height:14px;border-style:solid;border-width:0 0 0 1px;border-left-color:#e1e1e1;border-right-color:#fff}.x-toolbar-footer .x-box-menu-after{margin:0 6px}.x-toolbar-footer-vertical{padding:6px 6px 0}.x-toolbar-footer-vertical .x-toolbar-item{margin:0 0 6px 0}.x-toolbar-footer-vertical .x-toolbar-separator-vertical{margin:0 5px 6px;border-style:solid none;border-width:1px 0 0;border-top-color:#e1e1e1;border-bottom-color:#fff}.x-toolbar-footer-vertical .x-box-menu-after{margin:6px 0}.x-toolbar-text-footer{padding:0 4px;color:#334049;font:normal 13px/16px tahoma, verdana, sans-serif}.x-toolbar-spacer-footer{width:2px}.x-toolbar-footer-scroller .x-box-scroller-body-horizontal{margin-left:18px}.x-toolbar-footer-vertical-scroller .x-box-scroller-body-vertical{margin-top:18px}.x-box-scroller-toolbar-footer{cursor:pointer;color:#b0b0b0;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-box-scroller-toolbar-footer.x-box-scroller-hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=80)";opacity:0.8}.x-box-scroller-toolbar-footer.x-box-scroller-pressed{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";opacity:1}.x-box-scroller-toolbar-footer.x-box-scroller-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=25)";opacity:0.25;cursor:default}.x-box-scroller-toolbar-footer.x-box-scroller-left,.x-box-scroller-toolbar-footer.x-box-scroller-right{width:16px;height:16px;top:50%;margin-top:-8px}.x-box-scroller-toolbar-footer.x-box-scroller-left{margin-left:4px;margin-right:4px;margin-bottom:0;background-image:url(images/toolbar/footer-scroll-left.png)}.x-box-scroller-toolbar-footer.x-box-scroller-right{margin-left:4px;margin-right:4px;margin-bottom:0;background-image:url(images/toolbar/footer-scroll-right.png)}.x-ie8 .x-box-scroller-toolbar-footer{background-color:#e0ebf3}.x-toolbar-more-icon{background-image:url(images/toolbar/footer-more.png)}.x-dd-drag-proxy{color:#000;font:normal 13px/17px tahoma, verdana, sans-serif;border:1px solid #e1e1e1;background-color:#fff}.x-dd-drag-ghost,.x-dd-drop-icon{padding:5px}.x-dd-drag-ghost{padding-left:0}.x-dd-drop-ok .x-dd-drop-icon{background-image:url(images/dd/drop-yes.png)}.x-dd-drop-ok-add .x-dd-drop-icon{background-image:url(images/dd/drop-add.png)}.x-dd-drop-nodrop div.x-dd-drop-icon{background-image:url(images/dd/drop-no.png)}.x-panel-ghost{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-panel-default{border-color:#157fcc;padding:0}.x-panel-default.x-masked{border-color:#b9d9f0}.x-panel-header-default{font-size:13px;border:1px solid #157fcc}.x-panel-header-default .x-tool-tool-el{background-color:#157fcc}.x-panel-header-default-horizontal{padding:9px 9px 10px}.x-panel-header-default-horizontal .x-panel-header-default-tab-bar{margin-top:-9px;margin-bottom:-10px}.x-panel-header-default-horizontal.x-header-noborder{padding:10px 10px 10px 10px}.x-panel-header-default-horizontal.x-header-noborder .x-panel-header-default-tab-bar{margin-top:-10px;margin-bottom:-10px}.x-panel-header-default-vertical{padding:9px 9px 9px 10px}.x-panel-header-default-vertical .x-panel-header-default-tab-bar{margin-right:-9px;margin-left:-10px}.x-panel-header-default-vertical.x-header-noborder{padding:10px 10px 10px 10px}.x-panel-header-default-vertical.x-header-noborder .x-panel-header-default-tab-bar{margin-right:-10px;margin-left:-10px}.x-panel-header-title-default{color:#fff;font-size:13px;font-weight:bold;font-family: tahoma, verdana, sans-serif;line-height:16px}.x-keyboard-mode .x-panel-header-title-default.x-title-focus{outline:1px solid #fff;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus,.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus,.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after,.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #fff;pointer-events:none}.x-panel-header-title-default > .x-title-text-default{text-transform:none;padding:0}.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-top{height:22px;padding-bottom:6px}.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-right{width:22px;padding-left:6px}.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-bottom{height:22px;padding-top:6px}.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-left{width:22px;padding-right:6px}.x-panel-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default{width:16px;height:16px;font-size:16px;color:#fff;background-position:center center}.x-panel-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph{opacity:0.5}.x-ie8 .x-panel-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph{color:#8abfe6}.x-panel-body-default{background:#fff;border-color:#c2c2c2;color:#000;font-size:13px;font-weight:normal;font-family: tahoma, verdana, sans-serif;border-width:1px;border-style:solid}.x-panel-header-default{background-image:none;background-color:#157fcc}.x-panel-header-default-vertical{background-image:none;background-color:#157fcc}.x-panel .x-panel-header-default-collapsed-border-top{border-bottom-width:1px !important}.x-panel .x-panel-header-default-collapsed-border-right{border-left-width:1px !important}.x-panel .x-panel-header-default-collapsed-border-bottom{border-top-width:1px !important}.x-panel .x-panel-header-default-collapsed-border-left{border-right-width:1px !important}.x-panel-header-default-horizontal .x-tool-after-title{margin:0 0 0 6px}.x-panel-header-default-horizontal .x-tool-before-title{margin:0 6px 0 0}.x-panel-header-default-vertical .x-tool-after-title{margin:6px 0 0 0}.x-panel-header-default-vertical .x-tool-before-title{margin:0 0 6px 0}.x-keyboard-mode .x-panel-header-default .x-tool-focus{outline:1px solid #fff;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus,.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus,.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus:after,.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #fff;pointer-events:none}.x-panel-default-resizable .x-panel-handle{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-panel-default-outer-border-l{border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-outer-border-b{border-bottom-color:#157fcc !important;border-bottom-width:1px !important}.x-panel-default-outer-border-bl{border-bottom-color:#157fcc !important;border-bottom-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-outer-border-r{border-right-color:#157fcc !important;border-right-width:1px !important}.x-panel-default-outer-border-rl{border-right-color:#157fcc !important;border-right-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-outer-border-rb{border-right-color:#157fcc !important;border-right-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important}.x-panel-default-outer-border-rbl{border-right-color:#157fcc !important;border-right-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-outer-border-t{border-top-color:#157fcc !important;border-top-width:1px !important}.x-panel-default-outer-border-tl{border-top-color:#157fcc !important;border-top-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-outer-border-tb{border-top-color:#157fcc !important;border-top-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important}.x-panel-default-outer-border-tbl{border-top-color:#157fcc !important;border-top-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-outer-border-tr{border-top-color:#157fcc !important;border-top-width:1px !important;border-right-color:#157fcc !important;border-right-width:1px !important}.x-panel-default-outer-border-trl{border-top-color:#157fcc !important;border-top-width:1px !important;border-right-color:#157fcc !important;border-right-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-outer-border-trb{border-top-color:#157fcc !important;border-top-width:1px !important;border-right-color:#157fcc !important;border-right-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important}.x-panel-default-outer-border-trbl{border-color:#157fcc !important;border-width:1px !important}.x-panel-default-framed{border-color:#157fcc;padding:0}.x-panel-default-framed.x-masked{border-color:#b9d9f0}.x-panel-header-default-framed{font-size:13px;border:5px solid #157fcc}.x-panel-header-default-framed .x-tool-tool-el{background-color:#157fcc}.x-panel-header-default-framed-horizontal{padding:5px 5px 5px 5px}.x-panel-header-default-framed-horizontal .x-panel-header-default-framed-tab-bar{margin-top:-5px;margin-bottom:-5px}.x-panel-header-default-framed-horizontal.x-header-noborder{padding:10px 10px 5px 10px}.x-panel-header-default-framed-horizontal.x-header-noborder .x-panel-header-default-framed-tab-bar{margin-top:-10px;margin-bottom:-5px}.x-panel-header-default-framed-vertical{padding:5px 5px 5px 5px}.x-panel-header-default-framed-vertical .x-panel-header-default-framed-tab-bar{margin-right:-5px;margin-left:-5px}.x-panel-header-default-framed-vertical.x-header-noborder{padding:10px 10px 10px 5px}.x-panel-header-default-framed-vertical.x-header-noborder .x-panel-header-default-framed-tab-bar{margin-right:-10px;margin-left:-5px}.x-panel-header-title-default-framed{color:#fff;font-size:13px;font-weight:bold;font-family: tahoma, verdana, sans-serif;line-height:16px}.x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus{outline:1px solid #fff;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus,.x-ie10p .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus,.x-edge .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after,.x-edge .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #fff;pointer-events:none}.x-panel-header-title-default-framed > .x-title-text-default-framed{text-transform:none;padding:0}.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-top{height:22px;padding-bottom:6px}.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-right{width:22px;padding-left:6px}.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-bottom{height:22px;padding-top:6px}.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-left{width:22px;padding-right:6px}.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed > .x-title-icon-default-framed{width:16px;height:16px;font-size:16px;color:#fff;background-position:center center}.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed > .x-title-icon-default-framed.x-title-glyph{opacity:0.5}.x-ie8 .x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed > .x-title-icon-default-framed.x-title-glyph{color:#8abfe6}.x-panel-body-default-framed{background:#fff;border-color:#c2c2c2;color:#000;font-size:13px;font-weight:normal;font-family: tahoma, verdana, sans-serif;border-width:1px;border-style:solid}.x-panel-default-framed{-webkit-border-radius:4px;-moz-border-radius:4px;-ms-border-radius:4px;-o-border-radius:4px;border-radius:4px;padding:0px 0px 0px 0px;border-width:5px;border-style:solid;background-color:#fff}.x-panel-default-framed-mc{background-color:#fff}.x-nbr .x-panel-default-framed{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-default-framed-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-0-0-0-0}.x-panel-default-framed-tl{background-position:0 -10px}.x-panel-default-framed-tr{background-position:right -15px}.x-panel-default-framed-bl{background-position:0 -20px}.x-panel-default-framed-br{background-position:right -25px}.x-panel-default-framed-ml{background-position:0 top}.x-panel-default-framed-mr{background-position:right top}.x-panel-default-framed-tc{background-position:0 0}.x-panel-default-framed-bc{background-position:0 -5px}.x-panel-default-framed-tr,.x-panel-default-framed-br,.x-panel-default-framed-mr{padding-right:5px}.x-panel-default-framed-tl,.x-panel-default-framed-bl,.x-panel-default-framed-ml{padding-left:5px}.x-panel-default-framed-tc{height:5px}.x-panel-default-framed-bc{height:5px}.x-panel-default-framed-tl,.x-panel-default-framed-bl,.x-panel-default-framed-tr,.x-panel-default-framed-br,.x-panel-default-framed-tc,.x-panel-default-framed-bc,.x-panel-default-framed-ml,.x-panel-default-framed-mr{background-image:url(images/panel/panel-default-framed-corners.gif)}.x-panel-default-framed-ml,.x-panel-default-framed-mr{background-image:url(images/panel/panel-default-framed-sides.gif);background-repeat:repeat-y}.x-panel-default-framed-mc{padding:0px 0px 0px 0px}.x-panel-header-default-framed-top{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:5px 5px 5px 5px;border-width:5px 5px 0 5px;border-style:solid;background-color:#157fcc}.x-panel-header-default-framed-top-mc{background-color:#157fcc}.x-nbr .x-panel-header-default-framed-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-default-framed-top-frameInfo{font-family:dh-5-5-0-5-5-5-0-5-5-5-5-5}.x-panel-header-default-framed-top-tl{background-position:0 -10px}.x-panel-header-default-framed-top-tr{background-position:right -15px}.x-panel-header-default-framed-top-bl{background-position:0 -20px}.x-panel-header-default-framed-top-br{background-position:right -25px}.x-panel-header-default-framed-top-ml{background-position:0 top}.x-panel-header-default-framed-top-mr{background-position:right top}.x-panel-header-default-framed-top-tc{background-position:0 0}.x-panel-header-default-framed-top-bc{background-position:0 -5px}.x-panel-header-default-framed-top-tr,.x-panel-header-default-framed-top-br,.x-panel-header-default-framed-top-mr{padding-right:5px}.x-panel-header-default-framed-top-tl,.x-panel-header-default-framed-top-bl,.x-panel-header-default-framed-top-ml{padding-left:5px}.x-panel-header-default-framed-top-tc{height:5px}.x-panel-header-default-framed-top-bc{height:0}.x-panel-header-default-framed-top-tl,.x-panel-header-default-framed-top-bl,.x-panel-header-default-framed-top-tr,.x-panel-header-default-framed-top-br,.x-panel-header-default-framed-top-tc,.x-panel-header-default-framed-top-bc,.x-panel-header-default-framed-top-ml,.x-panel-header-default-framed-top-mr{background-image:url(images/panel-header/panel-header-default-framed-top-corners.gif)}.x-panel-header-default-framed-top-ml,.x-panel-header-default-framed-top-mr{background-image:url(images/panel-header/panel-header-default-framed-top-sides.gif);background-repeat:repeat-y}.x-panel-header-default-framed-top-mc{padding:5px 5px 5px 5px}.x-panel-header-default-framed-right{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:5px 5px 5px 5px;border-width:5px 5px 5px 0;border-style:solid;background-color:#157fcc}.x-panel-header-default-framed-right-mc{background-color:#157fcc}.x-nbr .x-panel-header-default-framed-right{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-default-framed-right-frameInfo{font-family:dh-5-5-5-0-5-5-5-0-5-5-5-5}.x-panel-header-default-framed-right-tl{background-position:0 -10px}.x-panel-header-default-framed-right-tr{background-position:right -15px}.x-panel-header-default-framed-right-bl{background-position:0 -20px}.x-panel-header-default-framed-right-br{background-position:right -25px}.x-panel-header-default-framed-right-ml{background-position:right 0}.x-panel-header-default-framed-right-mr{background-position:right 0}.x-panel-header-default-framed-right-tc{background-position:0 0}.x-panel-header-default-framed-right-bc{background-position:0 -5px}.x-panel-header-default-framed-right-tr,.x-panel-header-default-framed-right-br,.x-panel-header-default-framed-right-mr{padding-right:5px}.x-panel-header-default-framed-right-tl,.x-panel-header-default-framed-right-bl,.x-panel-header-default-framed-right-ml{padding-left:0}.x-panel-header-default-framed-right-tc{height:5px}.x-panel-header-default-framed-right-bc{height:5px}.x-panel-header-default-framed-right-tl,.x-panel-header-default-framed-right-bl,.x-panel-header-default-framed-right-tr,.x-panel-header-default-framed-right-br,.x-panel-header-default-framed-right-tc,.x-panel-header-default-framed-right-bc,.x-panel-header-default-framed-right-ml,.x-panel-header-default-framed-right-mr{background-image:url(images/panel-header/panel-header-default-framed-right-corners.gif)}.x-panel-header-default-framed-right-ml,.x-panel-header-default-framed-right-mr{background-image:url(images/panel-header/panel-header-default-framed-right-sides.gif);background-repeat:repeat-y}.x-panel-header-default-framed-right-mc{padding:5px 5px 5px 5px}.x-panel-header-default-framed-bottom{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:0 5px 5px 5px;border-style:solid;background-color:#157fcc}.x-panel-header-default-framed-bottom-mc{background-color:#157fcc}.x-nbr .x-panel-header-default-framed-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-default-framed-bottom-frameInfo{font-family:dh-0-5-5-5-0-5-5-5-5-5-5-5}.x-panel-header-default-framed-bottom-tl{background-position:0 -10px}.x-panel-header-default-framed-bottom-tr{background-position:right -15px}.x-panel-header-default-framed-bottom-bl{background-position:0 -20px}.x-panel-header-default-framed-bottom-br{background-position:right -25px}.x-panel-header-default-framed-bottom-ml{background-position:0 bottom}.x-panel-header-default-framed-bottom-mr{background-position:right bottom}.x-panel-header-default-framed-bottom-tc{background-position:0 0}.x-panel-header-default-framed-bottom-bc{background-position:0 -5px}.x-panel-header-default-framed-bottom-tr,.x-panel-header-default-framed-bottom-br,.x-panel-header-default-framed-bottom-mr{padding-right:5px}.x-panel-header-default-framed-bottom-tl,.x-panel-header-default-framed-bottom-bl,.x-panel-header-default-framed-bottom-ml{padding-left:5px}.x-panel-header-default-framed-bottom-tc{height:0}.x-panel-header-default-framed-bottom-bc{height:5px}.x-panel-header-default-framed-bottom-tl,.x-panel-header-default-framed-bottom-bl,.x-panel-header-default-framed-bottom-tr,.x-panel-header-default-framed-bottom-br,.x-panel-header-default-framed-bottom-tc,.x-panel-header-default-framed-bottom-bc,.x-panel-header-default-framed-bottom-ml,.x-panel-header-default-framed-bottom-mr{background-image:url(images/panel-header/panel-header-default-framed-bottom-corners.gif)}.x-panel-header-default-framed-bottom-ml,.x-panel-header-default-framed-bottom-mr{background-image:url(images/panel-header/panel-header-default-framed-bottom-sides.gif);background-repeat:repeat-y}.x-panel-header-default-framed-bottom-mc{padding:5px 5px 5px 5px}.x-panel-header-default-framed-left{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px 0 5px 5px;border-style:solid;background-color:#157fcc}.x-panel-header-default-framed-left-mc{background-color:#157fcc}.x-nbr .x-panel-header-default-framed-left{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-default-framed-left-frameInfo{font-family:dh-5-0-5-5-5-0-5-5-5-5-5-5}.x-panel-header-default-framed-left-tl{background-position:0 -10px}.x-panel-header-default-framed-left-tr{background-position:right -15px}.x-panel-header-default-framed-left-bl{background-position:0 -20px}.x-panel-header-default-framed-left-br{background-position:right -25px}.x-panel-header-default-framed-left-ml{background-position:left 0}.x-panel-header-default-framed-left-mr{background-position:left 0}.x-panel-header-default-framed-left-tc{background-position:0 0}.x-panel-header-default-framed-left-bc{background-position:0 -5px}.x-panel-header-default-framed-left-tr,.x-panel-header-default-framed-left-br,.x-panel-header-default-framed-left-mr{padding-right:0}.x-panel-header-default-framed-left-tl,.x-panel-header-default-framed-left-bl,.x-panel-header-default-framed-left-ml{padding-left:5px}.x-panel-header-default-framed-left-tc{height:5px}.x-panel-header-default-framed-left-bc{height:5px}.x-panel-header-default-framed-left-tl,.x-panel-header-default-framed-left-bl,.x-panel-header-default-framed-left-tr,.x-panel-header-default-framed-left-br,.x-panel-header-default-framed-left-tc,.x-panel-header-default-framed-left-bc,.x-panel-header-default-framed-left-ml,.x-panel-header-default-framed-left-mr{background-image:url(images/panel-header/panel-header-default-framed-left-corners.gif)}.x-panel-header-default-framed-left-ml,.x-panel-header-default-framed-left-mr{background-image:url(images/panel-header/panel-header-default-framed-left-sides.gif);background-repeat:repeat-y}.x-panel-header-default-framed-left-mc{padding:5px 5px 5px 5px}.x-panel-header-default-framed-collapsed-top{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#157fcc}.x-panel-header-default-framed-collapsed-top-mc{background-color:#157fcc}.x-nbr .x-panel-header-default-framed-collapsed-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-default-framed-collapsed-top-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-panel-header-default-framed-collapsed-top-tl{background-position:0 -10px}.x-panel-header-default-framed-collapsed-top-tr{background-position:right -15px}.x-panel-header-default-framed-collapsed-top-bl{background-position:0 -20px}.x-panel-header-default-framed-collapsed-top-br{background-position:right -25px}.x-panel-header-default-framed-collapsed-top-ml{background-position:0 top}.x-panel-header-default-framed-collapsed-top-mr{background-position:right top}.x-panel-header-default-framed-collapsed-top-tc{background-position:0 0}.x-panel-header-default-framed-collapsed-top-bc{background-position:0 -5px}.x-panel-header-default-framed-collapsed-top-tr,.x-panel-header-default-framed-collapsed-top-br,.x-panel-header-default-framed-collapsed-top-mr{padding-right:5px}.x-panel-header-default-framed-collapsed-top-tl,.x-panel-header-default-framed-collapsed-top-bl,.x-panel-header-default-framed-collapsed-top-ml{padding-left:5px}.x-panel-header-default-framed-collapsed-top-tc{height:5px}.x-panel-header-default-framed-collapsed-top-bc{height:5px}.x-panel-header-default-framed-collapsed-top-tl,.x-panel-header-default-framed-collapsed-top-bl,.x-panel-header-default-framed-collapsed-top-tr,.x-panel-header-default-framed-collapsed-top-br,.x-panel-header-default-framed-collapsed-top-tc,.x-panel-header-default-framed-collapsed-top-bc,.x-panel-header-default-framed-collapsed-top-ml,.x-panel-header-default-framed-collapsed-top-mr{background-image:url(images/panel-header/panel-header-default-framed-collapsed-top-corners.gif)}.x-panel-header-default-framed-collapsed-top-ml,.x-panel-header-default-framed-collapsed-top-mr{background-image:url(images/panel-header/panel-header-default-framed-collapsed-top-sides.gif);background-repeat:repeat-y}.x-panel-header-default-framed-collapsed-top-mc{padding:5px 5px 5px 5px}.x-panel-header-default-framed-collapsed-right{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#157fcc}.x-panel-header-default-framed-collapsed-right-mc{background-color:#157fcc}.x-nbr .x-panel-header-default-framed-collapsed-right{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-default-framed-collapsed-right-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-panel-header-default-framed-collapsed-right-tl{background-position:0 -10px}.x-panel-header-default-framed-collapsed-right-tr{background-position:right -15px}.x-panel-header-default-framed-collapsed-right-bl{background-position:0 -20px}.x-panel-header-default-framed-collapsed-right-br{background-position:right -25px}.x-panel-header-default-framed-collapsed-right-ml{background-position:right 0}.x-panel-header-default-framed-collapsed-right-mr{background-position:right 0}.x-panel-header-default-framed-collapsed-right-tc{background-position:0 0}.x-panel-header-default-framed-collapsed-right-bc{background-position:0 -5px}.x-panel-header-default-framed-collapsed-right-tr,.x-panel-header-default-framed-collapsed-right-br,.x-panel-header-default-framed-collapsed-right-mr{padding-right:5px}.x-panel-header-default-framed-collapsed-right-tl,.x-panel-header-default-framed-collapsed-right-bl,.x-panel-header-default-framed-collapsed-right-ml{padding-left:5px}.x-panel-header-default-framed-collapsed-right-tc{height:5px}.x-panel-header-default-framed-collapsed-right-bc{height:5px}.x-panel-header-default-framed-collapsed-right-tl,.x-panel-header-default-framed-collapsed-right-bl,.x-panel-header-default-framed-collapsed-right-tr,.x-panel-header-default-framed-collapsed-right-br,.x-panel-header-default-framed-collapsed-right-tc,.x-panel-header-default-framed-collapsed-right-bc,.x-panel-header-default-framed-collapsed-right-ml,.x-panel-header-default-framed-collapsed-right-mr{background-image:url(images/panel-header/panel-header-default-framed-collapsed-right-corners.gif)}.x-panel-header-default-framed-collapsed-right-ml,.x-panel-header-default-framed-collapsed-right-mr{background-image:url(images/panel-header/panel-header-default-framed-collapsed-right-sides.gif);background-repeat:repeat-y}.x-panel-header-default-framed-collapsed-right-mc{padding:5px 5px 5px 5px}.x-panel-header-default-framed-collapsed-bottom{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#157fcc}.x-panel-header-default-framed-collapsed-bottom-mc{background-color:#157fcc}.x-nbr .x-panel-header-default-framed-collapsed-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-default-framed-collapsed-bottom-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-panel-header-default-framed-collapsed-bottom-tl{background-position:0 -10px}.x-panel-header-default-framed-collapsed-bottom-tr{background-position:right -15px}.x-panel-header-default-framed-collapsed-bottom-bl{background-position:0 -20px}.x-panel-header-default-framed-collapsed-bottom-br{background-position:right -25px}.x-panel-header-default-framed-collapsed-bottom-ml{background-position:0 bottom}.x-panel-header-default-framed-collapsed-bottom-mr{background-position:right bottom}.x-panel-header-default-framed-collapsed-bottom-tc{background-position:0 0}.x-panel-header-default-framed-collapsed-bottom-bc{background-position:0 -5px}.x-panel-header-default-framed-collapsed-bottom-tr,.x-panel-header-default-framed-collapsed-bottom-br,.x-panel-header-default-framed-collapsed-bottom-mr{padding-right:5px}.x-panel-header-default-framed-collapsed-bottom-tl,.x-panel-header-default-framed-collapsed-bottom-bl,.x-panel-header-default-framed-collapsed-bottom-ml{padding-left:5px}.x-panel-header-default-framed-collapsed-bottom-tc{height:5px}.x-panel-header-default-framed-collapsed-bottom-bc{height:5px}.x-panel-header-default-framed-collapsed-bottom-tl,.x-panel-header-default-framed-collapsed-bottom-bl,.x-panel-header-default-framed-collapsed-bottom-tr,.x-panel-header-default-framed-collapsed-bottom-br,.x-panel-header-default-framed-collapsed-bottom-tc,.x-panel-header-default-framed-collapsed-bottom-bc,.x-panel-header-default-framed-collapsed-bottom-ml,.x-panel-header-default-framed-collapsed-bottom-mr{background-image:url(images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif)}.x-panel-header-default-framed-collapsed-bottom-ml,.x-panel-header-default-framed-collapsed-bottom-mr{background-image:url(images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif);background-repeat:repeat-y}.x-panel-header-default-framed-collapsed-bottom-mc{padding:5px 5px 5px 5px}.x-panel-header-default-framed-collapsed-left{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#157fcc}.x-panel-header-default-framed-collapsed-left-mc{background-color:#157fcc}.x-nbr .x-panel-header-default-framed-collapsed-left{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-default-framed-collapsed-left-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-panel-header-default-framed-collapsed-left-tl{background-position:0 -10px}.x-panel-header-default-framed-collapsed-left-tr{background-position:right -15px}.x-panel-header-default-framed-collapsed-left-bl{background-position:0 -20px}.x-panel-header-default-framed-collapsed-left-br{background-position:right -25px}.x-panel-header-default-framed-collapsed-left-ml{background-position:left 0}.x-panel-header-default-framed-collapsed-left-mr{background-position:left 0}.x-panel-header-default-framed-collapsed-left-tc{background-position:0 0}.x-panel-header-default-framed-collapsed-left-bc{background-position:0 -5px}.x-panel-header-default-framed-collapsed-left-tr,.x-panel-header-default-framed-collapsed-left-br,.x-panel-header-default-framed-collapsed-left-mr{padding-right:5px}.x-panel-header-default-framed-collapsed-left-tl,.x-panel-header-default-framed-collapsed-left-bl,.x-panel-header-default-framed-collapsed-left-ml{padding-left:5px}.x-panel-header-default-framed-collapsed-left-tc{height:5px}.x-panel-header-default-framed-collapsed-left-bc{height:5px}.x-panel-header-default-framed-collapsed-left-tl,.x-panel-header-default-framed-collapsed-left-bl,.x-panel-header-default-framed-collapsed-left-tr,.x-panel-header-default-framed-collapsed-left-br,.x-panel-header-default-framed-collapsed-left-tc,.x-panel-header-default-framed-collapsed-left-bc,.x-panel-header-default-framed-collapsed-left-ml,.x-panel-header-default-framed-collapsed-left-mr{background-image:url(images/panel-header/panel-header-default-framed-collapsed-left-corners.gif)}.x-panel-header-default-framed-collapsed-left-ml,.x-panel-header-default-framed-collapsed-left-mr{background-image:url(images/panel-header/panel-header-default-framed-collapsed-left-sides.gif);background-repeat:repeat-y}.x-panel-header-default-framed-collapsed-left-mc{padding:5px 5px 5px 5px}.x-panel .x-panel-header-default-framed-top{border-bottom-width:5px !important}.x-panel .x-panel-header-default-framed-right{border-left-width:5px !important}.x-panel .x-panel-header-default-framed-bottom{border-top-width:5px !important}.x-panel .x-panel-header-default-framed-left{border-right-width:5px !important}.x-nbr .x-panel-header-default-framed-collapsed-top{border-bottom-width:0 !important}.x-nbr .x-panel-header-default-framed-collapsed-right{border-left-width:0 !important}.x-nbr .x-panel-header-default-framed-collapsed-bottom{border-top-width:0 !important}.x-nbr .x-panel-header-default-framed-collapsed-left{border-right-width:0 !important}.x-panel-header-default-framed-horizontal .x-tool-after-title{margin:0 0 0 6px}.x-panel-header-default-framed-horizontal .x-tool-before-title{margin:0 6px 0 0}.x-panel-header-default-framed-vertical .x-tool-after-title{margin:6px 0 0 0}.x-panel-header-default-framed-vertical .x-tool-before-title{margin:0 0 6px 0}.x-keyboard-mode .x-panel-header-default-framed .x-tool-focus{outline:1px solid #fff;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus,.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus,.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after,.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #fff;pointer-events:none}.x-panel-default-framed-resizable{overflow:visible}.x-panel-default-framed-resizable .x-panel-handle{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-panel-default-framed-resizable .x-panel-handle-north-br{top:-5px}.x-panel-default-framed-resizable .x-panel-handle-south-br{bottom:-5px}.x-panel-default-framed-resizable .x-panel-handle-east-br{right:-5px}.x-panel-default-framed-resizable .x-panel-handle-west-br{left:-5px}.x-panel-default-framed-resizable .x-panel-handle-northwest-br{left:-5px;top:-5px}.x-panel-default-framed-resizable .x-panel-handle-northeast-br{right:-5px;top:-5px}.x-panel-default-framed-resizable .x-panel-handle-southeast-br{right:-5px;bottom:-5px}.x-panel-default-framed-resizable .x-panel-handle-southwest-br{left:-5px;bottom:-5px}.x-panel-default-framed-outer-border-l{border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-framed-outer-border-b{border-bottom-color:#157fcc !important;border-bottom-width:1px !important}.x-panel-default-framed-outer-border-bl{border-bottom-color:#157fcc !important;border-bottom-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-framed-outer-border-r{border-right-color:#157fcc !important;border-right-width:1px !important}.x-panel-default-framed-outer-border-rl{border-right-color:#157fcc !important;border-right-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-framed-outer-border-rb{border-right-color:#157fcc !important;border-right-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important}.x-panel-default-framed-outer-border-rbl{border-right-color:#157fcc !important;border-right-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-framed-outer-border-t{border-top-color:#157fcc !important;border-top-width:1px !important}.x-panel-default-framed-outer-border-tl{border-top-color:#157fcc !important;border-top-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-framed-outer-border-tb{border-top-color:#157fcc !important;border-top-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important}.x-panel-default-framed-outer-border-tbl{border-top-color:#157fcc !important;border-top-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-framed-outer-border-tr{border-top-color:#157fcc !important;border-top-width:1px !important;border-right-color:#157fcc !important;border-right-width:1px !important}.x-panel-default-framed-outer-border-trl{border-top-color:#157fcc !important;border-top-width:1px !important;border-right-color:#157fcc !important;border-right-width:1px !important;border-left-color:#157fcc !important;border-left-width:1px !important}.x-panel-default-framed-outer-border-trb{border-top-color:#157fcc !important;border-top-width:1px !important;border-right-color:#157fcc !important;border-right-width:1px !important;border-bottom-color:#157fcc !important;border-bottom-width:1px !important}.x-panel-default-framed-outer-border-trbl{border-color:#157fcc !important;border-width:1px !important}.x-btn-group-default{border-color:#e0ebf3;-webkit-box-shadow:#fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset;-moz-box-shadow:#fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset;box-shadow:#fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset}.x-btn-group-header-default{padding:4px 5px;line-height:16px;background:#e0ebf3;-moz-border-radius-topleft:0px;-webkit-border-top-left-radius:0px;border-top-left-radius:0px;-moz-border-radius-topright:0px;-webkit-border-top-right-radius:0px;border-top-right-radius:0px}.x-btn-group-header-default .x-tool-img{background-image:url(images/tools/tool-sprites-dark.png);background-color:#e0ebf3}.x-btn-group-header-title-default{font:normal 13px tahoma, verdana, sans-serif;line-height:16px;color:#666}.x-btn-group-body-default{padding:0 1px}.x-btn-group-body-default .x-table-layout{border-spacing:5px}.x-btn-group-default-framed{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:0px 1px 0px 1px;border-width:3px;border-style:solid;background-color:#fff}.x-btn-group-default-framed-mc{background-color:#fff}.x-nbr .x-btn-group-default-framed{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-btn-group-default-framed-frameInfo{font-family:dh-3-3-3-3-3-3-3-3-0-1-0-1}.x-btn-group-default-framed-tl{background-position:0 -6px}.x-btn-group-default-framed-tr{background-position:right -9px}.x-btn-group-default-framed-bl{background-position:0 -12px}.x-btn-group-default-framed-br{background-position:right -15px}.x-btn-group-default-framed-ml{background-position:0 top}.x-btn-group-default-framed-mr{background-position:right top}.x-btn-group-default-framed-tc{background-position:0 0}.x-btn-group-default-framed-bc{background-position:0 -3px}.x-btn-group-default-framed-tr,.x-btn-group-default-framed-br,.x-btn-group-default-framed-mr{padding-right:3px}.x-btn-group-default-framed-tl,.x-btn-group-default-framed-bl,.x-btn-group-default-framed-ml{padding-left:3px}.x-btn-group-default-framed-tc{height:3px}.x-btn-group-default-framed-bc{height:3px}.x-btn-group-default-framed-tl,.x-btn-group-default-framed-bl,.x-btn-group-default-framed-tr,.x-btn-group-default-framed-br,.x-btn-group-default-framed-tc,.x-btn-group-default-framed-bc,.x-btn-group-default-framed-ml,.x-btn-group-default-framed-mr{background-image:url(images/btn-group/btn-group-default-framed-corners.gif)}.x-btn-group-default-framed-ml,.x-btn-group-default-framed-mr{background-image:url(images/btn-group/btn-group-default-framed-sides.gif);background-repeat:repeat-y}.x-btn-group-default-framed-mc{padding:0px 1px 0px 1px}.x-btn-group-default-framed-notitle{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:0px 1px 0px 1px;border-width:3px;border-style:solid;background-color:#fff}.x-btn-group-default-framed-notitle-mc{background-color:#fff}.x-nbr .x-btn-group-default-framed-notitle{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-btn-group-default-framed-notitle-frameInfo{font-family:dh-3-3-3-3-3-3-3-3-0-1-0-1}.x-btn-group-default-framed-notitle-tl{background-position:0 -6px}.x-btn-group-default-framed-notitle-tr{background-position:right -9px}.x-btn-group-default-framed-notitle-bl{background-position:0 -12px}.x-btn-group-default-framed-notitle-br{background-position:right -15px}.x-btn-group-default-framed-notitle-ml{background-position:0 top}.x-btn-group-default-framed-notitle-mr{background-position:right top}.x-btn-group-default-framed-notitle-tc{background-position:0 0}.x-btn-group-default-framed-notitle-bc{background-position:0 -3px}.x-btn-group-default-framed-notitle-tr,.x-btn-group-default-framed-notitle-br,.x-btn-group-default-framed-notitle-mr{padding-right:3px}.x-btn-group-default-framed-notitle-tl,.x-btn-group-default-framed-notitle-bl,.x-btn-group-default-framed-notitle-ml{padding-left:3px}.x-btn-group-default-framed-notitle-tc{height:3px}.x-btn-group-default-framed-notitle-bc{height:3px}.x-btn-group-default-framed-notitle-tl,.x-btn-group-default-framed-notitle-bl,.x-btn-group-default-framed-notitle-tr,.x-btn-group-default-framed-notitle-br,.x-btn-group-default-framed-notitle-tc,.x-btn-group-default-framed-notitle-bc,.x-btn-group-default-framed-notitle-ml,.x-btn-group-default-framed-notitle-mr{background-image:url(images/btn-group/btn-group-default-framed-notitle-corners.gif)}.x-btn-group-default-framed-notitle-ml,.x-btn-group-default-framed-notitle-mr{background-image:url(images/btn-group/btn-group-default-framed-notitle-sides.gif);background-repeat:repeat-y}.x-btn-group-default-framed-notitle-mc{padding:0px 1px 0px 1px}.x-btn-group-default-framed{border-color:#e0ebf3;-webkit-box-shadow:#fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset;-moz-box-shadow:#fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset;box-shadow:#fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset}.x-btn-group-header-default-framed{padding:4px 5px;line-height:16px;background:#e0ebf3;-moz-border-radius-topleft:3px;-webkit-border-top-left-radius:3px;border-top-left-radius:3px;-moz-border-radius-topright:3px;-webkit-border-top-right-radius:3px;border-top-right-radius:3px}.x-btn-group-header-default-framed .x-tool-img{background-image:url(images/tools/tool-sprites-dark.png);background-color:#e0ebf3}.x-btn-group-header-title-default-framed{font:normal 13px tahoma, verdana, sans-serif;line-height:16px;color:#666}.x-btn-group-body-default-framed{padding:0 1px}.x-btn-group-body-default-framed .x-table-layout{border-spacing:5px}.x-dashboard-column{padding:0 0 7px 0}.x-dashboard-panel{margin-top:7px}.x-dashboard-column-first{padding-left:7px;clear:left}.x-dashboard-column-last{padding-right:7px}.x-dashboard .x-panel-dd-spacer{border:2px dashed #99bbe8;background:#f6f6f6;border-radius:4px;-moz-border-radius:4px;margin-top:7px}.x-dashboard-dd-over{overflow:hidden !important}.x-window-ghost{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-window-default{border-color:#3892d4;-webkit-border-radius:4px;-moz-border-radius:4px;-ms-border-radius:4px;-o-border-radius:4px;border-radius:4px}.x-window-default{-webkit-border-radius:4px;-moz-border-radius:4px;-ms-border-radius:4px;-o-border-radius:4px;border-radius:4px;padding:0px 0px 0px 0px;border-width:5px;border-style:solid;background-color:#fff}.x-window-default-mc{background-color:#fff}.x-nbr .x-window-default{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-window-default-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-0-0-0-0}.x-window-default-tl{background-position:0 -10px}.x-window-default-tr{background-position:right -15px}.x-window-default-bl{background-position:0 -20px}.x-window-default-br{background-position:right -25px}.x-window-default-ml{background-position:0 top}.x-window-default-mr{background-position:right top}.x-window-default-tc{background-position:0 0}.x-window-default-bc{background-position:0 -5px}.x-window-default-tr,.x-window-default-br,.x-window-default-mr{padding-right:5px}.x-window-default-tl,.x-window-default-bl,.x-window-default-ml{padding-left:5px}.x-window-default-tc{height:5px}.x-window-default-bc{height:5px}.x-window-default-tl,.x-window-default-bl,.x-window-default-tr,.x-window-default-br,.x-window-default-tc,.x-window-default-bc,.x-window-default-ml,.x-window-default-mr{background-image:url(images/window/window-default-corners.gif)}.x-window-default-ml,.x-window-default-mr{background-image:url(images/window/window-default-sides.gif);background-repeat:repeat-y}.x-window-default-mc{padding:0px 0px 0px 0px}.x-window-body-default{border-color:#3892d4;border-width:1px;border-style:solid;background:#fff;color:#000;font-size:13px;font-weight:normal;font-family: tahoma, verdana, sans-serif}.x-window-header-default{font-size:13px;border-color:#3892d4;background-color:#3892d4}.x-window-header-default .x-tool-img{background-color:#3892d4}.x-window-header-default-horizontal .x-window-header-default-tab-bar{margin-top:-5px;margin-bottom:-5px}.x-window-header-default-vertical .x-window-header-default-tab-bar{margin-right:-5px;margin-left:-5px}.x-window-header-title-default{color:#fff;font-size:13px;font-weight:bold;font-family: tahoma, verdana, sans-serif;line-height:16px}.x-window-header-title-default > .x-title-text-default{padding:0;text-transform:none}.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-top{height:22px;padding-bottom:6px}.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-right{width:22px;padding-left:6px}.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-bottom{height:22px;padding-top:6px}.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-left{width:22px;padding-right:6px}.x-window-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default{width:16px;height:16px;font-size:16px;color:#fff;background-position:center center}.x-window-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph{opacity:0.5}.x-ie8 .x-window-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph{color:#9cc9e9}.x-window-header-default-top{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:5px 5px 5px 5px;border-width:5px 5px 5px 5px;border-style:solid;background-color:#3892d4}.x-window-header-default-top-mc{background-color:#3892d4}.x-nbr .x-window-header-default-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-window-header-default-top-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-window-header-default-top-tl{background-position:0 -10px}.x-window-header-default-top-tr{background-position:right -15px}.x-window-header-default-top-bl{background-position:0 -20px}.x-window-header-default-top-br{background-position:right -25px}.x-window-header-default-top-ml{background-position:0 top}.x-window-header-default-top-mr{background-position:right top}.x-window-header-default-top-tc{background-position:0 0}.x-window-header-default-top-bc{background-position:0 -5px}.x-window-header-default-top-tr,.x-window-header-default-top-br,.x-window-header-default-top-mr{padding-right:5px}.x-window-header-default-top-tl,.x-window-header-default-top-bl,.x-window-header-default-top-ml{padding-left:5px}.x-window-header-default-top-tc{height:5px}.x-window-header-default-top-bc{height:5px}.x-window-header-default-top-tl,.x-window-header-default-top-bl,.x-window-header-default-top-tr,.x-window-header-default-top-br,.x-window-header-default-top-tc,.x-window-header-default-top-bc,.x-window-header-default-top-ml,.x-window-header-default-top-mr{background-image:url(images/window-header/window-header-default-top-corners.gif)}.x-window-header-default-top-ml,.x-window-header-default-top-mr{background-image:url(images/window-header/window-header-default-top-sides.gif);background-repeat:repeat-y}.x-window-header-default-top-mc{padding:5px 5px 5px 5px}.x-window-header-default-right{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:5px 5px 5px 5px;border-width:5px 5px 5px 5px;border-style:solid;background-color:#3892d4}.x-window-header-default-right-mc{background-color:#3892d4}.x-nbr .x-window-header-default-right{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-window-header-default-right-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-window-header-default-right-tl{background-position:0 -10px}.x-window-header-default-right-tr{background-position:right -15px}.x-window-header-default-right-bl{background-position:0 -20px}.x-window-header-default-right-br{background-position:right -25px}.x-window-header-default-right-ml{background-position:0 top}.x-window-header-default-right-mr{background-position:right top}.x-window-header-default-right-tc{background-position:0 0}.x-window-header-default-right-bc{background-position:0 -5px}.x-window-header-default-right-tr,.x-window-header-default-right-br,.x-window-header-default-right-mr{padding-right:5px}.x-window-header-default-right-tl,.x-window-header-default-right-bl,.x-window-header-default-right-ml{padding-left:5px}.x-window-header-default-right-tc{height:5px}.x-window-header-default-right-bc{height:5px}.x-window-header-default-right-tl,.x-window-header-default-right-bl,.x-window-header-default-right-tr,.x-window-header-default-right-br,.x-window-header-default-right-tc,.x-window-header-default-right-bc,.x-window-header-default-right-ml,.x-window-header-default-right-mr{background-image:url(images/window-header/window-header-default-right-corners.gif)}.x-window-header-default-right-ml,.x-window-header-default-right-mr{background-image:url(images/window-header/window-header-default-right-sides.gif);background-repeat:repeat-y}.x-window-header-default-right-mc{padding:5px 5px 5px 5px}.x-window-header-default-bottom{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px 5px 5px 5px;border-style:solid;background-color:#3892d4}.x-window-header-default-bottom-mc{background-color:#3892d4}.x-nbr .x-window-header-default-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-window-header-default-bottom-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-window-header-default-bottom-tl{background-position:0 -10px}.x-window-header-default-bottom-tr{background-position:right -15px}.x-window-header-default-bottom-bl{background-position:0 -20px}.x-window-header-default-bottom-br{background-position:right -25px}.x-window-header-default-bottom-ml{background-position:0 top}.x-window-header-default-bottom-mr{background-position:right top}.x-window-header-default-bottom-tc{background-position:0 0}.x-window-header-default-bottom-bc{background-position:0 -5px}.x-window-header-default-bottom-tr,.x-window-header-default-bottom-br,.x-window-header-default-bottom-mr{padding-right:5px}.x-window-header-default-bottom-tl,.x-window-header-default-bottom-bl,.x-window-header-default-bottom-ml{padding-left:5px}.x-window-header-default-bottom-tc{height:5px}.x-window-header-default-bottom-bc{height:5px}.x-window-header-default-bottom-tl,.x-window-header-default-bottom-bl,.x-window-header-default-bottom-tr,.x-window-header-default-bottom-br,.x-window-header-default-bottom-tc,.x-window-header-default-bottom-bc,.x-window-header-default-bottom-ml,.x-window-header-default-bottom-mr{background-image:url(images/window-header/window-header-default-bottom-corners.gif)}.x-window-header-default-bottom-ml,.x-window-header-default-bottom-mr{background-image:url(images/window-header/window-header-default-bottom-sides.gif);background-repeat:repeat-y}.x-window-header-default-bottom-mc{padding:5px 5px 5px 5px}.x-window-header-default-left{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px 5px 5px 5px;border-style:solid;background-color:#3892d4}.x-window-header-default-left-mc{background-color:#3892d4}.x-nbr .x-window-header-default-left{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-window-header-default-left-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-window-header-default-left-tl{background-position:0 -10px}.x-window-header-default-left-tr{background-position:right -15px}.x-window-header-default-left-bl{background-position:0 -20px}.x-window-header-default-left-br{background-position:right -25px}.x-window-header-default-left-ml{background-position:0 top}.x-window-header-default-left-mr{background-position:right top}.x-window-header-default-left-tc{background-position:0 0}.x-window-header-default-left-bc{background-position:0 -5px}.x-window-header-default-left-tr,.x-window-header-default-left-br,.x-window-header-default-left-mr{padding-right:5px}.x-window-header-default-left-tl,.x-window-header-default-left-bl,.x-window-header-default-left-ml{padding-left:5px}.x-window-header-default-left-tc{height:5px}.x-window-header-default-left-bc{height:5px}.x-window-header-default-left-tl,.x-window-header-default-left-bl,.x-window-header-default-left-tr,.x-window-header-default-left-br,.x-window-header-default-left-tc,.x-window-header-default-left-bc,.x-window-header-default-left-ml,.x-window-header-default-left-mr{background-image:url(images/window-header/window-header-default-left-corners.gif)}.x-window-header-default-left-ml,.x-window-header-default-left-mr{background-image:url(images/window-header/window-header-default-left-sides.gif);background-repeat:repeat-y}.x-window-header-default-left-mc{padding:5px 5px 5px 5px}.x-window-header-default-collapsed-top{-webkit-border-radius:4px;-moz-border-radius:4px;-ms-border-radius:4px;-o-border-radius:4px;border-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#3892d4}.x-window-header-default-collapsed-top-mc{background-color:#3892d4}.x-nbr .x-window-header-default-collapsed-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-window-header-default-collapsed-top-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-window-header-default-collapsed-top-tl{background-position:0 -10px}.x-window-header-default-collapsed-top-tr{background-position:right -15px}.x-window-header-default-collapsed-top-bl{background-position:0 -20px}.x-window-header-default-collapsed-top-br{background-position:right -25px}.x-window-header-default-collapsed-top-ml{background-position:0 top}.x-window-header-default-collapsed-top-mr{background-position:right top}.x-window-header-default-collapsed-top-tc{background-position:0 0}.x-window-header-default-collapsed-top-bc{background-position:0 -5px}.x-window-header-default-collapsed-top-tr,.x-window-header-default-collapsed-top-br,.x-window-header-default-collapsed-top-mr{padding-right:5px}.x-window-header-default-collapsed-top-tl,.x-window-header-default-collapsed-top-bl,.x-window-header-default-collapsed-top-ml{padding-left:5px}.x-window-header-default-collapsed-top-tc{height:5px}.x-window-header-default-collapsed-top-bc{height:5px}.x-window-header-default-collapsed-top-tl,.x-window-header-default-collapsed-top-bl,.x-window-header-default-collapsed-top-tr,.x-window-header-default-collapsed-top-br,.x-window-header-default-collapsed-top-tc,.x-window-header-default-collapsed-top-bc,.x-window-header-default-collapsed-top-ml,.x-window-header-default-collapsed-top-mr{background-image:url(images/window-header/window-header-default-collapsed-top-corners.gif)}.x-window-header-default-collapsed-top-ml,.x-window-header-default-collapsed-top-mr{background-image:url(images/window-header/window-header-default-collapsed-top-sides.gif);background-repeat:repeat-y}.x-window-header-default-collapsed-top-mc{padding:5px 5px 5px 5px}.x-window-header-default-collapsed-right{-webkit-border-radius:4px;-moz-border-radius:4px;-ms-border-radius:4px;-o-border-radius:4px;border-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#3892d4}.x-window-header-default-collapsed-right-mc{background-color:#3892d4}.x-nbr .x-window-header-default-collapsed-right{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-window-header-default-collapsed-right-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-window-header-default-collapsed-right-tl{background-position:0 -10px}.x-window-header-default-collapsed-right-tr{background-position:right -15px}.x-window-header-default-collapsed-right-bl{background-position:0 -20px}.x-window-header-default-collapsed-right-br{background-position:right -25px}.x-window-header-default-collapsed-right-ml{background-position:0 top}.x-window-header-default-collapsed-right-mr{background-position:right top}.x-window-header-default-collapsed-right-tc{background-position:0 0}.x-window-header-default-collapsed-right-bc{background-position:0 -5px}.x-window-header-default-collapsed-right-tr,.x-window-header-default-collapsed-right-br,.x-window-header-default-collapsed-right-mr{padding-right:5px}.x-window-header-default-collapsed-right-tl,.x-window-header-default-collapsed-right-bl,.x-window-header-default-collapsed-right-ml{padding-left:5px}.x-window-header-default-collapsed-right-tc{height:5px}.x-window-header-default-collapsed-right-bc{height:5px}.x-window-header-default-collapsed-right-tl,.x-window-header-default-collapsed-right-bl,.x-window-header-default-collapsed-right-tr,.x-window-header-default-collapsed-right-br,.x-window-header-default-collapsed-right-tc,.x-window-header-default-collapsed-right-bc,.x-window-header-default-collapsed-right-ml,.x-window-header-default-collapsed-right-mr{background-image:url(images/window-header/window-header-default-collapsed-right-corners.gif)}.x-window-header-default-collapsed-right-ml,.x-window-header-default-collapsed-right-mr{background-image:url(images/window-header/window-header-default-collapsed-right-sides.gif);background-repeat:repeat-y}.x-window-header-default-collapsed-right-mc{padding:5px 5px 5px 5px}.x-window-header-default-collapsed-bottom{-webkit-border-radius:4px;-moz-border-radius:4px;-ms-border-radius:4px;-o-border-radius:4px;border-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#3892d4}.x-window-header-default-collapsed-bottom-mc{background-color:#3892d4}.x-nbr .x-window-header-default-collapsed-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-window-header-default-collapsed-bottom-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-window-header-default-collapsed-bottom-tl{background-position:0 -10px}.x-window-header-default-collapsed-bottom-tr{background-position:right -15px}.x-window-header-default-collapsed-bottom-bl{background-position:0 -20px}.x-window-header-default-collapsed-bottom-br{background-position:right -25px}.x-window-header-default-collapsed-bottom-ml{background-position:0 top}.x-window-header-default-collapsed-bottom-mr{background-position:right top}.x-window-header-default-collapsed-bottom-tc{background-position:0 0}.x-window-header-default-collapsed-bottom-bc{background-position:0 -5px}.x-window-header-default-collapsed-bottom-tr,.x-window-header-default-collapsed-bottom-br,.x-window-header-default-collapsed-bottom-mr{padding-right:5px}.x-window-header-default-collapsed-bottom-tl,.x-window-header-default-collapsed-bottom-bl,.x-window-header-default-collapsed-bottom-ml{padding-left:5px}.x-window-header-default-collapsed-bottom-tc{height:5px}.x-window-header-default-collapsed-bottom-bc{height:5px}.x-window-header-default-collapsed-bottom-tl,.x-window-header-default-collapsed-bottom-bl,.x-window-header-default-collapsed-bottom-tr,.x-window-header-default-collapsed-bottom-br,.x-window-header-default-collapsed-bottom-tc,.x-window-header-default-collapsed-bottom-bc,.x-window-header-default-collapsed-bottom-ml,.x-window-header-default-collapsed-bottom-mr{background-image:url(images/window-header/window-header-default-collapsed-bottom-corners.gif)}.x-window-header-default-collapsed-bottom-ml,.x-window-header-default-collapsed-bottom-mr{background-image:url(images/window-header/window-header-default-collapsed-bottom-sides.gif);background-repeat:repeat-y}.x-window-header-default-collapsed-bottom-mc{padding:5px 5px 5px 5px}.x-window-header-default-collapsed-left{-webkit-border-radius:4px;-moz-border-radius:4px;-ms-border-radius:4px;-o-border-radius:4px;border-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#3892d4}.x-window-header-default-collapsed-left-mc{background-color:#3892d4}.x-nbr .x-window-header-default-collapsed-left{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-window-header-default-collapsed-left-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-window-header-default-collapsed-left-tl{background-position:0 -10px}.x-window-header-default-collapsed-left-tr{background-position:right -15px}.x-window-header-default-collapsed-left-bl{background-position:0 -20px}.x-window-header-default-collapsed-left-br{background-position:right -25px}.x-window-header-default-collapsed-left-ml{background-position:0 top}.x-window-header-default-collapsed-left-mr{background-position:right top}.x-window-header-default-collapsed-left-tc{background-position:0 0}.x-window-header-default-collapsed-left-bc{background-position:0 -5px}.x-window-header-default-collapsed-left-tr,.x-window-header-default-collapsed-left-br,.x-window-header-default-collapsed-left-mr{padding-right:5px}.x-window-header-default-collapsed-left-tl,.x-window-header-default-collapsed-left-bl,.x-window-header-default-collapsed-left-ml{padding-left:5px}.x-window-header-default-collapsed-left-tc{height:5px}.x-window-header-default-collapsed-left-bc{height:5px}.x-window-header-default-collapsed-left-tl,.x-window-header-default-collapsed-left-bl,.x-window-header-default-collapsed-left-tr,.x-window-header-default-collapsed-left-br,.x-window-header-default-collapsed-left-tc,.x-window-header-default-collapsed-left-bc,.x-window-header-default-collapsed-left-ml,.x-window-header-default-collapsed-left-mr{background-image:url(images/window-header/window-header-default-collapsed-left-corners.gif)}.x-window-header-default-collapsed-left-ml,.x-window-header-default-collapsed-left-mr{background-image:url(images/window-header/window-header-default-collapsed-left-sides.gif);background-repeat:repeat-y}.x-window-header-default-collapsed-left-mc{padding:5px 5px 5px 5px}.x-window-header-default .x-window-header-icon{width:16px;height:16px;color:#fff;font-size:16px;line-height:16px;background-position:center center}.x-window-header-default .x-window-header-glyph{color:#fff;font-size:16px;line-height:16px;opacity:0.5}.x-ie8 .x-window-header-default .x-window-header-glyph{color:#9cc9e9}.x-window-header-default-horizontal .x-tool-after-title{margin:0 0 0 6px}.x-window-header-default-horizontal .x-tool-before-title{margin:0 6px 0 0}.x-window-header-default-vertical .x-tool-after-title{margin:6px 0 0 0}.x-window-header-default-vertical .x-tool-before-title{margin:0 0 6px 0}.x-keyboard-mode .x-window-header-default .x-tool-focus{outline:1px solid #fff;outline-offset:2px}.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus,.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus,.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus{outline:none}.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus:after,.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus:after,.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #fff;pointer-events:none}.x-window-header-default{border-width:5px !important}.x-nbr .x-window-default-collapsed .x-window-header{border-width:0 !important}.x-window-default-resizable{overflow:visible}.x-window-default-resizable .x-window-handle-north-br{top:-5px}.x-window-default-resizable .x-window-handle-south-br{bottom:-5px}.x-window-default-resizable .x-window-handle-east-br{right:-5px}.x-window-default-resizable .x-window-handle-west-br{left:-5px}.x-window-default-resizable .x-window-handle-northwest-br{left:-5px;top:-5px}.x-window-default-resizable .x-window-handle-northeast-br{right:-5px;top:-5px}.x-window-default-resizable .x-window-handle-southeast-br{right:-5px;bottom:-5px}.x-window-default-resizable .x-window-handle-southwest-br{left:-5px;bottom:-5px}.x-window-default-outer-border-l{border-left-color:#3892d4 !important;border-left-width:1px !important}.x-window-default-outer-border-b{border-bottom-color:#3892d4 !important;border-bottom-width:1px !important}.x-window-default-outer-border-bl{border-bottom-color:#3892d4 !important;border-bottom-width:1px !important;border-left-color:#3892d4 !important;border-left-width:1px !important}.x-window-default-outer-border-r{border-right-color:#3892d4 !important;border-right-width:1px !important}.x-window-default-outer-border-rl{border-right-color:#3892d4 !important;border-right-width:1px !important;border-left-color:#3892d4 !important;border-left-width:1px !important}.x-window-default-outer-border-rb{border-right-color:#3892d4 !important;border-right-width:1px !important;border-bottom-color:#3892d4 !important;border-bottom-width:1px !important}.x-window-default-outer-border-rbl{border-right-color:#3892d4 !important;border-right-width:1px !important;border-bottom-color:#3892d4 !important;border-bottom-width:1px !important;border-left-color:#3892d4 !important;border-left-width:1px !important}.x-window-default-outer-border-t{border-top-color:#3892d4 !important;border-top-width:1px !important}.x-window-default-outer-border-tl{border-top-color:#3892d4 !important;border-top-width:1px !important;border-left-color:#3892d4 !important;border-left-width:1px !important}.x-window-default-outer-border-tb{border-top-color:#3892d4 !important;border-top-width:1px !important;border-bottom-color:#3892d4 !important;border-bottom-width:1px !important}.x-window-default-outer-border-tbl{border-top-color:#3892d4 !important;border-top-width:1px !important;border-bottom-color:#3892d4 !important;border-bottom-width:1px !important;border-left-color:#3892d4 !important;border-left-width:1px !important}.x-window-default-outer-border-tr{border-top-color:#3892d4 !important;border-top-width:1px !important;border-right-color:#3892d4 !important;border-right-width:1px !important}.x-window-default-outer-border-trl{border-top-color:#3892d4 !important;border-top-width:1px !important;border-right-color:#3892d4 !important;border-right-width:1px !important;border-left-color:#3892d4 !important;border-left-width:1px !important}.x-window-default-outer-border-trb{border-top-color:#3892d4 !important;border-top-width:1px !important;border-right-color:#3892d4 !important;border-right-width:1px !important;border-bottom-color:#3892d4 !important;border-bottom-width:1px !important}.x-window-default-outer-border-trbl{border-color:#3892d4 !important;border-width:1px !important}.x-window-body-plain{background-color:transparent}.x-form-item-label-default{color:#000;font:normal 13px/17px tahoma, verdana, sans-serif;min-height:24px;padding-top:4px;padding-right:5px}.x-ie8 .x-form-item-label-default{min-height:20px}.x-form-item-label-default.x-form-item-label-top{height:1px}.x-form-item-label-default.x-form-item-label-top > .x-form-item-label-inner{padding-top:4px;padding-bottom:5px}.x-form-item-label-default.x-form-item-label-top-side-error:after{width:26px}.x-form-item-body-default{min-height:24px}.x-form-invalid-icon-default{width:16px;height:16px;margin:0 5px;background:url(images/form/exclamation.png) no-repeat}.x-form-invalid-under-default{padding:2px 2px 2px 20px;color:#cf4c35;font:normal 13px/16px tahoma, verdana, sans-serif;background:no-repeat 0 2px;background-image:url(images/form/exclamation.png)}.x-form-error-wrap-default.x-form-error-wrap-side{width:26px}.x-form-item-default.x-item-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=30)";opacity:0.3}.x-autocontainer-form-item,.x-anchor-form-item,.x-vbox-form-item,.x-table-form-item{margin-bottom:5px}.x-form-text-field-body-default{min-width:170px;max-width:170px}.x-form-trigger-wrap-default{border-width:1px;border-style:solid;border-color:#c2c2c2 #dadada #dadada}.x-form-trigger-wrap-default.x-form-trigger-wrap-focus{border-color:#3892d4}.x-form-trigger-wrap-default.x-form-trigger-wrap-invalid{border-color:#cf4c35}.x-form-text-default{color:#000;padding:3px 6px 2px;background-color:#fff;font:normal 13px/17px tahoma, verdana, sans-serif;min-height:22px}.x-ie8 .x-form-text-default{min-height:17px}.x-form-text-default.x-form-textarea{line-height:15px;min-height:60px}.x-ie8 .x-form-text-default.x-form-textarea{min-height:55px}.x-form-text-default.x-form-text-file{color:grey}.x-form-text-default.x-webkit-border-box-bug{height:calc(100% + 5px)}.x-placeholder-label-default{padding:3px 6px 2px}.x-form-empty-field-default + .x-placeholder-label-default{color:grey}.x-form-text-default:-ms-input-placeholder{color:grey}.x-form-invalid-field-default{background-color:#fff}.x-form-trigger-default{width:22px;background:0 center #fff url(images/form/trigger.png) no-repeat}.x-form-trigger-default.x-form-trigger-over{background-position:-22px center}.x-form-trigger-default.x-form-trigger-over.x-form-trigger-focus{background-position:-88px center}.x-form-trigger-default.x-form-trigger-focus{background-position:-66px center}.x-form-trigger.x-form-trigger-default.x-form-trigger-click{background-position:-44px center}.x-textfield-default-cell > .x-grid-cell-inner{padding-top:0px;padding-bottom:0px}.x-form-clear-trigger{background-image:url(images/form/clear-trigger.png)}.x-form-search-trigger{background-image:url(images/form/search-trigger.png)}.x-message-box .x-window-body{background-color:#fff;border-width:0}.x-message-box-info,.x-message-box-warning,.x-message-box-question,.x-message-box-error{background-position:left top;background-repeat:no-repeat}.x-message-box-icon{height:32px;width:32px;margin-right:10px}.x-message-box-info{background-image:url(images/shared/icon-info.png)}.x-message-box-warning{background-image:url(images/shared/icon-warning.png)}.x-message-box-question{background-image:url(images/shared/icon-question.png)}.x-message-box-error{background-image:url(images/shared/icon-error.png)}.x-form-cb-wrap-default{height:24px;min-width:15px}.x-form-cb-default{margin-top:5px}.x-form-checkbox-default,.x-form-radio-default{width:15px;height:15px}.x-form-radio-default{background:url(images/form/radio.png) no-repeat}.x-form-cb-checked .x-form-radio-default{background-position:0 -15px}.x-form-checkbox-default{background:url(images/form/checkbox.png) no-repeat}.x-form-cb-checked .x-form-checkbox-default{background-position:0 -15px}.x-keyboard-mode .x-form-checkbox-focus.x-form-radio-default{background-position:-15px 0}.x-keyboard-mode .x-form-checkbox-focus.x-form-checkbox-default{background-position:-15px 0}.x-keyboard-mode .x-form-cb-checked .x-form-checkbox-focus.x-form-radio-default{background-position:-15px -15px}.x-keyboard-mode .x-form-cb-checked .x-form-checkbox-focus.x-form-checkbox-default{background-position:-15px -15px}.x-form-cb-label-default{margin-top:4px;font:normal 13px/17px tahoma, verdana, sans-serif;color:#000}.x-form-cb-label-default.x-form-cb-label-before{padding-right:19px}.x-form-cb-label-default.x-form-cb-label-after{padding-left:19px}.x-checkbox-default-cell > .x-grid-cell-inner{padding-top:0px;padding-bottom:0px}.x-form-item-body-default.x-form-checkboxgroup-body{padding:0 4px}.x-form-invalid .x-form-item-body-default.x-form-checkboxgroup-body{border-width:1px;border-style:solid;border-color:#cf4c35}.x-fieldset-default{border:1px solid #b0b0b0;padding:0 10px;margin:0 0 10px}.x-ie8 .x-fieldset-default{padding-top:0}.x-ie8 .x-fieldset-body-default{padding-top:0}.x-fieldset-header-default{padding:0 3px 1px;line-height:16px}.x-fieldset-header-default > .x-fieldset-header-text{font:normal 12px/16px tahoma, verdana, sans-serif;color:#000;padding:1px 0}.x-fieldset-header-checkbox-default{margin:2px 4px 0 0;line-height:16px}.x-fieldset-header-tool-default{margin:2px 4px 0 0;padding:0}.x-fieldset-header-tool-default > .x-tool-img{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=80)";opacity:0.8;height:15px;width:15px}.x-fieldset-header-tool-default.x-tool-over > .x-tool-img{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=90)";opacity:0.9}.x-fieldset-header-tool-default.x-tool-pressed > .x-tool-img{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";opacity:1}.x-fieldset-header-tool-default > .x-tool-toggle{background-image:url(images/fieldset/collapse-tool.png);background-position:0 0}.x-fieldset-header-tool-default.x-tool-over > .x-tool-toggle{background-position:0 -15px}.x-keyboard-mode .x-fieldset-header-tool-default.x-focus{outline:1px solid #3892d4}.x-fieldset-default.x-fieldset-collapsed{border-width:1px 1px 0 1px;border-left-color:transparent;border-right-color:transparent}.x-fieldset-default.x-fieldset-collapsed .x-tool-toggle{background-position:-15px 0}.x-fieldset-default.x-fieldset-collapsed .x-tool-over > .x-tool-toggle{background-position:-15px -15px}.x-form-trigger-spinner-default{width:22px}.x-form-spinner-default{background-image:url(images/form/spinner.png);background-color:#fff;width:22px;height:11px}.x-form-spinner-up-default{background-position:0 0}.x-form-spinner-up-default.x-form-spinner-over{background-position:-22px 0}.x-form-spinner-up-default.x-form-spinner-over.x-form-spinner-focus{background-position:-88px 0}.x-form-spinner-up-default.x-form-spinner-focus{background-position:-66px 0}.x-form-spinner-up-default.x-form-spinner.x-form-spinner-click{background-position:-44px 0}.x-form-spinner-down-default{background-position:0 -11px}.x-form-spinner-down-default.x-form-spinner-over{background-position:-22px -11px}.x-form-spinner-down-default.x-form-spinner-over.x-form-spinner-focus{background-position:-88px -11px}.x-form-spinner-down-default.x-form-spinner-focus{background-position:-66px -11px}.x-form-spinner-down-default.x-form-spinner.x-form-spinner-click{background-position:-44px -11px}.x-tbar-page-number{width:30px}.x-btn-icon-el.x-tbar-page-first{background-image:url(images/grid/page-first.png)}.x-btn-icon-el.x-tbar-page-prev{background-image:url(images/grid/page-prev.png)}.x-btn-icon-el.x-tbar-page-next{background-image:url(images/grid/page-next.png)}.x-btn-icon-el.x-tbar-page-last{background-image:url(images/grid/page-last.png)}.x-btn-icon-el.x-tbar-loading{background-image:url(images/grid/refresh.png)}.x-boundlist{border-width:1px;border-style:solid;border-color:#e1e1e1;background:#fff}.x-boundlist-item{padding:0 6px;font:normal 13px tahoma, verdana, sans-serif;line-height:22px;cursor:pointer;cursor:hand;position:relative;border-width:1px;border-style:dotted;border-color:#fff;color:#000}.x-boundlist-selected{background:#c2ddf2;border-color:#c2ddf2}.x-boundlist-item-over{background:#d6e9f6;border-color:#d6e9f6}.x-boundlist-floating{border-top-width:0}.x-boundlist-above{border-top-width:1px;border-bottom-width:1px}.x-datepicker{border-width:1px;border-style:solid;border-color:#e1e1e1;background-color:#fff;width:212px}.x-datepicker-header{padding:4px 6px;text-align:center;background-color:#f5f5f5}.x-datepicker-arrow{width:12px;height:12px;top:9px;cursor:pointer;-webkit-touch-callout:none;background-color:#f5f5f5;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=70)";opacity:0.7}div.x-datepicker-arrow:hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";opacity:1}.x-datepicker-next{right:6px;background:url(images/datepicker/arrow-right.png) no-repeat 0 0}.x-datepicker-prev{left:6px;background:url(images/datepicker/arrow-left.png) no-repeat 0 0}.x-datepicker-month{background:transparent}.x-datepicker-month .x-btn,.x-datepicker-month .x-btn .x-btn-tc,.x-datepicker-month .x-btn .x-btn-tl,.x-datepicker-month .x-btn .x-btn-tr,.x-datepicker-month .x-btn .x-btn-mc,.x-datepicker-month .x-btn .x-btn-ml,.x-datepicker-month .x-btn .x-btn-mr,.x-datepicker-month .x-btn .x-btn-bc,.x-datepicker-month .x-btn .x-btn-bl,.x-datepicker-month .x-btn .x-btn-br{background:transparent;border-width:0 !important}.x-datepicker-month .x-btn-inner{color:#3892d4}.x-datepicker-month .x-btn-split-right:after,.x-datepicker-month .x-btn-over .x-btn-split-right:after{background-image:url(images/datepicker/month-arrow.png);padding:0;text-align:right;width:8px}.x-datepicker-month .x-btn{padding:3px}.x-datepicker-month .x-btn-over{border-color:transparent;background:transparent}.x-datepicker-month .x-btn.x-btn-pressed{border-color:transparent;background:transparent}.x-datepicker-month .x-btn-inner{font-size:12px}.x-datepicker-column-header{width:30px;color:#000;font:bold 13px tahoma, verdana, sans-serif;text-align:right;background-color:#fff}.x-datepicker-column-header-inner{line-height:25px;padding:0 9px 0 0}.x-datepicker-cell{text-align:right;border:1px solid #fff}.x-datepicker-date{padding:0 7px 0 0;font:normal 13px tahoma, verdana, sans-serif;color:#000;cursor:pointer;line-height:23px}div.x-datepicker-date:hover{color:#000;background-color:#ebf4fb}.x-datepicker-selected{border-style:solid;border-color:#3892d4}.x-datepicker-selected div.x-datepicker-date{background-color:#d6e9f6;color:#000;font-weight:bold}.x-datepicker-today{border-color:darkred;border-style:solid}.x-datepicker-prevday .x-datepicker-date,.x-datepicker-nextday .x-datepicker-date{color:#bfbfbf}.x-datepicker-disabled .x-datepicker-date{background-color:#eee;cursor:default;color:grey}.x-datepicker-disabled div.x-datepicker-date:hover{background-color:#eee;color:grey}.x-datepicker-footer,.x-monthpicker-buttons{padding:3px 0;background-color:#f5f5f5;text-align:center}.x-datepicker-footer .x-btn,.x-monthpicker-buttons .x-btn{margin:0 3px 0 2px}.x-monthpicker{width:212px;border-width:1px;border-style:solid;border-color:#e1e1e1;background-color:#fff}.x-monthpicker-months{border-width:0 1px 0 0;border-color:#e1e1e1;border-style:solid;width:105px}.x-monthpicker-months .x-monthpicker-item{width:52px}.x-monthpicker-years{width:105px}.x-monthpicker-years .x-monthpicker-item{width:52px}.x-monthpicker-item{margin:5px 0 5px;font:normal 13px tahoma, verdana, sans-serif;text-align:center}.x-monthpicker-item-inner{margin:0 5px 0 5px;color:#000;border:1px solid #fff;line-height:22px;cursor:pointer}a.x-monthpicker-item-inner:hover{color:#000;background-color:#ebf4fb}.x-monthpicker-item a.x-monthpicker-selected{background-color:#d6e9f6;color:#000;border-style:solid;border-color:#3892d4}.x-monthpicker-yearnav{height:34px}.x-monthpicker-yearnav-button-ct{width:52px}.x-monthpicker-yearnav-button{height:12px;width:12px;cursor:pointer;margin-top:11px;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=70)";opacity:0.7;-webkit-touch-callout:none;background-color:#fff}a.x-monthpicker-yearnav-button:hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";opacity:1}.x-monthpicker-yearnav-next{background:url(images/datepicker/arrow-right.png) no-repeat 0 0}.x-monthpicker-yearnav-next-over{background-position:0 0}.x-monthpicker-yearnav-prev{background:url(images/datepicker/arrow-left.png) no-repeat 0 0}.x-monthpicker-yearnav-prev-over{background-position:0 0}.x-monthpicker-small .x-monthpicker-item{margin:2px 0 2px}.x-monthpicker-small .x-monthpicker-item-inner{margin:0 5px 0 5px}.x-monthpicker-small .x-monthpicker-yearnav{height:28px}.x-monthpicker-small .x-monthpicker-yearnav-button{margin-top:8px}.x-form-field-date .x-form-date-trigger{background-image:url(images/form/date-trigger.png)}.x-form-display-field-default{min-height:24px;font:normal 13px/17px tahoma, verdana, sans-serif;color:#000;margin-top:4px}.x-keyboard-mode .x-form-display-field-default.x-field-form-focus{outline:1px solid #3892d4;outline-offset:-1px}.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus,.x-ie10p .x-keyboard-mode .x-form-display-field-default.x-field-form-focus,.x-edge .x-keyboard-mode .x-form-display-field-default.x-field-form-focus{outline:none}.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after,.x-ie10p .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after,.x-edge .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after{position:absolute;content:' ';top:0px;right:0px;bottom:0px;left:0px;border:1px solid #3892d4;pointer-events:none}.x-ie8 .x-form-display-field-default.x-field-form-focus{position:relative}.x-tip-default{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:2px 2px 2px 2px;border-width:1px;border-style:solid;background-color:#ebf4fb}.x-tip-default-mc{background-color:#ebf4fb}.x-nbr .x-tip-default{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-tip-default-frameInfo{font-family:th-3-3-3-3-1-1-1-1-2-2-2-2}.x-tip-default-tl{background-position:0 -6px}.x-tip-default-tr{background-position:right -9px}.x-tip-default-bl{background-position:0 -12px}.x-tip-default-br{background-position:right -15px}.x-tip-default-ml{background-position:0 top}.x-tip-default-mr{background-position:right top}.x-tip-default-tc{background-position:0 0}.x-tip-default-bc{background-position:0 -3px}.x-tip-default-tr,.x-tip-default-br,.x-tip-default-mr{padding-right:3px}.x-tip-default-tl,.x-tip-default-bl,.x-tip-default-ml{padding-left:3px}.x-tip-default-tc{height:3px}.x-tip-default-bc{height:3px}.x-tip-default-tl,.x-tip-default-bl,.x-tip-default-tr,.x-tip-default-br,.x-tip-default-tc,.x-tip-default-bc,.x-tip-default-ml,.x-tip-default-mr{background-image:url(images/tip/tip-default-corners.gif)}.x-tip-default-ml,.x-tip-default-mr{background-image:url(images/tip/tip-default-sides.gif);background-repeat:repeat-y}.x-tip-default-mc{padding:0px 0px 0px 0px}.x-tip-default{background-color:#ebf4fb;border-color:#e1e1e1}.x-tip-default .x-tool-img{background-image:url(images/tools/tool-sprites-dark.png);background-color:#ebf4fb}.x-tip-header-default .x-tool-after-title{margin:0 0 0 6px}.x-tip-header-default .x-tool-before-title{margin:0 6px 0 0}.x-tip-header-default{padding:3px 3px 0 3px}.x-tip-header-title-default{color:#000;font-size:13px;font-weight:bold}.x-tip-body-default{padding:3px;color:#000;font-size:13px;font-weight:normal}.x-tip-body-default a{color:#000}.x-tip-default .x-tip-anchor{border:6px solid transparent;_border-color:pink;_filter:chroma(color=pink)}.x-tip-default .x-tip-anchor:after{position:absolute;border:6px solid transparent;content:"";_border-color:pink;_filter:chroma(color=pink)}.x-tip-default .x-tip-anchor-top{border-top-width:0;border-bottom:6px solid #d4d4d4;top:-6px}.x-tip-default .x-tip-anchor-bottom{border-bottom-width:0;border-top:6px solid #d4d4d4;bottom:-6px}.x-tip-default .x-tip-anchor-left{border-left-width:0;border-right:6px solid #d4d4d4;left:-6px}.x-tip-default .x-tip-anchor-right{border-right-width:0;border-left:6px solid #d4d4d4;right:-6px}.x-tip-default .x-tip-anchor-top:after{border-top-width:0;border-bottom:6px solid #ebf4fb;top:1px;margin-left:-6px}.x-tip-default .x-tip-anchor-bottom:after{border-bottom-width:0;border-top:6px solid #ebf4fb;bottom:1px;margin-left:-6px}.x-tip-default .x-tip-anchor-left:after{border-left-width:0;border-right:6px solid #ebf4fb;left:1px;margin-top:-6px}.x-tip-default .x-tip-anchor-right:after{border-right-width:0;border-left:6px solid #ebf4fb;right:1px;margin-top:-6px}.x-tip-form-invalid{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:2px 2px 2px 2px;border-width:1px;border-style:solid;background-color:#ebf4fb}.x-tip-form-invalid-mc{background-color:#ebf4fb}.x-nbr .x-tip-form-invalid{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-tip-form-invalid-frameInfo{font-family:th-3-3-3-3-1-1-1-1-2-2-2-2}.x-tip-form-invalid-tl{background-position:0 -6px}.x-tip-form-invalid-tr{background-position:right -9px}.x-tip-form-invalid-bl{background-position:0 -12px}.x-tip-form-invalid-br{background-position:right -15px}.x-tip-form-invalid-ml{background-position:0 top}.x-tip-form-invalid-mr{background-position:right top}.x-tip-form-invalid-tc{background-position:0 0}.x-tip-form-invalid-bc{background-position:0 -3px}.x-tip-form-invalid-tr,.x-tip-form-invalid-br,.x-tip-form-invalid-mr{padding-right:3px}.x-tip-form-invalid-tl,.x-tip-form-invalid-bl,.x-tip-form-invalid-ml{padding-left:3px}.x-tip-form-invalid-tc{height:3px}.x-tip-form-invalid-bc{height:3px}.x-tip-form-invalid-tl,.x-tip-form-invalid-bl,.x-tip-form-invalid-tr,.x-tip-form-invalid-br,.x-tip-form-invalid-tc,.x-tip-form-invalid-bc,.x-tip-form-invalid-ml,.x-tip-form-invalid-mr{background-image:url(images/tip/tip-form-invalid-corners.gif)}.x-tip-form-invalid-ml,.x-tip-form-invalid-mr{background-image:url(images/tip/tip-form-invalid-sides.gif);background-repeat:repeat-y}.x-tip-form-invalid-mc{padding:0px 0px 0px 0px}.x-tip-form-invalid{background-color:#ebf4fb;border-color:#e1e1e1}.x-tip-form-invalid .x-tool-img{background-image:url(images/tools/tool-sprites-dark.png);background-color:#ebf4fb}.x-tip-header-form-invalid .x-tool-after-title{margin:0 0 0 6px}.x-tip-header-form-invalid .x-tool-before-title{margin:0 6px 0 0}.x-tip-header-form-invalid{padding:3px 3px 0 3px}.x-tip-header-title-form-invalid{color:#000;font-size:13px;font-weight:bold}.x-tip-body-form-invalid{padding:3px 3px 3px 22px;color:#000;font-size:13px;font-weight:normal}.x-tip-body-form-invalid a{color:#000}.x-tip-form-invalid .x-tip-anchor{border:6px solid transparent;_border-color:pink;_filter:chroma(color=pink)}.x-tip-form-invalid .x-tip-anchor:after{position:absolute;border:6px solid transparent;content:"";_border-color:pink;_filter:chroma(color=pink)}.x-tip-form-invalid .x-tip-anchor-top{border-top-width:0;border-bottom:6px solid #d4d4d4;top:-6px}.x-tip-form-invalid .x-tip-anchor-bottom{border-bottom-width:0;border-top:6px solid #d4d4d4;bottom:-6px}.x-tip-form-invalid .x-tip-anchor-left{border-left-width:0;border-right:6px solid #d4d4d4;left:-6px}.x-tip-form-invalid .x-tip-anchor-right{border-right-width:0;border-left:6px solid #d4d4d4;right:-6px}.x-tip-form-invalid .x-tip-anchor-top:after{border-top-width:0;border-bottom:6px solid #ebf4fb;top:1px;margin-left:-6px}.x-tip-form-invalid .x-tip-anchor-bottom:after{border-bottom-width:0;border-top:6px solid #ebf4fb;bottom:1px;margin-left:-6px}.x-tip-form-invalid .x-tip-anchor-left:after{border-left-width:0;border-right:6px solid #ebf4fb;left:1px;margin-top:-6px}.x-tip-form-invalid .x-tip-anchor-right:after{border-right-width:0;border-left:6px solid #ebf4fb;right:1px;margin-top:-6px}.x-tip-body-form-invalid{background:1px 1px no-repeat;background-image:url(images/form/exclamation.png)}.x-tip-body-form-invalid li{margin-bottom:4px}.x-tip-body-form-invalid li.last{margin-bottom:0}.x-color-picker{width:192px;height:120px;background-color:#fff;border-color:#fff;border-width:0;border-style:solid}.x-color-picker-item{width:24px;height:24px;border-width:1px;border-color:#fff;border-style:solid;background-color:#fff;cursor:pointer;padding:2px}a.x-color-picker-item:hover{border-color:#8bb8f3;background-color:#e6e6e6}.x-color-picker-selected{border-color:#8bb8f3;background-color:#e6e6e6}.x-color-picker-item-inner{line-height:16px;border-color:#e1e1e1;border-width:1px;border-style:solid}.x-html-editor-tb .x-edit-bold,.x-menu-item div.x-edit-bold{background-position:0 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-italic,.x-menu-item div.x-edit-italic{background-position:-16px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-underline,.x-menu-item div.x-edit-underline{background-position:-32px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-forecolor,.x-menu-item div.x-edit-forecolor{background-position:-160px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-backcolor,.x-menu-item div.x-edit-backcolor{background-position:-176px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-justifyleft,.x-menu-item div.x-edit-justifyleft{background-position:-112px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-justifycenter,.x-menu-item div.x-edit-justifycenter{background-position:-128px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-justifyright,.x-menu-item div.x-edit-justifyright{background-position:-144px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-insertorderedlist,.x-menu-item div.x-edit-insertorderedlist{background-position:-80px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-insertunorderedlist,.x-menu-item div.x-edit-insertunorderedlist{background-position:-96px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-increasefontsize,.x-menu-item div.x-edit-increasefontsize{background-position:-48px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-decreasefontsize,.x-menu-item div.x-edit-decreasefontsize{background-position:-64px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-sourceedit,.x-menu-item div.x-edit-sourceedit{background-position:-192px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tb .x-edit-createlink,.x-menu-item div.x-edit-createlink{background-position:-208px 0;background-image:url(images/editor/tb-sprite.png)}.x-html-editor-tip .x-tip-bd .x-tip-bd-inner{padding:5px;padding-bottom:1px}.x-html-editor-tb .x-font-select{font-size:13px;font-family:inherit}.x-html-editor-wrap textarea{font:normal 13px tahoma, verdana, sans-serif;background-color:#fff;resize:none}.x-htmleditor-iframe{background-color:#fff}.x-form-text-default.x-tagfield{padding:2px 0 0 4px}.x-form-text-default .x-tagfield-input{margin:0 4px 2px 0}.x-form-text-default .x-tagfield-input-field{height:18px;line-height:18px}.x-form-text-default .x-tagfield-item{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;background-color:#e6e6e6;border:1px solid #e6e6e6;padding:0 19px 0 5px;margin:0 4px 2px 0;color:#000;line-height:16px}.x-form-text-default .x-tagfield-item:hover{background-color:#dadada;border-color:#dadada;color:#000}.x-form-text-default .x-tagfield-item.x-tagfield-item-selected{background-color:#3892d4;border-color:#3892d4;color:#fff}.x-form-text-default .x-tagfield-item-close{width:12px;height:12px;top:1px;right:1px;background-image:url(images/form/tag-field-item-close.png)}.x-form-text-default .x-tagfield-item-close:hover{background-position:-12px 0}.x-form-text-default .x-tagfield-item-close:active{background-position:-24px 0}.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close{background-position:0 -12px}.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close:hover{background-position:-12px -12px}.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close:active{background-position:-24px -12px}.x-grid-view,.x-tree-view{z-index:1}.x-theme-row-height-el{height:24px}.x-grid-body{background:#fff;border-width:1px;border-style:solid;border-color:#c2c2c2}.x-grid-empty{padding:10px;color:grey;background-color:#fff;font:normal 13px tahoma, verdana, sans-serif}.x-grid-item{color:#000;font:normal 13px/15px tahoma, verdana, sans-serif;background-color:#fff}.x-grid-item-alt{background-color:#fafafa}.x-grid-item-over{color:#000;background-color:#e2eff9}.x-grid-item-focused{outline:0}.x-grid-item-focused .x-grid-cell-inner{z-index:1}.x-keyboard-mode .x-grid-item-focused{color:#000}.x-keyboard-mode .x-grid-item-focused .x-grid-cell-inner:before{content:"";position:absolute;z-index:-1;top:0px;right:0px;bottom:0px;left:0px;pointer-events:none;border:1px solid #3d92cf}.x-grid-item-selected{color:#000;background-color:#c2ddf2}.x-grid-with-row-lines .x-grid-item{border-style:solid;border-width:1px 0 0;border-color:#ededed}.x-grid-with-row-lines .x-grid-item:first-child{border-top-color:#fff}.x-grid-with-row-lines .x-grid-item.x-grid-item-over{border-style:solid;border-color:#e2eff9}.x-grid-with-row-lines .x-grid-item-over + .x-grid-item{border-top-style:solid;border-top-color:#e2eff9}.x-grid-with-row-lines .x-grid-item.x-grid-item-selected{border-style:solid;border-color:#c2ddf2}.x-grid-with-row-lines .x-grid-item-selected + .x-grid-item{border-top-style:solid;border-top-color:#c2ddf2}.x-grid-with-row-lines .x-grid-item:last-child{border-bottom-width:1px}.x-ie8 .x-grid-with-row-lines .x-grid-item{border-width:1px 0;margin-top:-1px}.x-ie8 .x-grid-with-row-lines .x-grid-item:first-child{margin-top:0}.x-grid-cell-inner{position:relative;text-overflow:ellipsis;padding:5px 10px 4px}.x-grid-cell-special{border-color:#ededed;border-style:solid;border-right-width:1px}.x-grid-dirty-cell{background:url(images/grid/dirty.png) no-repeat 0 0}.x-grid-row .x-grid-cell-selected{color:#000;background-color:#c2ddf2}.x-grid-with-col-lines .x-grid-cell{border-style:solid;border-color:#ededed;border-width:0 1px 0 0}.x-grid-with-col-lines .x-grid-item-over .x-grid-cell{border-color:#e2eff9;border-style:solid}.x-grid-with-col-lines .x-grid-item-selected .x-grid-cell{border-color:#c2ddf2;border-style:solid}.x-grid-resize-marker{width:1px;background-color:#0f0f0f}.x-grid-drop-indicator{position:absolute;height:1px;line-height:0px;background-color:#77bc71;overflow:visible;pointer-events:none}.x-grid-drop-indicator .x-grid-drop-indicator-left{position:absolute;top:-8px;left:-12px;background-image:url(images/grid/dd-insert-arrow-right.png);height:16px;width:16px}.x-grid-drop-indicator .x-grid-drop-indicator-right{position:absolute;top:-8px;right:-11px;background-image:url(images/grid/dd-insert-arrow-left.png);height:16px;width:16px}.x-col-move-top,.x-col-move-bottom{width:9px;height:9px}.x-col-move-top{background-image:url(images/grid/col-move-top.png)}.x-col-move-bottom{background-image:url(images/grid/col-move-bottom.png)}.x-grid-header-ct{border:1px solid #c2c2c2;border-bottom-color:#f5f5f5;background-color:#f5f5f5}.x-accordion-item .x-grid-header-ct{border-width:0 0 1px !important}.x-grid-header-ct-hidden{border-top:0 !important;border-bottom:0 !important}.x-grid-body{border-top-color:#c2c2c2}.x-hmenu-sort-asc{background-image:url(images/grid/hmenu-asc.png)}.x-hmenu-sort-desc{background-image:url(images/grid/hmenu-desc.png)}.x-cols-icon{background-image:url(images/grid/columns.png)}.x-column-header{border-right:1px solid #c2c2c2;color:#666;font:bold 13px/15px tahoma, verdana, sans-serif;outline:0;background-color:#f5f5f5}.x-group-sub-header{background:transparent;border-top:1px solid #c2c2c2}.x-group-sub-header .x-column-header-inner{padding:6px 10px 7px 10px}.x-column-header-inner{padding:7px 10px}.x-column-header-inner-empty{text-overflow:clip}.x-keyboard-mode .x-column-header.x-column-header-focus{color:#666}.x-keyboard-mode .x-column-header.x-column-header-focus .x-column-header-inner:after{content:"";position:absolute;z-index:5;top:0px;right:0px;bottom:0px;left:0px;border:1px solid #4297d4;pointer-events:none}.x-keyboard-mode .x-column-header.x-column-header-focus.x-group-sub-header .x-column-header-inner:before{bottom:0px}.x-column-header-over{background-image:none;background-color:#eff6fb}.x-column-header-sort-ASC,.x-column-header-sort-DESC{background-image:none;background-color:#eff6fb}.x-column-header-open{background-color:#eff6fb}.x-column-header-open .x-column-header-trigger{background-color:#e0ebf3}.x-column-header-over .x-column-header-trigger,.x-column-header-open .x-column-header-trigger{width:18px;cursor:pointer;background:transparent url(images/grid/hd-pop.png) no-repeat center center}.x-column-header-align-right .x-column-header-text{margin-right:12px}.x-column-header-sort-ASC .x-column-header-text-inner,.x-column-header-sort-DESC .x-column-header-text-inner{padding-right:17px;background-position:right center}.x-column-header-sort-ASC .x-column-header-text-inner{background-image:url(images/grid/sort_asc.png)}.x-column-header-sort-DESC .x-column-header-text-inner{background-image:url(images/grid/sort_desc.png)}.x-no-header-borders .x-column-header{border:0 none}.x-no-header-borders .x-column-header .x-column-header-inner{padding-top:7px}.x-grid-cell-inner-action-col{padding:4px 4px 4px 4px}.x-action-col-cell .x-item-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=30)";opacity:0.3}.x-action-col-icon{color:#b0b0b0;font-size:16px;height:16px;width:16px;cursor:pointer}.x-column-header-checkbox .x-column-header-inner,.x-grid-checkcolumn-cell-inner{padding:5px 4px 4px 4px;text-overflow:clip}.x-column-header-checkbox{border-color:#f5f5f5}.x-column-header-checkbox .x-column-header-text{overflow:visible}.x-column-header-checkbox .x-column-header-checkbox:after,.x-grid-checkcolumn:after{content:" ";height:15px;width:15px;background-image:url(images/form/checkbox.png);display:inline-block}.x-item-disabled .x-column-header-checkbox .x-column-header-checkbox,.x-item-disabled .x-grid-checkcolumn{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=30)";opacity:0.3}.x-grid-hd-checker-on .x-column-header-checkbox:after,.x-grid-checkcolumn-checked:after{background-position:0 -15px}.x-grid-item-selected .x-selmodel-column .x-grid-checkcolumn:after{background-position:0 -15px}.x-gecko .x-selmodel-checkbox .x-grid-checkcolumn{pointer-events:none}.x-grid-cell-row-numberer{background-color:#f5f5f5}.x-grid-cell-inner-row-numberer{padding:5px 5px 4px 3px}.x-btn-grid-cell-small{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4)}.x-btn-grid-cell-small-mc{background-image:url(images/btn/btn-grid-cell-small-fbg.gif);background-position:0 top;background-color:#3892d4}.x-nbr .x-btn-grid-cell-small{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-grid-cell-small-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-grid-cell-small-tl{background-position:0 -6px}.x-btn-grid-cell-small-tr{background-position:right -9px}.x-btn-grid-cell-small-bl{background-position:0 -12px}.x-btn-grid-cell-small-br{background-position:right -15px}.x-btn-grid-cell-small-ml{background-position:0 top}.x-btn-grid-cell-small-mr{background-position:right top}.x-btn-grid-cell-small-tc{background-position:0 0}.x-btn-grid-cell-small-bc{background-position:0 -3px}.x-btn-grid-cell-small-tr,.x-btn-grid-cell-small-br,.x-btn-grid-cell-small-mr{padding-right:3px}.x-btn-grid-cell-small-tl,.x-btn-grid-cell-small-bl,.x-btn-grid-cell-small-ml{padding-left:3px}.x-btn-grid-cell-small-tc{height:3px}.x-btn-grid-cell-small-bc{height:3px}.x-btn-grid-cell-small-tl,.x-btn-grid-cell-small-bl,.x-btn-grid-cell-small-tr,.x-btn-grid-cell-small-br,.x-btn-grid-cell-small-tc,.x-btn-grid-cell-small-bc,.x-btn-grid-cell-small-ml,.x-btn-grid-cell-small-mr{background-image:url(images/btn/btn-grid-cell-small-corners.gif)}.x-btn-grid-cell-small-ml,.x-btn-grid-cell-small-mr{background-image:url(images/btn/btn-grid-cell-small-sides.gif)}.x-btn-grid-cell-small-mc{padding:1px 1px 1px 1px}.x-btn-grid-cell-small{border-color:#126daf}.x-btn-button-grid-cell-small{min-height:16px}.x-ie9m .x-btn-button-grid-cell-small{min-height:auto;height:16px}.x-btn-inner-grid-cell-small{font:bold 12px/16px tahoma, verdana, sans-serif;color:#fff;padding:0 5px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-grid-cell-small,.x-ie9 .x-btn-icon-left > .x-btn-inner-grid-cell-small{max-width:calc(100% - 16px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-grid-cell-small,.x-safari8m .x-btn-icon-left > .x-btn-inner-grid-cell-small{max-width:calc(100% - 15px)}.x-ie10p .x-btn-inner-grid-cell-small{max-width:none}.x-btn-icon-el-grid-cell-small{font-size:16px;height:16px;color:#fff;line-height:16px}.x-btn-icon-left > .x-btn-icon-el-grid-cell-small,.x-btn-icon-right > .x-btn-icon-el-grid-cell-small{width:16px}.x-btn-icon-top > .x-btn-icon-el-grid-cell-small,.x-btn-icon-bottom > .x-btn-icon-el-grid-cell-small{min-width:16px}.x-btn-icon-el-grid-cell-small.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-grid-cell-small.x-btn-glyph{color:#9cc9e9}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-grid-cell-small{margin-right:0px}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small{margin-left:0px}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-grid-cell-small{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-grid-cell-small{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-grid-cell-small{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small{margin-right:5px}.x-btn-arrow-bottom > .x-btn-button-grid-cell-small,.x-btn-split-bottom > .x-btn-button-grid-cell-small{padding-bottom:3px}.x-btn-wrap-grid-cell-small.x-btn-arrow-right:after{width:8px;background-image:url(images/button/grid-cell-small-arrow.png);padding-right:8px}.x-btn-wrap-grid-cell-small.x-btn-arrow-bottom:after{height:8px;background-image:url(images/button/grid-cell-small-arrow.png)}.x-btn-wrap-grid-cell-small.x-btn-split-right:after{width:14px;background-image:url(images/button/grid-cell-small-s-arrow.png);padding-right:14px}.x-btn-wrap-grid-cell-small.x-btn-split-bottom:after{height:14px;background-image:url(images/button/grid-cell-small-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-grid-cell-small{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small{margin-right:5px}.x-keyboard-mode .x-btn-focus.x-btn-grid-cell-small{background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4)}.x-btn-grid-cell-small .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:17px;pointer-events:none}.x-btn-over.x-btn-grid-cell-small{border-color:#1164a1;background-image:none;background-color:#3487c3;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4893c9), color-stop(50%, #3487c3), color-stop(51%, #3180b9), color-stop(0%, #3487c3));background-image:-webkit-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-moz-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-o-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:-ms-linear-gradient(top, #4893c9, #3487c3 50%, #3180b9 51%, #3487c3);background-image:linear-gradient(top,#4893c9, #3487c3 50%, #3180b9 51%, #3487c3)}.x-btn.x-btn-menu-active.x-btn-grid-cell-small,.x-btn.x-btn-pressed.x-btn-grid-cell-small{border-color:#0e5284;background-image:none;background-color:#2a6e9f;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #2a6e9f), color-stop(50%, #286897), color-stop(51%, #2a6e9f), color-stop(0%, #3f7ca8));background-image:-webkit-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-moz-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-o-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:-ms-linear-gradient(top, #2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8);background-image:linear-gradient(top,#2a6e9f, #286897 50%, #2a6e9f 51%, #3f7ca8)}.x-btn.x-btn-disabled.x-btn-grid-cell-small{background-image:none;background-color:#3892d4;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #4c9dd8), color-stop(50%, #3892d4), color-stop(51%, #358bc9), color-stop(0%, #3892d4));background-image:-webkit-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-moz-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-o-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:-ms-linear-gradient(top, #4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4);background-image:linear-gradient(top,#4c9dd8, #3892d4 50%, #358bc9 51%, #3892d4)}.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tl,.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-bl,.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tr,.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-br,.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tc,.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-bc{background-image:url(images/btn/btn-grid-cell-small-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-ml,.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-mr{background-image:url(images/btn/btn-grid-cell-small-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-mc{background-color:#3892d4;background-image:url(images/btn/btn-grid-cell-small-focus-fbg.gif)}.x-btn-over .x-btn-grid-cell-small-tl,.x-btn-over .x-btn-grid-cell-small-bl,.x-btn-over .x-btn-grid-cell-small-tr,.x-btn-over .x-btn-grid-cell-small-br,.x-btn-over .x-btn-grid-cell-small-tc,.x-btn-over .x-btn-grid-cell-small-bc{background-image:url(images/btn/btn-grid-cell-small-over-corners.gif)}.x-btn-over .x-btn-grid-cell-small-ml,.x-btn-over .x-btn-grid-cell-small-mr{background-image:url(images/btn/btn-grid-cell-small-over-sides.gif)}.x-btn-over .x-btn-grid-cell-small-mc{background-color:#3487c3;background-image:url(images/btn/btn-grid-cell-small-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-bc{background-image:url(images/btn/btn-grid-cell-small-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-mr{background-image:url(images/btn/btn-grid-cell-small-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-mc{background-color:#3487c3;background-image:url(images/btn/btn-grid-cell-small-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tl,.x-btn.x-btn-menu-active .x-btn-grid-cell-small-bl,.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tr,.x-btn.x-btn-menu-active .x-btn-grid-cell-small-br,.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tc,.x-btn.x-btn-menu-active .x-btn-grid-cell-small-bc,.x-btn.x-btn-pressed .x-btn-grid-cell-small-tl,.x-btn.x-btn-pressed .x-btn-grid-cell-small-bl,.x-btn.x-btn-pressed .x-btn-grid-cell-small-tr,.x-btn.x-btn-pressed .x-btn-grid-cell-small-br,.x-btn.x-btn-pressed .x-btn-grid-cell-small-tc,.x-btn.x-btn-pressed .x-btn-grid-cell-small-bc{background-image:url(images/btn/btn-grid-cell-small-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-grid-cell-small-ml,.x-btn.x-btn-menu-active .x-btn-grid-cell-small-mr,.x-btn.x-btn-pressed .x-btn-grid-cell-small-ml,.x-btn.x-btn-pressed .x-btn-grid-cell-small-mr{background-image:url(images/btn/btn-grid-cell-small-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-grid-cell-small-mc,.x-btn.x-btn-pressed .x-btn-grid-cell-small-mc{background-color:#2a6e9f;background-image:url(images/btn/btn-grid-cell-small-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-bc{background-image:url(images/btn/btn-grid-cell-small-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-mr{background-image:url(images/btn/btn-grid-cell-small-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-mc{background-color:#2a6e9f;background-image:url(images/btn/btn-grid-cell-small-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-grid-cell-small-tl,.x-btn.x-btn-disabled .x-btn-grid-cell-small-bl,.x-btn.x-btn-disabled .x-btn-grid-cell-small-tr,.x-btn.x-btn-disabled .x-btn-grid-cell-small-br,.x-btn.x-btn-disabled .x-btn-grid-cell-small-tc,.x-btn.x-btn-disabled .x-btn-grid-cell-small-bc{background-image:url(images/btn/btn-grid-cell-small-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-grid-cell-small-ml,.x-btn.x-btn-disabled .x-btn-grid-cell-small-mr{background-image:url(images/btn/btn-grid-cell-small-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-grid-cell-small-mc{background-color:#3892d4;background-image:url(images/btn/btn-grid-cell-small-disabled-fbg.gif)}.x-nbr .x-btn-grid-cell-small{background-image:none}.x-btn-disabled.x-btn-grid-cell-small{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first .x-btn-grid-cell-small-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-middle .x-btn-grid-cell-small-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-last .x-btn-grid-cell-small-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first .x-btn-grid-cell-small-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-middle .x-btn-grid-cell-small-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-last .x-btn-grid-cell-small-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-grid-cell-small:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-last:after{bottom:1px}.x-button-grid-cell-small-cell > .x-grid-cell-inner{padding-top:0px;padding-bottom:0px}.x-button-grid-cell-small-cell > .x-grid-cell-inner >.x-btn-grid-cell-small{vertical-align:top}.x-grid-widgetcolumn-cell-inner{text-overflow:clip}.x-grid-group-hd{border-width:0 0 1px 0;border-style:solid;border-color:#c2c2c2;padding:7px 4px;background:#f5f5f5;cursor:pointer}.x-grid-group-hd-not-collapsible{cursor:default}.x-grid-group-hd-collapsible .x-grid-group-title{padding:0 0 0 17px;background:url(images/grid/group-collapse.png) no-repeat left center}.x-grid-group-title{color:#666;font:bold 13px/15px tahoma, verdana, sans-serif}.x-grid-group-hd-collapsed .x-grid-group-title{background-image:url(images/grid/group-expand.png)}.x-group-by-icon{background-image:url(images/grid/group-by.png)}.x-grid-rowbody{font:normal 13px/15px tahoma, verdana, sans-serif;padding:5px 10px 5px 10px}.x-docked-summary{border-width:1px;border-color:#c2c2c2;border-style:solid;background:#fff!important}.x-docked-summary .x-grid-table{border:0 none}.x-grid-row-summary .x-grid-cell,.x-grid-row-summary .x-grid-rowwrap,.x-grid-row-summary .x-grid-cell-rowbody{border-color:#ededed;background-color:#fff !important;border-top:1px solid #ededed;font:normal 13px/15px tahoma, verdana, sans-serif}.x-docked-summary .x-grid-item,.x-docked-summary .x-grid-row-summary .x-grid-cell{border-bottom:0 none;border-top:0 none}.x-docked-summary > :first-child{background-color:#fff}.x-grid-row-summary .x-grid-cell-inner-row-expander{display:none}.x-menu-default{border-style:solid;border-width:1px;border-color:#e1e1e1}.x-menu-body-default{background:#fff;padding:0}.x-menu-icon-separator-default{left:26px;border-left:solid 1px #e1e1e1;background-color:#fff;width:1px}.x-menu-item-default{border-width:0;cursor:pointer}.x-menu-item-default.x-menu-item-focus,.x-menu-item-default.x-menu-item-active{background-image:none;background-color:#d6e9f6}.x-nlg .x-menu-item-default.x-menu-item-focus,.x-nlg .x-menu-item-default.x-menu-item-active{background:#d6e9f6 repeat-x left top;background-image:url(images/menu/menu-item-default-active-bg.gif)}.x-menu-item-default.x-menu-item-disabled{cursor:default}.x-menu-item-default.x-menu-item-disabled a{cursor:default}.x-menu-item-default.x-menu-item-separator{height:1px;border-top:solid 1px #e1e1e1;background-color:#fff;margin:2px 0;padding:0}.x-menu-item-default.x-menu-item-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-icon-ui{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-text-default{background-color:transparent}.x-menu-item-default .x-form-item-label{font-size:13px;color:#000}.x-menu-item-text-default,.x-menu-item-cmp-default{margin:0 5px 0 5px}.x-menu-item-text-default{font:normal 13px tahoma, verdana, sans-serif;line-height:23px;padding-top:1px;color:#000;cursor:pointer}.x-menu-item-text-default.x-menu-item-indent{margin-left:32px}.x-menu-item-text-default.x-menu-item-indent-no-separator{margin-left:26px}.x-menu-item-text-default.x-menu-item-indent-right-icon{margin-right:31px}.x-menu-item-text-default.x-menu-item-indent-right-arrow{margin-right:22px}.x-menu-item-disabled .x-menu-item-text-default{cursor:default}.x-menu-item-indent-default{margin-left:32px}.x-menu-item-icon-default{width:16px;height:16px;top:4px;left:5px;line-height:16px;font-size:16px;color:grey;background-position:center center}.x-menu-item-icon-default.x-menu-item-glyph{opacity:0.5}.x-ie8 .x-menu-item-icon-default.x-menu-item-glyph{color:silver}.x-menu-item-icon-default.x-menu-item-icon-right{width:16px;height:16px;top:4px;right:5px;left:auto;background-position:center center}.x-menu-item-checked .x-menu-item-icon-default.x-menu-item-checkbox{background-image:url(images/menu/default-checked.png)}.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-item-checkbox{background-image:url(images/menu/default-unchecked.png)}.x-menu-item-checked .x-menu-item-icon-default.x-menu-group-icon{background-image:url(images/menu/default-group-checked.png)}.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-group-icon{background-image:none}.x-menu-item-arrow-default{width:12px;height:9px;top:8px;right:0;background-image:url(images/menu/default-menu-parent.png)}.x-menu-item-focus .x-menu-item-arrow-default,.x-menu-item-active .x-menu-item-arrow-default{top:8px;right:0}.x-menu-default-scroller .x-box-scroller-body-horizontal{margin-left:16px}.x-menu-default-vertical-scroller .x-box-scroller-body-vertical{margin-top:24px}.x-box-scroller-menu-default{cursor:pointer;color:#e1e1e1;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-box-scroller-menu-default.x-box-scroller-hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-box-scroller-menu-default.x-box-scroller-pressed{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=70)";opacity:0.7}.x-box-scroller-menu-default.x-box-scroller-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=25)";opacity:0.25;cursor:default}.x-box-scroller-menu-default.x-box-scroller-top,.x-box-scroller-menu-default.x-box-scroller-bottom{height:16px;width:16px;left:50%;margin-left:-8px}.x-box-scroller-menu-default.x-box-scroller-top{margin-top:4px;margin-right:0;margin-bottom:4px;background-image:url(images/menu/default-scroll-top.png)}.x-box-scroller-menu-default.x-box-scroller-bottom{margin-top:4px;margin-right:0;margin-bottom:4px;background-image:url(images/menu/default-scroll-bottom.png)}.x-ie8 .x-box-scroller-menu-default{background-color:#fff}.x-menu-default-menubar{border-style:solid;border-width:1px;border-color:#e1e1e1}.x-menu-body-default-menubar{background:#fff;padding:0}.x-menu-icon-separator-default-menubar{left:26px;border-left:solid 1px #e1e1e1;background-color:#fff;width:1px}.x-menu-item-default-menubar{border-width:0;cursor:pointer}.x-menu-item-default-menubar.x-menu-item-focus,.x-menu-item-default-menubar.x-menu-item-active{background-image:none;background-color:#d6e9f6}.x-nlg .x-menu-item-default-menubar.x-menu-item-focus,.x-nlg .x-menu-item-default-menubar.x-menu-item-active{background:#d6e9f6 repeat-x left top;background-image:url(images/menu/menu-item-default-menubar-active-bg.gif)}.x-menu-item-default-menubar.x-menu-item-disabled{cursor:default}.x-menu-item-default-menubar.x-menu-item-disabled a{cursor:default}.x-menu-item-default-menubar.x-menu-item-separator{height:1px;border-top:solid 1px #e1e1e1;background-color:#fff;margin:2px 0;padding:0}.x-menu-item-default-menubar.x-menu-item-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-ie9m .x-menu-item-default-menubar.x-menu-item-disabled .x-menu-item-icon-ui{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-ie9m .x-menu-item-default-menubar.x-menu-item-disabled .x-menu-item-text-default-menubar{background-color:transparent}.x-menu-item-default-menubar .x-form-item-label{font-size:13px;color:#000}.x-menu-item-text-default-menubar,.x-menu-item-cmp-default-menubar{margin:0 5px 0 5px}.x-menu-item-text-default-menubar{font:normal 13px tahoma, verdana, sans-serif;line-height:23px;padding-top:1px;color:#000;cursor:pointer}.x-menu-item-text-default-menubar.x-menu-item-indent{margin-left:32px}.x-menu-item-text-default-menubar.x-menu-item-indent-no-separator{margin-left:26px}.x-menu-item-text-default-menubar.x-menu-item-indent-right-icon{margin-right:31px}.x-menu-item-text-default-menubar.x-menu-item-indent-right-arrow{margin-right:24px}.x-menu-item-disabled .x-menu-item-text-default-menubar{cursor:default}.x-menu-item-indent-default-menubar{margin-left:32px}.x-menu-item-icon-default-menubar{width:16px;height:16px;top:4px;left:5px;line-height:16px;font-size:16px;color:grey;background-position:center center}.x-menu-item-icon-default-menubar.x-menu-item-glyph{opacity:0.5}.x-ie8 .x-menu-item-icon-default-menubar.x-menu-item-glyph{color:silver}.x-menu-item-icon-default-menubar.x-menu-item-icon-right{width:16px;height:16px;top:4px;right:5px;left:auto;background-position:center center}.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-item-checkbox{background-image:url(images/menu/default-menubar-checked.png)}.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-item-checkbox{background-image:url(images/menu/default-menubar-unchecked.png)}.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-group-icon{background-image:url(images/menu/default-menubar-group-checked.png)}.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-group-icon{background-image:none}.x-menu-item-arrow-default-menubar{width:9px;height:6px;top:10px;right:5px;background-image:url(images/menu/default-menubar-menu-parent.png)}.x-menu-item-focus .x-menu-item-arrow-default-menubar,.x-menu-item-active .x-menu-item-arrow-default-menubar{top:10px;right:5px}.x-menu-default-menubar-scroller .x-box-scroller-body-horizontal{margin-left:16px}.x-menu-default-menubar-vertical-scroller .x-box-scroller-body-vertical{margin-top:24px}.x-box-scroller-menu-default-menubar{cursor:pointer;color:#e1e1e1;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-box-scroller-menu-default-menubar.x-box-scroller-hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-box-scroller-menu-default-menubar.x-box-scroller-pressed{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=70)";opacity:0.7}.x-box-scroller-menu-default-menubar.x-box-scroller-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=25)";opacity:0.25;cursor:default}.x-box-scroller-menu-default-menubar.x-box-scroller-top,.x-box-scroller-menu-default-menubar.x-box-scroller-bottom{height:16px;width:16px;left:50%;margin-left:-8px}.x-box-scroller-menu-default-menubar.x-box-scroller-top{margin-top:4px;margin-right:0;margin-bottom:4px;background-image:url(images/menu/default-menubar-scroll-top.png)}.x-box-scroller-menu-default-menubar.x-box-scroller-bottom{margin-top:4px;margin-right:0;margin-bottom:4px;background-image:url(images/menu/default-menubar-scroll-bottom.png)}.x-ie8 .x-box-scroller-menu-default-menubar{background-color:#fff}.x-grid-filters-filtered-column{font-style:italic;font-weight:bold;text-decoration:underline}.x-grid-filters-icon{background-repeat:no-repeat;background-position:center center;color:grey;text-align:center}.x-grid-filters-find{background-image:url(images/grid/filters/find.png)}.x-grid-filters-gt{background-image:url(images/grid/filters/greater_than.png)}.x-grid-filters-lt{background-image:url(images/grid/filters/less_than.png)}.x-grid-filters-eq{background-image:url(images/grid/filters/equals.png)}.x-grid-locked .x-grid-inner-locked{border-width:0 1px 0 0;border-style:solid}.x-grid-locked-split .x-grid-inner-normal{border-width:0 0 0 1px;border-style:solid;border-left-color:#157fcc}.x-grid-locking-body{border-width:1px}.x-grid-locking-body > .x-splitter{background-color:#3892d4}.x-grid-locking-body > .x-splitter-active{background-color:#b4b4b4}.x-grid-inner-locked{border-right-color:#157fcc}.x-grid-inner-locked .x-column-header-last,.x-grid-inner-locked .x-grid-cell-last{border-right-width:0!important}.x-hmenu-lock{background-image:url(images/grid/hmenu-lock.png)}.x-hmenu-unlock{background-image:url(images/grid/hmenu-unlock.png)}.x-grid-scrollbar-clipper > .x-grid-view,.x-grid-scrollbar-clipper > .x-tree-view{background-color:#fff}.x-grid-scrollbar-clipper-locked,.x-grid-scrollbar-locked{border-width:0 1px 0 0;border-style:solid;border-color:#157fcc}.x-grid-scroll-container{background-color:#fff}.x-grid-editor .x-form-display-field{text-overflow:ellipsis}.x-grid-editor .x-form-action-col-field{padding:4px 4px 4px 4px}.x-grid-editor .x-form-text{padding-left:9px;padding-right:9px}.x-tree-cell-editor .x-form-text{padding-left:3px;padding-right:3px}.x-grid-row-editor .x-field{margin:0 3px 0 2px}.x-grid-row-editor .x-form-display-field{padding:5px 8px 4px 8px;line-height:15px}.x-ie9m .x-grid-row-editor .x-form-display-field{min-height:15px}.x-grid-row-editor .x-form-action-col-field{padding:4px 1px 4px 2px}.x-grid-row-editor .x-form-text{padding:3px 6px 2px 7px}.x-gecko .x-grid-row-editor .x-form-text{padding-left:6px;padding-right:5px}.x-grid-row-editor .x-panel-body{border-top:1px solid #e1e1e1 !important;border-bottom:1px solid #e1e1e1 !important;padding:5px 0 5px 0;background-color:#e0ebf3}.x-grid-with-col-lines .x-grid-row-editor .x-form-cb{margin-right:1px}.x-grid-row-editor-buttons-default-bottom{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:5px;-webkit-border-bottom-right-radius:5px;border-bottom-right-radius:5px;-moz-border-radius-bottomleft:5px;-webkit-border-bottom-left-radius:5px;border-bottom-left-radius:5px;padding:5px 5px 5px 5px;border-width:0 1px 1px 1px;border-style:solid;background-color:#e0ebf3}.x-grid-row-editor-buttons-default-bottom-mc{background-color:#e0ebf3}.x-nbr .x-grid-row-editor-buttons-default-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-grid-row-editor-buttons-default-bottom-frameInfo{font-family:th-0-5-5-5-0-1-1-1-5-5-5-5}.x-grid-row-editor-buttons-default-bottom-tl{background-position:0 -10px}.x-grid-row-editor-buttons-default-bottom-tr{background-position:right -15px}.x-grid-row-editor-buttons-default-bottom-bl{background-position:0 -20px}.x-grid-row-editor-buttons-default-bottom-br{background-position:right -25px}.x-grid-row-editor-buttons-default-bottom-ml{background-position:0 top}.x-grid-row-editor-buttons-default-bottom-mr{background-position:right top}.x-grid-row-editor-buttons-default-bottom-tc{background-position:0 0}.x-grid-row-editor-buttons-default-bottom-bc{background-position:0 -5px}.x-grid-row-editor-buttons-default-bottom-tr,.x-grid-row-editor-buttons-default-bottom-br,.x-grid-row-editor-buttons-default-bottom-mr{padding-right:5px}.x-grid-row-editor-buttons-default-bottom-tl,.x-grid-row-editor-buttons-default-bottom-bl,.x-grid-row-editor-buttons-default-bottom-ml{padding-left:5px}.x-grid-row-editor-buttons-default-bottom-tc{height:0}.x-grid-row-editor-buttons-default-bottom-bc{height:5px}.x-grid-row-editor-buttons-default-bottom-tl,.x-grid-row-editor-buttons-default-bottom-bl,.x-grid-row-editor-buttons-default-bottom-tr,.x-grid-row-editor-buttons-default-bottom-br,.x-grid-row-editor-buttons-default-bottom-tc,.x-grid-row-editor-buttons-default-bottom-bc,.x-grid-row-editor-buttons-default-bottom-ml,.x-grid-row-editor-buttons-default-bottom-mr{background-image:url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif)}.x-grid-row-editor-buttons-default-bottom-ml,.x-grid-row-editor-buttons-default-bottom-mr{background-image:url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif);background-repeat:repeat-y}.x-grid-row-editor-buttons-default-bottom-mc{padding:5px 1px 1px 1px}.x-grid-row-editor-buttons-default-top{-moz-border-radius-topleft:5px;-webkit-border-top-left-radius:5px;border-top-left-radius:5px;-moz-border-radius-topright:5px;-webkit-border-top-right-radius:5px;border-top-right-radius:5px;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:5px 5px 5px 5px;border-width:1px 1px 0 1px;border-style:solid;background-color:#e0ebf3}.x-grid-row-editor-buttons-default-top-mc{background-color:#e0ebf3}.x-nbr .x-grid-row-editor-buttons-default-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-grid-row-editor-buttons-default-top-frameInfo{font-family:th-5-5-0-5-1-1-0-1-5-5-5-5}.x-grid-row-editor-buttons-default-top-tl{background-position:0 -10px}.x-grid-row-editor-buttons-default-top-tr{background-position:right -15px}.x-grid-row-editor-buttons-default-top-bl{background-position:0 -20px}.x-grid-row-editor-buttons-default-top-br{background-position:right -25px}.x-grid-row-editor-buttons-default-top-ml{background-position:0 top}.x-grid-row-editor-buttons-default-top-mr{background-position:right top}.x-grid-row-editor-buttons-default-top-tc{background-position:0 0}.x-grid-row-editor-buttons-default-top-bc{background-position:0 -5px}.x-grid-row-editor-buttons-default-top-tr,.x-grid-row-editor-buttons-default-top-br,.x-grid-row-editor-buttons-default-top-mr{padding-right:5px}.x-grid-row-editor-buttons-default-top-tl,.x-grid-row-editor-buttons-default-top-bl,.x-grid-row-editor-buttons-default-top-ml{padding-left:5px}.x-grid-row-editor-buttons-default-top-tc{height:5px}.x-grid-row-editor-buttons-default-top-bc{height:0}.x-grid-row-editor-buttons-default-top-tl,.x-grid-row-editor-buttons-default-top-bl,.x-grid-row-editor-buttons-default-top-tr,.x-grid-row-editor-buttons-default-top-br,.x-grid-row-editor-buttons-default-top-tc,.x-grid-row-editor-buttons-default-top-bc,.x-grid-row-editor-buttons-default-top-ml,.x-grid-row-editor-buttons-default-top-mr{background-image:url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif)}.x-grid-row-editor-buttons-default-top-ml,.x-grid-row-editor-buttons-default-top-mr{background-image:url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif);background-repeat:repeat-y}.x-grid-row-editor-buttons-default-top-mc{padding:1px 1px 5px 1px}.x-grid-row-editor-buttons{border-color:#e1e1e1}.x-row-editor-update-button{margin-right:3px}.x-row-editor-cancel-button{margin-left:2px}.x-grid-row-editor-errors .x-tip-body{padding:5px}.x-grid-row-editor-errors-item{list-style:disc;margin-left:15px}.x-grid-cell-inner-row-expander{padding:7px 6px 6px 6px}.x-grid-row-expander{width:11px;height:11px;cursor:pointer;background-image:url(images/grid/group-collapse.png)}.x-grid-row-collapsed .x-grid-row-expander{background-image:url(images/grid/group-expand.png)}.x-ssm-row-numberer-hd{cursor:se-resize!important}.x-ssm-row-numberer-cell{cursor:e-resize}.x-ssm-column-select .x-column-header{cursor:s-resize}.x-ssm-extender-drag-handle{height:7px;width:7px;background-color:#157fcc}.x-ssm-extender-mask{border:1px dotted #157fcc}.x-accordion-layout-ct{background-color:#fff;padding:5px 5px 0}.x-accordion-hd .x-panel-header-title{color:#666;font-weight:bold;font-family: tahoma, verdana, sans-serif;text-transform:none}.x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus{outline:1px solid #157fcc;outline-offset:2px}.x-ie .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus,.x-ie10p .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus,.x-edge .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus{outline:none}.x-ie .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus:after,.x-ie10p .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus:after,.x-edge .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #157fcc;pointer-events:none}.x-accordion-item{margin:0 0 5px}.x-accordion-item .x-accordion-hd{background:#e0ebf3;border-width:0;border-color:#157fcc;padding:8px 10px}.x-accordion-item .x-accordion-hd-over{background-color:#e6f2fa}.x-accordion-item .x-accordion-hd-over .x-tool-tool-el{background-color:#e6f2fa}.x-accordion-item .x-accordion-hd-sibling-expanded{border-top-color:#157fcc;border-top-width:0}.x-accordion-item .x-accordion-hd-last-collapsed{border-bottom-color:#e0ebf3}.x-accordion-item .x-accordion-body{border-width:0}.x-accordion-hd .x-tool-tool-el{background-color:#e0ebf3;color:#666}.x-accordion-hd .x-tool-img{background-image:url(images/tools/tool-sprites-dark.png)}.x-accordion-hd .x-tool-collapse-top,.x-accordion-hd .x-tool-collapse-bottom{background-position:0 -272px}.x-accordion-hd .x-tool-expand-top,.x-accordion-hd .x-tool-expand-bottom{background-position:0 -256px}.x-keyboard-mode .x-accordion-hd .x-tool-focus{outline:1px solid #157fcc;outline-offset:2px}.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus,.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus,.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus{outline:none}.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus:after,.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus:after,.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #157fcc;pointer-events:none}body.x-border-layout-ct,div.x-border-layout-ct{background-color:#3892d4}.x-form-layout-wrap{border-spacing:5px}.x-resizable-handle{position:absolute;z-index:100;font-size:1px;line-height:5px;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0;background-color:#c2c2c2;-webkit-border-radius:5px;-moz-border-radius:5px;-ms-border-radius:5px;-o-border-radius:5px;border-radius:5px}.x-collapsed .x-resizable-handle{display:none}.x-resizable-handle-southeast{cursor:se-resize}.x-resizable-handle-northwest{cursor:nw-resize}.x-resizable-handle-northeast{cursor:ne-resize}.x-resizable-handle-southwest{cursor:sw-resize}.x-resizable-handle-east{cursor:e-resize;width:5px;right:0;top:0;bottom:0}.x-resizable-handle-south{cursor:s-resize;height:5px;left:0;right:0;bottom:0}.x-resizable-handle-west{cursor:w-resize;width:5px;left:0;top:0;bottom:0}.x-resizable-handle-north{cursor:n-resize;height:5px;left:0;right:0;top:0}.x-resizable-handle-southeast{width:5px;height:5px;right:0;bottom:0;z-index:101}.x-resizable-handle-northwest{width:5px;height:5px;left:0;top:0;z-index:101}.x-resizable-handle-northeast{width:5px;height:5px;right:0;top:0;z-index:101}.x-resizable-handle-southwest{width:5px;height:5px;left:0;bottom:0;z-index:101}.x-tablet .x-resizable-handle-north,.x-tablet .x-resizable-handle-south{height:10px}.x-tablet .x-resizable-handle-east,.x-tablet .x-resizable-handle-west{width:10px}.x-tablet .x-resizable-handle-northwest,.x-tablet .x-resizable-handle-northeast,.x-tablet .x-resizable-handle-southwest,.x-tablet .x-resizable-handle-southeast{width:10px;height:10px}.x-window .x-window-handle{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-window-collapsed .x-window-handle{display:none}.x-resizable-proxy{border:1px dashed #3b5a82;position:absolute;overflow:hidden;z-index:50000}.x-resizable-handle-over,.x-resizable-pinned .x-resizable-handle{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";opacity:1}.x-resizable-handle-east-over,.x-resizable-handle-west-over,.x-resizable-pinned > .x-resizable-handle-east,.x-resizable-pinned > .x-resizable-handle-west{background-image:url(images/sizer/e-handle.png)}.x-resizable-handle-south-over,.x-resizable-handle-north-over,.x-resizable-pinned > .x-resizable-handle-south,.x-resizable-pinned > .x-resizable-handle-north{background-image:url(images/sizer/s-handle.png)}.x-resizable-handle-southeast-over,.x-resizable-pinned > .x-resizable-handle-southeast{background-position:top left;background-image:url(images/sizer/se-handle.png)}.x-resizable-handle-northwest-over,.x-resizable-pinned > .x-resizable-handle-northwest{background-position:bottom right;background-image:url(images/sizer/nw-handle.png)}.x-resizable-handle-northeast-over,.x-resizable-pinned > .x-resizable-handle-northeast{background-position:bottom left;background-image:url(images/sizer/ne-handle.png)}.x-resizable-handle-southwest-over,.x-resizable-pinned > .x-resizable-handle-southwest{background-position:top right;background-image:url(images/sizer/sw-handle.png)}.x-slider-horz{padding-left:7px;background:no-repeat 0 -15px;margin:5px 0 4px}.x-slider-horz .x-slider-end{padding-right:8px;background:no-repeat right -30px}.x-slider-horz .x-slider-inner{height:15px}.x-slider-horz .x-slider-thumb{width:15px;height:15px;margin-left:-7px;background-image:url(images/slider/slider-thumb.png)}.x-keyboard-mode .x-slider-horz.x-slider-focus .x-slider-thumb{background-position:-45px -45px}.x-slider-horz .x-slider-thumb-over{background-position:-15px -15px}.x-keyboard-mode .x-slider-horz.x-slider-focus .x-slider-thumb-over{background-position:-60px -60px}.x-slider-horz .x-slider-thumb-drag{background-position:-30px -30px}.x-keyboard-mode .x-slider-horz.x-slider-focus .x-slider-thumb-drag{background-position:-75px -75px}.x-slider-ct-vert{height:100%}.x-slider-vert{padding-top:7px;background:no-repeat -30px 0;height:100%}.x-slider-vert > .x-slider-end{height:100%}.x-slider-vert > .x-slider-end > .x-slider-inner{height:100%}.x-slider-vert .x-slider-end{padding-bottom:8px;background:no-repeat -15px bottom;width:15px}.x-slider-vert .x-slider-inner{width:15px}.x-slider-vert .x-slider-thumb{width:15px;height:15px;margin-bottom:-8px;background-image:url(images/slider/slider-v-thumb.png)}.x-keyboard-mode .x-slider-vert.x-slider-focus .x-slider-thumb{background-position:-45px -45px}.x-slider-vert .x-slider-thumb-over{background-position:-15px -15px}.x-keyboard-mode .x-slider-vert.x-slider-focus .x-slider-thumb-over{background-position:-60px -60px}.x-slider-vert .x-slider-thumb-drag{background-position:-30px -30px}.x-keyboard-mode .x-slider-vert.x-slider-focus .x-slider-thumb-drag{background-position:-75px -75px}.x-slider-horz,.x-slider-horz .x-slider-end,.x-slider-horz .x-slider-inner{background-image:url(images/slider/slider-bg.png)}.x-slider-vert,.x-slider-vert .x-slider-end,.x-slider-vert .x-slider-inner{background-image:url(images/slider/slider-v-bg.png)}.x-slider-default-cell > .x-grid-cell-inner,.x-sliderwidget-default-cell > .x-grid-cell-inner{padding-top:0;padding-bottom:1px}.x-tab-default-top{-moz-border-radius-topleft:3px;-webkit-border-top-left-radius:3px;border-top-left-radius:3px;-moz-border-radius-topright:3px;-webkit-border-top-right-radius:3px;border-top-right-radius:3px;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:7px 12px 6px 12px;border-width:1px;border-style:solid;background-color:#4c9dd8}.x-tab-default-top-mc{background-color:#4c9dd8}.x-nbr .x-tab-default-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-tab-default-top-frameInfo{font-family:th-3-3-3-3-1-1-1-1-7-12-6-12}.x-tab-default-top-tl{background-position:0 -6px}.x-tab-default-top-tr{background-position:right -9px}.x-tab-default-top-bl{background-position:0 -12px}.x-tab-default-top-br{background-position:right -15px}.x-tab-default-top-ml{background-position:0 top}.x-tab-default-top-mr{background-position:right top}.x-tab-default-top-tc{background-position:0 0}.x-tab-default-top-bc{background-position:0 -3px}.x-tab-default-top-tr,.x-tab-default-top-br,.x-tab-default-top-mr{padding-right:3px}.x-tab-default-top-tl,.x-tab-default-top-bl,.x-tab-default-top-ml{padding-left:3px}.x-tab-default-top-tc{height:3px}.x-tab-default-top-bc{height:3px}.x-tab-default-top-tl,.x-tab-default-top-bl,.x-tab-default-top-tr,.x-tab-default-top-br,.x-tab-default-top-tc,.x-tab-default-top-bc,.x-tab-default-top-ml,.x-tab-default-top-mr{background-image:url(images/tab/tab-default-top-corners.gif)}.x-tab-default-top-ml,.x-tab-default-top-mr{background-image:url(images/tab/tab-default-top-sides.gif);background-repeat:repeat-y}.x-tab-default-top-mc{padding:5px 10px 4px 10px}.x-tab-default-bottom{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:3px;-webkit-border-bottom-right-radius:3px;border-bottom-right-radius:3px;-moz-border-radius-bottomleft:3px;-webkit-border-bottom-left-radius:3px;border-bottom-left-radius:3px;padding:6px 12px 7px 12px;border-width:1px 1px 1px 1px;border-style:solid;background-color:#4c9dd8}.x-tab-default-bottom-mc{background-color:#4c9dd8}.x-nbr .x-tab-default-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-tab-default-bottom-frameInfo{font-family:th-3-3-3-3-1-1-1-1-6-12-7-12}.x-tab-default-bottom-tl{background-position:0 -6px}.x-tab-default-bottom-tr{background-position:right -9px}.x-tab-default-bottom-bl{background-position:0 -12px}.x-tab-default-bottom-br{background-position:right -15px}.x-tab-default-bottom-ml{background-position:0 bottom}.x-tab-default-bottom-mr{background-position:right bottom}.x-tab-default-bottom-tc{background-position:0 0}.x-tab-default-bottom-bc{background-position:0 -3px}.x-tab-default-bottom-tr,.x-tab-default-bottom-br,.x-tab-default-bottom-mr{padding-right:3px}.x-tab-default-bottom-tl,.x-tab-default-bottom-bl,.x-tab-default-bottom-ml{padding-left:3px}.x-tab-default-bottom-tc{height:3px}.x-tab-default-bottom-bc{height:3px}.x-tab-default-bottom-tl,.x-tab-default-bottom-bl,.x-tab-default-bottom-tr,.x-tab-default-bottom-br,.x-tab-default-bottom-tc,.x-tab-default-bottom-bc,.x-tab-default-bottom-ml,.x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-corners.gif)}.x-tab-default-bottom-ml,.x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-sides.gif);background-repeat:repeat-y}.x-tab-default-bottom-mc{padding:4px 10px 5px 10px}.x-tab-default-left{-moz-border-radius-topleft:3px;-webkit-border-top-left-radius:3px;border-top-left-radius:3px;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:3px;-webkit-border-bottom-left-radius:3px;border-bottom-left-radius:3px;padding:7px 12px 6px 12px;border-width:1px 1px 1px 1px;border-style:solid;background-color:#4c9dd8}.x-tab-default-left-mc{background-color:#4c9dd8}.x-nbr .x-tab-default-left{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-tab-default-left-frameInfo{font-family:th-3-3-3-3-1-1-1-1-7-12-6-12}.x-tab-default-left-tl{background-position:0 -6px}.x-tab-default-left-tr{background-position:right -9px}.x-tab-default-left-bl{background-position:0 -12px}.x-tab-default-left-br{background-position:right -15px}.x-tab-default-left-ml{background-position:0 top}.x-tab-default-left-mr{background-position:right top}.x-tab-default-left-tc{background-position:0 0}.x-tab-default-left-bc{background-position:0 -3px}.x-tab-default-left-tr,.x-tab-default-left-br,.x-tab-default-left-mr{padding-right:3px}.x-tab-default-left-tl,.x-tab-default-left-bl,.x-tab-default-left-ml{padding-left:3px}.x-tab-default-left-tc{height:3px}.x-tab-default-left-bc{height:3px}.x-tab-default-left-tl,.x-tab-default-left-bl,.x-tab-default-left-tr,.x-tab-default-left-br,.x-tab-default-left-tc,.x-tab-default-left-bc,.x-tab-default-left-ml,.x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-corners.gif)}.x-tab-default-left-ml,.x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-sides.gif);background-repeat:repeat-y}.x-tab-default-left-mc{padding:5px 10px 4px 10px}.x-tab-default-right{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:3px;-webkit-border-top-right-radius:3px;border-top-right-radius:3px;-moz-border-radius-bottomright:3px;-webkit-border-bottom-right-radius:3px;border-bottom-right-radius:3px;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:7px 12px 6px 12px;border-width:1px 1px 1px 1px;border-style:solid;background-color:#4c9dd8}.x-tab-default-right-mc{background-color:#4c9dd8}.x-nbr .x-tab-default-right{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-tab-default-right-frameInfo{font-family:th-3-3-3-3-1-1-1-1-7-12-6-12}.x-tab-default-right-tl{background-position:0 -6px}.x-tab-default-right-tr{background-position:right -9px}.x-tab-default-right-bl{background-position:0 -12px}.x-tab-default-right-br{background-position:right -15px}.x-tab-default-right-ml{background-position:0 top}.x-tab-default-right-mr{background-position:right top}.x-tab-default-right-tc{background-position:0 0}.x-tab-default-right-bc{background-position:0 -3px}.x-tab-default-right-tr,.x-tab-default-right-br,.x-tab-default-right-mr{padding-right:3px}.x-tab-default-right-tl,.x-tab-default-right-bl,.x-tab-default-right-ml{padding-left:3px}.x-tab-default-right-tc{height:3px}.x-tab-default-right-bc{height:3px}.x-tab-default-right-tl,.x-tab-default-right-bl,.x-tab-default-right-tr,.x-tab-default-right-br,.x-tab-default-right-tc,.x-tab-default-right-bc,.x-tab-default-right-ml,.x-tab-default-right-mr{background-image:url(images/tab/tab-default-right-corners.gif)}.x-tab-default-right-ml,.x-tab-default-right-mr{background-image:url(images/tab/tab-default-right-sides.gif);background-repeat:repeat-y}.x-tab-default-right-mc{padding:5px 10px 4px 10px}.x-tab-default{border-color:#4c9dd8;cursor:pointer}.x-tab-default-top{margin:0 1px 0 0}.x-tab-default-top.x-tab-rotate-left{margin:0 0 0 1px}.x-keyboard-mode .x-tab-default-top.x-tab-focus{-webkit-box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset;-moz-box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset;box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset}.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-over{-webkit-box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset;-moz-box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset;box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset}.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-active{-webkit-box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset;-moz-box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset;box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset}.x-tab-default-right{margin:0 0 1px 0}.x-tab-default-right.x-tab-rotate-right{margin:1px 0 0 0}.x-keyboard-mode .x-tab-default-right.x-tab-focus{-webkit-box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset;-moz-box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset;box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset}.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-over{-webkit-box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset;-moz-box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset;box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset}.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-active{-webkit-box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset;-moz-box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset;box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset}.x-tab-default-bottom{margin:0 1px 0 0}.x-tab-default-bottom.x-tab-rotate-left{margin:0 0 0 1px}.x-keyboard-mode .x-tab-default-bottom.x-tab-focus{-webkit-box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset;-moz-box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset;box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset}.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-over{-webkit-box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset;-moz-box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset;box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset}.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-active{-webkit-box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset;-moz-box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset;box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset}.x-tab-default-left{margin:0 0 1px 0}.x-tab-default-left.x-tab-rotate-right{margin:1px 0 0 0}.x-keyboard-mode .x-tab-default-left.x-tab-focus{-webkit-box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset;-moz-box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset;box-shadow:#dbebf7 0 1px 0px 0 inset, #dbebf7 0 -1px 0px 0 inset, #dbebf7 -1px 0 0px 0 inset, #dbebf7 1px 0 0px 0 inset}.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-over{-webkit-box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset;-moz-box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset;box-shadow:#dfeef8 0 1px 0px 0 inset, #dfeef8 0 -1px 0px 0 inset, #dfeef8 -1px 0 0px 0 inset, #dfeef8 1px 0 0px 0 inset}.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-active{-webkit-box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset;-moz-box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset;box-shadow:#3390d3 0 1px 0px 0 inset, #3390d3 0 -1px 0px 0 inset, #3390d3 -1px 0 0px 0 inset, #3390d3 1px 0 0px 0 inset}.x-tab-button-default{height:16px}.x-tab-inner-default{font:bold 13px/16px tahoma, verdana, sans-serif;color:#fff;max-width:100%}.x-tab-icon-right > .x-tab-inner-default,.x-tab-icon-left > .x-tab-inner-default{max-width:calc(100% - 16px)}.x-tab-icon-el-default{min-height:16px;background-position:center center;font-size:16px;line-height:16px;color:#fff}.x-tab-icon-left > .x-tab-icon-el-default,.x-tab-icon-right > .x-tab-icon-el-default{width:16px}.x-tab-icon-top > .x-tab-icon-el-default,.x-tab-icon-bottom > .x-tab-icon-el-default{min-width:16px}.x-tab-icon-el-default.x-tab-glyph{opacity:0.5}.x-ie8 .x-tab-icon-el-default.x-tab-glyph{color:#a5ceeb}.x-tab-text.x-tab-icon-left > .x-tab-icon-el-default{margin-right:6px}.x-tab-text.x-tab-icon-right > .x-tab-icon-el-default{margin-left:6px}.x-tab-text.x-tab-icon-top > .x-tab-icon-el-default{margin-bottom:6px}.x-tab-text.x-tab-icon-bottom > .x-tab-icon-el-default{margin-top:6px}.x-keyboard-mode .x-tab-focus.x-tab-default{border-color:#4c9dd8;background-color:#4c9dd8}.x-tab-over.x-tab-default{border-color:#60a8dc;background-color:#60a8dc}.x-keyboard-mode .x-tab-focus.x-tab-over.x-tab-default{border-color:#60a8dc;background-color:#60a8dc}.x-tab.x-tab-active.x-tab-default{border-color:#add2ed;background-color:#add2ed}.x-tab.x-tab-active.x-tab-default .x-tab-inner-default{color:#157fcc}.x-tab.x-tab-active.x-tab-default .x-tab-icon-el{color:#157fcc}.x-ie8 .x-tab.x-tab-active.x-tab-default .x-tab-icon-el{color:#61a9dd}.x-keyboard-mode .x-tab-focus.x-tab-active.x-tab-default{border-color:#add2ed;background-color:#add2ed}.x-tab.x-tab-disabled.x-tab-default{border-color:#4c9dd8;background-color:#4c9dd8;cursor:default}.x-tab.x-tab-disabled.x-tab-default .x-tab-inner-default{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=30)";opacity:0.3}.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el-default{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el{color:#fff;opacity:0.3;filter:none}.x-ie8 .x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el{color:#82bae4}.x-nbr .x-tab-default{background-image:none}.x-tab-over .x-tab-default-top-tl,.x-tab-over .x-tab-default-top-bl,.x-tab-over .x-tab-default-top-tr,.x-tab-over .x-tab-default-top-br,.x-tab-over .x-tab-default-top-tc,.x-tab-over .x-tab-default-top-bc{background-image:url(images/tab/tab-default-top-over-corners.gif)}.x-tab-over .x-tab-default-top-ml,.x-tab-over .x-tab-default-top-mr{background-image:url(images/tab/tab-default-top-over-sides.gif)}.x-tab-over .x-tab-default-top-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-top-over-fbg.gif)}.x-tab-focus .x-tab-default-top-tl,.x-tab-focus .x-tab-default-top-bl,.x-tab-focus .x-tab-default-top-tr,.x-tab-focus .x-tab-default-top-br,.x-tab-focus .x-tab-default-top-tc,.x-tab-focus .x-tab-default-top-bc{background-image:url(images/tab/tab-default-top-focus-corners.gif)}.x-tab-focus .x-tab-default-top-ml,.x-tab-focus .x-tab-default-top-mr{background-image:url(images/tab/tab-default-top-focus-sides.gif)}.x-tab-focus .x-tab-default-top-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-top-focus-fbg.gif)}.x-tab-focus.x-tab-over .x-tab-default-top-tl,.x-tab-focus.x-tab-over .x-tab-default-top-bl,.x-tab-focus.x-tab-over .x-tab-default-top-tr,.x-tab-focus.x-tab-over .x-tab-default-top-br,.x-tab-focus.x-tab-over .x-tab-default-top-tc,.x-tab-focus.x-tab-over .x-tab-default-top-bc{background-image:url(images/tab/tab-default-top-focus-over-corners.gif)}.x-tab-focus.x-tab-over .x-tab-default-top-ml,.x-tab-focus.x-tab-over .x-tab-default-top-mr{background-image:url(images/tab/tab-default-top-focus-over-sides.gif)}.x-tab-focus.x-tab-over .x-tab-default-top-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-top-focus-over-fbg.gif)}.x-tab.x-tab-active .x-tab-default-top-tl,.x-tab.x-tab-active .x-tab-default-top-bl,.x-tab.x-tab-active .x-tab-default-top-tr,.x-tab.x-tab-active .x-tab-default-top-br,.x-tab.x-tab-active .x-tab-default-top-tc,.x-tab.x-tab-active .x-tab-default-top-bc{background-image:url(images/tab/tab-default-top-active-corners.gif)}.x-tab.x-tab-active .x-tab-default-top-ml,.x-tab.x-tab-active .x-tab-default-top-mr{background-image:url(images/tab/tab-default-top-active-sides.gif)}.x-tab.x-tab-active .x-tab-default-top-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-top-active-fbg.gif)}.x-tab-focus.x-tab-active .x-tab-default-top-tl,.x-tab-focus.x-tab-active .x-tab-default-top-bl,.x-tab-focus.x-tab-active .x-tab-default-top-tr,.x-tab-focus.x-tab-active .x-tab-default-top-br,.x-tab-focus.x-tab-active .x-tab-default-top-tc,.x-tab-focus.x-tab-active .x-tab-default-top-bc{background-image:url(images/tab/tab-default-top-focus-active-corners.gif)}.x-tab-focus.x-tab-active .x-tab-default-top-ml,.x-tab-focus.x-tab-active .x-tab-default-top-mr{background-image:url(images/tab/tab-default-top-focus-active-sides.gif)}.x-tab-focus.x-tab-active .x-tab-default-top-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-top-focus-active-fbg.gif)}.x-tab.x-tab-disabled .x-tab-default-top-tl,.x-tab.x-tab-disabled .x-tab-default-top-bl,.x-tab.x-tab-disabled .x-tab-default-top-tr,.x-tab.x-tab-disabled .x-tab-default-top-br,.x-tab.x-tab-disabled .x-tab-default-top-tc,.x-tab.x-tab-disabled .x-tab-default-top-bc{background-image:url(images/tab/tab-default-top-disabled-corners.gif)}.x-tab.x-tab-disabled .x-tab-default-top-ml,.x-tab.x-tab-disabled .x-tab-default-top-mr{background-image:url(images/tab/tab-default-top-disabled-sides.gif)}.x-tab.x-tab-disabled .x-tab-default-top-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-top-disabled-fbg.gif)}.x-tab-over .x-tab-default-right-tl,.x-tab-over .x-tab-default-right-bl,.x-tab-over .x-tab-default-right-tr,.x-tab-over .x-tab-default-right-br,.x-tab-over .x-tab-default-right-tc,.x-tab-over .x-tab-default-right-bc{background-image:url(images/tab/tab-default-right-over-corners.gif)}.x-tab-over .x-tab-default-right-ml,.x-tab-over .x-tab-default-right-mr{background-image:url(images/tab/tab-default-right-over-sides.gif)}.x-tab-over .x-tab-default-right-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-right-over-fbg.gif)}.x-tab-focus .x-tab-default-right-tl,.x-tab-focus .x-tab-default-right-bl,.x-tab-focus .x-tab-default-right-tr,.x-tab-focus .x-tab-default-right-br,.x-tab-focus .x-tab-default-right-tc,.x-tab-focus .x-tab-default-right-bc{background-image:url(images/tab/tab-default-right-focus-corners.gif)}.x-tab-focus .x-tab-default-right-ml,.x-tab-focus .x-tab-default-right-mr{background-image:url(images/tab/tab-default-right-focus-sides.gif)}.x-tab-focus .x-tab-default-right-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-right-focus-fbg.gif)}.x-tab-focus.x-tab-over .x-tab-default-right-tl,.x-tab-focus.x-tab-over .x-tab-default-right-bl,.x-tab-focus.x-tab-over .x-tab-default-right-tr,.x-tab-focus.x-tab-over .x-tab-default-right-br,.x-tab-focus.x-tab-over .x-tab-default-right-tc,.x-tab-focus.x-tab-over .x-tab-default-right-bc{background-image:url(images/tab/tab-default-right-focus-over-corners.gif)}.x-tab-focus.x-tab-over .x-tab-default-right-ml,.x-tab-focus.x-tab-over .x-tab-default-right-mr{background-image:url(images/tab/tab-default-right-focus-over-sides.gif)}.x-tab-focus.x-tab-over .x-tab-default-right-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-right-focus-over-fbg.gif)}.x-tab.x-tab-active .x-tab-default-right-tl,.x-tab.x-tab-active .x-tab-default-right-bl,.x-tab.x-tab-active .x-tab-default-right-tr,.x-tab.x-tab-active .x-tab-default-right-br,.x-tab.x-tab-active .x-tab-default-right-tc,.x-tab.x-tab-active .x-tab-default-right-bc{background-image:url(images/tab/tab-default-right-active-corners.gif)}.x-tab.x-tab-active .x-tab-default-right-ml,.x-tab.x-tab-active .x-tab-default-right-mr{background-image:url(images/tab/tab-default-right-active-sides.gif)}.x-tab.x-tab-active .x-tab-default-right-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-right-active-fbg.gif)}.x-tab-focus.x-tab-active .x-tab-default-right-tl,.x-tab-focus.x-tab-active .x-tab-default-right-bl,.x-tab-focus.x-tab-active .x-tab-default-right-tr,.x-tab-focus.x-tab-active .x-tab-default-right-br,.x-tab-focus.x-tab-active .x-tab-default-right-tc,.x-tab-focus.x-tab-active .x-tab-default-right-bc{background-image:url(images/tab/tab-default-right-focus-active-corners.gif)}.x-tab-focus.x-tab-active .x-tab-default-right-ml,.x-tab-focus.x-tab-active .x-tab-default-right-mr{background-image:url(images/tab/tab-default-right-focus-active-sides.gif)}.x-tab-focus.x-tab-active .x-tab-default-right-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-right-focus-active-fbg.gif)}.x-tab.x-tab-disabled .x-tab-default-right-tl,.x-tab.x-tab-disabled .x-tab-default-right-bl,.x-tab.x-tab-disabled .x-tab-default-right-tr,.x-tab.x-tab-disabled .x-tab-default-right-br,.x-tab.x-tab-disabled .x-tab-default-right-tc,.x-tab.x-tab-disabled .x-tab-default-right-bc{background-image:url(images/tab/tab-default-right-disabled-corners.gif)}.x-tab.x-tab-disabled .x-tab-default-right-ml,.x-tab.x-tab-disabled .x-tab-default-right-mr{background-image:url(images/tab/tab-default-right-disabled-sides.gif)}.x-tab.x-tab-disabled .x-tab-default-right-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-right-disabled-fbg.gif)}.x-tab-over .x-tab-default-bottom-tl,.x-tab-over .x-tab-default-bottom-bl,.x-tab-over .x-tab-default-bottom-tr,.x-tab-over .x-tab-default-bottom-br,.x-tab-over .x-tab-default-bottom-tc,.x-tab-over .x-tab-default-bottom-bc{background-image:url(images/tab/tab-default-bottom-over-corners.gif)}.x-tab-over .x-tab-default-bottom-ml,.x-tab-over .x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-over-sides.gif)}.x-tab-over .x-tab-default-bottom-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-bottom-over-fbg.gif)}.x-tab-focus .x-tab-default-bottom-tl,.x-tab-focus .x-tab-default-bottom-bl,.x-tab-focus .x-tab-default-bottom-tr,.x-tab-focus .x-tab-default-bottom-br,.x-tab-focus .x-tab-default-bottom-tc,.x-tab-focus .x-tab-default-bottom-bc{background-image:url(images/tab/tab-default-bottom-focus-corners.gif)}.x-tab-focus .x-tab-default-bottom-ml,.x-tab-focus .x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-focus-sides.gif)}.x-tab-focus .x-tab-default-bottom-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-bottom-focus-fbg.gif)}.x-tab-focus.x-tab-over .x-tab-default-bottom-tl,.x-tab-focus.x-tab-over .x-tab-default-bottom-bl,.x-tab-focus.x-tab-over .x-tab-default-bottom-tr,.x-tab-focus.x-tab-over .x-tab-default-bottom-br,.x-tab-focus.x-tab-over .x-tab-default-bottom-tc,.x-tab-focus.x-tab-over .x-tab-default-bottom-bc{background-image:url(images/tab/tab-default-bottom-focus-over-corners.gif)}.x-tab-focus.x-tab-over .x-tab-default-bottom-ml,.x-tab-focus.x-tab-over .x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-focus-over-sides.gif)}.x-tab-focus.x-tab-over .x-tab-default-bottom-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-bottom-focus-over-fbg.gif)}.x-tab.x-tab-active .x-tab-default-bottom-tl,.x-tab.x-tab-active .x-tab-default-bottom-bl,.x-tab.x-tab-active .x-tab-default-bottom-tr,.x-tab.x-tab-active .x-tab-default-bottom-br,.x-tab.x-tab-active .x-tab-default-bottom-tc,.x-tab.x-tab-active .x-tab-default-bottom-bc{background-image:url(images/tab/tab-default-bottom-active-corners.gif)}.x-tab.x-tab-active .x-tab-default-bottom-ml,.x-tab.x-tab-active .x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-active-sides.gif)}.x-tab.x-tab-active .x-tab-default-bottom-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-bottom-active-fbg.gif)}.x-tab-focus.x-tab-active .x-tab-default-bottom-tl,.x-tab-focus.x-tab-active .x-tab-default-bottom-bl,.x-tab-focus.x-tab-active .x-tab-default-bottom-tr,.x-tab-focus.x-tab-active .x-tab-default-bottom-br,.x-tab-focus.x-tab-active .x-tab-default-bottom-tc,.x-tab-focus.x-tab-active .x-tab-default-bottom-bc{background-image:url(images/tab/tab-default-bottom-focus-active-corners.gif)}.x-tab-focus.x-tab-active .x-tab-default-bottom-ml,.x-tab-focus.x-tab-active .x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-focus-active-sides.gif)}.x-tab-focus.x-tab-active .x-tab-default-bottom-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-bottom-focus-active-fbg.gif)}.x-tab.x-tab-disabled .x-tab-default-bottom-tl,.x-tab.x-tab-disabled .x-tab-default-bottom-bl,.x-tab.x-tab-disabled .x-tab-default-bottom-tr,.x-tab.x-tab-disabled .x-tab-default-bottom-br,.x-tab.x-tab-disabled .x-tab-default-bottom-tc,.x-tab.x-tab-disabled .x-tab-default-bottom-bc{background-image:url(images/tab/tab-default-bottom-disabled-corners.gif)}.x-tab.x-tab-disabled .x-tab-default-bottom-ml,.x-tab.x-tab-disabled .x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-disabled-sides.gif)}.x-tab.x-tab-disabled .x-tab-default-bottom-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-bottom-disabled-fbg.gif)}.x-tab-over .x-tab-default-left-tl,.x-tab-over .x-tab-default-left-bl,.x-tab-over .x-tab-default-left-tr,.x-tab-over .x-tab-default-left-br,.x-tab-over .x-tab-default-left-tc,.x-tab-over .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-over-corners.gif)}.x-tab-over .x-tab-default-left-ml,.x-tab-over .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-over-sides.gif)}.x-tab-over .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-over-fbg.gif)}.x-tab-focus .x-tab-default-left-tl,.x-tab-focus .x-tab-default-left-bl,.x-tab-focus .x-tab-default-left-tr,.x-tab-focus .x-tab-default-left-br,.x-tab-focus .x-tab-default-left-tc,.x-tab-focus .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-focus-corners.gif)}.x-tab-focus .x-tab-default-left-ml,.x-tab-focus .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-focus-sides.gif)}.x-tab-focus .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-focus-fbg.gif)}.x-tab-focus.x-tab-over .x-tab-default-left-tl,.x-tab-focus.x-tab-over .x-tab-default-left-bl,.x-tab-focus.x-tab-over .x-tab-default-left-tr,.x-tab-focus.x-tab-over .x-tab-default-left-br,.x-tab-focus.x-tab-over .x-tab-default-left-tc,.x-tab-focus.x-tab-over .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-focus-over-corners.gif)}.x-tab-focus.x-tab-over .x-tab-default-left-ml,.x-tab-focus.x-tab-over .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-focus-over-sides.gif)}.x-tab-focus.x-tab-over .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-focus-over-fbg.gif)}.x-tab.x-tab-active .x-tab-default-left-tl,.x-tab.x-tab-active .x-tab-default-left-bl,.x-tab.x-tab-active .x-tab-default-left-tr,.x-tab.x-tab-active .x-tab-default-left-br,.x-tab.x-tab-active .x-tab-default-left-tc,.x-tab.x-tab-active .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-active-corners.gif)}.x-tab.x-tab-active .x-tab-default-left-ml,.x-tab.x-tab-active .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-active-sides.gif)}.x-tab.x-tab-active .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-active-fbg.gif)}.x-tab-focus.x-tab-active .x-tab-default-left-tl,.x-tab-focus.x-tab-active .x-tab-default-left-bl,.x-tab-focus.x-tab-active .x-tab-default-left-tr,.x-tab-focus.x-tab-active .x-tab-default-left-br,.x-tab-focus.x-tab-active .x-tab-default-left-tc,.x-tab-focus.x-tab-active .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-focus-active-corners.gif)}.x-tab-focus.x-tab-active .x-tab-default-left-ml,.x-tab-focus.x-tab-active .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-focus-active-sides.gif)}.x-tab-focus.x-tab-active .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-focus-active-fbg.gif)}.x-tab.x-tab-disabled .x-tab-default-left-tl,.x-tab.x-tab-disabled .x-tab-default-left-bl,.x-tab.x-tab-disabled .x-tab-default-left-tr,.x-tab.x-tab-disabled .x-tab-default-left-br,.x-tab.x-tab-disabled .x-tab-default-left-tc,.x-tab.x-tab-disabled .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-disabled-corners.gif)}.x-tab.x-tab-disabled .x-tab-default-left-ml,.x-tab.x-tab-disabled .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-disabled-sides.gif)}.x-tab.x-tab-disabled .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-disabled-fbg.gif)}.x-tab-default-tl,.x-tab-default-bl,.x-tab-default-tr,.x-tab-default-br{-ms-filter:"progid:DXImageTransform.Microsoft.gradient(startColorstr=#00FFFFFF,endColorstr=#00FFFFFF)"}.x-tab-default .x-tab-close-btn{top:2px;right:2px;width:12px;height:12px;background:url(images/tab/tab-default-close.png) 0 0}.x-tab-default .x-tab-close-btn-over{background-position:-12px 0}.x-tab-default .x-tab-close-btn-pressed{background-position:-24px 0}.x-tab-default.x-tab-active .x-tab-close-btn{background-position:0 -12px}.x-tab-default.x-tab-active .x-tab-close-btn-over{background-position:-12px -12px}.x-tab-default.x-tab-active .x-tab-close-btn-pressed{background-position:-24px -12px}.x-tab-default.x-tab-disabled .x-tab-close-btn{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=30)";opacity:0.3;background-position:0 0}.x-tab-closable.x-tab-default .x-tab-button{padding-right:15px}.x-tab-bar-default{background-color:#157fcc}.x-tab-bar-default-top > .x-tab-bar-body-default{padding:0}.x-tab-bar-default-bottom > .x-tab-bar-body-default{padding:0 0 0 0}.x-tab-bar-default-left > .x-tab-bar-body-default{padding:0 0 0 0}.x-tab-bar-default-right > .x-tab-bar-body-default{padding:0 0 0 0}.x-tab-bar-plain.x-tab-bar-default-horizontal{border-top-color:transparent;border-bottom-color:transparent;border-left-width:0;border-right-width:0}.x-tab-bar-plain.x-tab-bar-default-vertical{border-right-color:transparent;border-left-color:transparent;border-top-width:0;border-bottom-width:0}.x-tab-bar-top > .x-tab-bar-body-default{padding-bottom:5px}.x-tab-bar-bottom > .x-tab-bar-body-default{padding-top:5px}.x-tab-bar-left > .x-tab-bar-body-default{padding-right:5px}.x-tab-bar-right > .x-tab-bar-body-default{padding-left:5px}.x-tab-bar-strip-default{border-style:solid;border-color:#157fcc;background-color:#add2ed}.x-tab-bar-top > .x-tab-bar-strip-default{border-width:0 0;height:5px}.x-tab-bar-top.x-tab-bar-plain > .x-tab-bar-strip-default{border-width:0 0 0 0}.x-tab-bar-bottom > .x-tab-bar-strip-default{border-width:0 0 0 0;height:5px}.x-tab-bar-bottom.x-tab-bar-plain > .x-tab-bar-strip-default{border-width:0 0 0 0}.x-tab-bar-left > .x-tab-bar-strip-default{border-width:0 0 0 0;width:5px}.x-tab-bar-left.x-tab-bar-plain > .x-tab-bar-strip-default{border-width:0 0 0 0}.x-tab-bar-right > .x-tab-bar-strip-default{border-width:0 0 0 0;width:5px}.x-tab-bar-right.x-tab-bar-plain > .x-tab-bar-strip-default{border-width:0 0 0 0}.x-tab-bar-horizontal > .x-tab-bar-body-default{min-height:34px}.x-ie8m .x-tab-bar-horizontal > .x-tab-bar-body-default{min-height:29px}.x-tab-bar-vertical > .x-tab-bar-body-default{min-width:34px}.x-ie8m .x-tab-bar-vertical > .x-tab-bar-body-default{min-width:29px}.x-tab-bar-default-scroller .x-box-scroller-body-horizontal{margin-left:24px}.x-tab-bar-default-vertical-scroller .x-box-scroller-body-vertical{margin-top:24px}.x-box-scroller-tab-bar-default{cursor:pointer;color:#fff;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-box-scroller-tab-bar-default.x-box-scroller-hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-box-scroller-tab-bar-default.x-box-scroller-pressed{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=70)";opacity:0.7}.x-box-scroller-tab-bar-default.x-box-scroller-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=25)";opacity:0.25;cursor:default}.x-box-scroller-tab-bar-default.x-box-scroller-left,.x-box-scroller-tab-bar-default.x-box-scroller-right{width:24px;height:24px;top:50%;margin-top:-12px}.x-box-scroller-tab-bar-default.x-box-scroller-left{margin-left:0;margin-right:0;margin-bottom:0;background-image:url(images/tab-bar/default-scroll-left.png)}.x-box-scroller-tab-bar-default.x-box-scroller-right{margin-left:0;margin-right:0;margin-bottom:0;background-image:url(images/tab-bar/default-scroll-right.png)}.x-box-scroller-tab-bar-default.x-box-scroller-top,.x-box-scroller-tab-bar-default.x-box-scroller-bottom{height:24px;width:24px;left:50%;margin-left:-12px}.x-box-scroller-tab-bar-default.x-box-scroller-top{margin-top:0;margin-right:0;margin-bottom:0;background-image:url(images/tab-bar/default-scroll-top.png)}.x-box-scroller-tab-bar-default.x-box-scroller-bottom{margin-top:0;margin-right:0;margin-bottom:0;background-image:url(images/tab-bar/default-scroll-bottom.png)}.x-tab-bar-more-icon{background-image:url(images/tab-bar/default-more.png)}.x-tab-bar-plain.x-tab-bar-default-scroller .x-box-scroller-body-horizontal{margin-left:24px}.x-tab-bar-plain.x-tab-bar-default-vertical-scroller .x-box-scroller-body-vertical{margin-top:24px}.x-tab-bar-plain .x-box-scroller-tab-bar-default{color:#b0b0b0}.x-tab-bar-default-top .x-box-scroller-tab-bar-default{margin-top:-14px}.x-tab-bar-default-right .x-box-scroller-tab-bar-default{margin-left:-10px}.x-tab-bar-default-bottom .x-box-scroller-tab-bar-default{margin-top:-10px}.x-tab-bar-default-left .x-box-scroller-tab-bar-default{margin-left:-14px}.x-box-scroller-tab-bar-default{background-color:#157fcc}.x-box-scroller-tab-bar-default .x-ie8 .x-box-scroller-plain{background-color:#fff}.x-box-scroller-plain.x-box-scroller-tab-bar-default.x-box-scroller-left{background-image:url(images/tab-bar/default-plain-scroll-left.png)}.x-box-scroller-plain.x-box-scroller-tab-bar-default.x-box-scroller-right{background-image:url(images/tab-bar/default-plain-scroll-right.png)}.x-box-scroller-plain.x-box-scroller-tab-bar-default.x-box-scroller-top{background-image:url(images/tab-bar/default-plain-scroll-top.png)}.x-box-scroller-plain.x-box-scroller-tab-bar-default.x-box-scroller-bottom{background-image:url(images/tab-bar/default-plain-scroll-bottom.png)}.x-breadcrumb-btn-default{margin:0 0 0 0px}.x-breadcrumb-icon-folder-default{background-image:url(images/tree/folder.png)}.x-btn-menu-active .x-breadcrumb-icon-folder-default{background-image:url(images/tree/folder-open.png)}.x-breadcrumb-icon-leaf-default{background-image:url(images/tree/leaf.png)}.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-arrow:after{width:20px;background-image:url(images/breadcrumb/default-arrow.png)}.x-btn-menu-active.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-arrow:after{background-image:url(images/breadcrumb/default-arrow-open.png)}.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after{width:20px;background-image:url(images/breadcrumb/default-split-arrow.png)}.x-btn-over.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after{background-image:url(images/breadcrumb/default-split-arrow-over.png)}.x-btn-menu-active.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after{background-image:url(images/breadcrumb/default-split-arrow-open.png)}.x-breadcrumb-default-scroller .x-box-scroller-body-horizontal{margin-left:24px}.x-breadcrumb-default-vertical-scroller .x-box-scroller-body-vertical{margin-top:24px}.x-box-scroller-breadcrumb-default{cursor:pointer;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-box-scroller-breadcrumb-default.x-box-scroller-hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=80)";opacity:0.8}.x-box-scroller-breadcrumb-default.x-box-scroller-pressed{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";opacity:1}.x-box-scroller-breadcrumb-default.x-box-scroller-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=25)";opacity:0.25;cursor:default}.x-box-scroller-breadcrumb-default.x-box-scroller-left,.x-box-scroller-breadcrumb-default.x-box-scroller-right{width:16px;height:16px;top:50%;margin-top:-8px}.x-box-scroller-breadcrumb-default.x-box-scroller-left{margin-left:4px;margin-right:4px;margin-bottom:0;background-image:url(images/breadcrumb/default-scroll-left.png)}.x-box-scroller-breadcrumb-default.x-box-scroller-right{margin-left:4px;margin-right:4px;margin-bottom:0;background-image:url(images/breadcrumb/default-scroll-right.png)}.x-tree-expander{cursor:pointer}.x-tree-arrows .x-tree-expander{background-image:url(images/tree/arrows.png)}.x-tree-arrows .x-tree-expander-over .x-tree-expander{background-position:-36px center}.x-tree-arrows .x-grid-tree-node-expanded .x-tree-expander{background-position:-18px center}.x-tree-arrows .x-grid-tree-node-expanded .x-tree-expander-over .x-tree-expander{background-position:-54px center}.x-tree-lines .x-tree-elbow{background-image:url(images/tree/elbow.png)}.x-tree-lines .x-tree-elbow-end{background-image:url(images/tree/elbow-end.png)}.x-tree-lines .x-tree-elbow-plus{background-image:url(images/tree/elbow-plus.png)}.x-tree-lines .x-tree-elbow-end-plus{background-image:url(images/tree/elbow-end-plus.png)}.x-tree-lines .x-grid-tree-node-expanded .x-tree-elbow-plus{background-image:url(images/tree/elbow-minus.png)}.x-tree-lines .x-grid-tree-node-expanded .x-tree-elbow-end-plus{background-image:url(images/tree/elbow-end-minus.png)}.x-tree-lines .x-tree-elbow-line{background-image:url(images/tree/elbow-line.png)} \ No newline at end of file diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all_2.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all_2.css new file mode 100644 index 0000000..ccf4fac --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neptune-all_2.css @@ -0,0 +1 @@ +.x-tree-no-lines .x-tree-expander{background-image:url(images/tree/elbow-plus-nl.png)}.x-tree-no-lines .x-grid-tree-node-expanded .x-tree-expander{background-image:url(images/tree/elbow-minus-nl.png)}.x-tree-icon{width:16px;height:24px;line-height:24px;color:#b0b0b0;font-size:16px}.x-tree-elbow-img{width:18px;height:24px;line-height:24px;margin-right:2px}.x-tree-icon,.x-tree-elbow-img,.x-tree-checkbox{margin-top:-5px;margin-bottom:-4px}.x-tree-icon-leaf{background-image:url(images/tree/leaf.png)}.x-tree-icon-parent{background-image:url(images/tree/folder.png)}.x-tree-icon-parent-expanded{background-image:url(images/tree/folder-open.png)}.x-tree-icon-custom{background-image:none}.x-tree-checkbox{margin-right:4px;top:5px;width:15px;height:15px;background-image:url(images/form/checkbox.png)}.x-tree-checkbox-checked{background-position:0 -15px}.x-grid-tree-loading .x-tree-icon{background-image:url(images/tree/loading.gif)}.x-tree-node-text{padding-left:4px}.x-grid-cell-inner-treecolumn{padding:5px 10px 4px 6px}.x-tree-drop-ok-append .x-dd-drop-icon{background-image:url(images/tree/drop-append.png)}.x-tree-drop-ok-above .x-dd-drop-icon{background-image:url(images/tree/drop-above.png)}.x-tree-drop-ok-below .x-dd-drop-icon{background-image:url(images/tree/drop-below.png)}.x-tree-drop-ok-between .x-dd-drop-icon{background-image:url(images/tree/drop-between.png)}.x-tree-ddindicator{height:1px;border-width:1px 0px 0px;border-style:dotted;border-color:green}.x-multiselector-remove{font-size:110%;color:#e1e1e1;cursor:pointer}.x-multiselector-remove .x-grid-cell-inner{padding:5px 4px 4px 4px}.x-grid-item-over .x-multiselector-remove{color:red}.x-multiselector-search-input .x-form-text::-ms-clear{display:none}.x-toast-icon-information{background-image:url(images/window/toast/icon16_info.png)}.x-toast-icon-error{background-image:url(images/window/toast/icon16_error.png)}.x-toast-window .x-window-body{padding:15px 5px 15px 5px}.x-toast-light .x-window-header{background-color:#3892d4}.x-toast-light .x-tool-img{background-color:#3892d4}.x-toast-light{background-image:url(images/window/toast/fader.png)}.x-toast-light .x-window-body{padding:15px 5px 20px 5px;background-color:transparent;border:0px solid white}.x-btn-plain-toolbar-small{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:transparent}.x-btn-plain-toolbar-small-mc{background-image:url(images/btn/btn-plain-toolbar-small-fbg.gif);background-position:0 top;background-color:transparent}.x-nbr .x-btn-plain-toolbar-small{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-plain-toolbar-small-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-plain-toolbar-small-tl{background-position:0 -6px}.x-btn-plain-toolbar-small-tr{background-position:right -9px}.x-btn-plain-toolbar-small-bl{background-position:0 -12px}.x-btn-plain-toolbar-small-br{background-position:right -15px}.x-btn-plain-toolbar-small-ml{background-position:0 top}.x-btn-plain-toolbar-small-mr{background-position:right top}.x-btn-plain-toolbar-small-tc{background-position:0 0}.x-btn-plain-toolbar-small-bc{background-position:0 -3px}.x-btn-plain-toolbar-small-tr,.x-btn-plain-toolbar-small-br,.x-btn-plain-toolbar-small-mr{padding-right:3px}.x-btn-plain-toolbar-small-tl,.x-btn-plain-toolbar-small-bl,.x-btn-plain-toolbar-small-ml{padding-left:3px}.x-btn-plain-toolbar-small-tc{height:3px}.x-btn-plain-toolbar-small-bc{height:3px}.x-btn-plain-toolbar-small-mc{padding:1px 1px 1px 1px}.x-btn-plain-toolbar-small{border-color:transparent}.x-btn-button-plain-toolbar-small{min-height:16px}.x-ie9m .x-btn-button-plain-toolbar-small{min-height:auto;height:16px}.x-btn-inner-plain-toolbar-small{font:bold 12px/16px tahoma, verdana, sans-serif;color:#666;padding:0 5px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-small,.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-small{max-width:calc(100% - 16px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-small,.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-small{max-width:calc(100% - 15px)}.x-ie10p .x-btn-inner-plain-toolbar-small{max-width:none}.x-btn-icon-el-plain-toolbar-small{font-size:16px;height:16px;color:#666;line-height:16px}.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small,.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small{width:16px}.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small,.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small{min-width:16px}.x-btn-icon-el-plain-toolbar-small.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-plain-toolbar-small.x-btn-glyph{color:#b3b3b3}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small{margin-right:0px}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small{margin-left:0px}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small{margin-right:5px}.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-small,.x-btn-split-bottom > .x-btn-button-plain-toolbar-small{padding-bottom:3px}.x-btn-wrap-plain-toolbar-small.x-btn-arrow-right:after{width:16px;background-image:url(images/button/plain-toolbar-small-arrow.png);padding-right:16px}.x-btn-wrap-plain-toolbar-small.x-btn-arrow-bottom:after{height:13px;background-image:url(images/button/plain-toolbar-small-arrow.png)}.x-btn-wrap-plain-toolbar-small.x-btn-split-right:after{width:20px;background-image:url(images/button/plain-toolbar-small-s-arrow.png);padding-right:20px}.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom:after{height:15px;background-image:url(images/button/plain-toolbar-small-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small{margin-right:5px}.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-small{background-image:none;background-color:transparent;-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn-plain-toolbar-small .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:23px;pointer-events:none}.x-keyboard-mode .x-btn-plain-toolbar-small.x-arrow-focus .x-btn-arrow-el{border:1px solid #4297d4}.x-btn-over.x-btn-plain-toolbar-small{border-color:#d8d8d8;background-image:none;background-color:#ececec;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec));background-image:-webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:linear-gradient(top,#eee, #ececec 50%, #e0e0e0 51%, #ececec)}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-small{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-plain-toolbar-small,.x-btn.x-btn-pressed.x-btn-plain-toolbar-small{border-color:#cfcfcf;background-image:none;background-color:#e2e2e2;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5));background-image:-webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:linear-gradient(top,#e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-plain-toolbar-small{background-image:none;background-color:transparent}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tr,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-br,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tc,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-ml,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mc{background-color:transparent;background-image:url(images/btn/btn-plain-toolbar-small-focus-fbg.gif)}.x-btn-over .x-btn-plain-toolbar-small-tl,.x-btn-over .x-btn-plain-toolbar-small-bl,.x-btn-over .x-btn-plain-toolbar-small-tr,.x-btn-over .x-btn-plain-toolbar-small-br,.x-btn-over .x-btn-plain-toolbar-small-tc,.x-btn-over .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-over-corners.gif)}.x-btn-over .x-btn-plain-toolbar-small-ml,.x-btn-over .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-over-sides.gif)}.x-btn-over .x-btn-plain-toolbar-small-mc{background-color:#ececec;background-image:url(images/btn/btn-plain-toolbar-small-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mc{background-color:#ececec;background-image:url(images/btn/btn-plain-toolbar-small-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tr,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-br,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tc,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-br,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-ml,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-ml,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-plain-toolbar-small-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-plain-toolbar-small-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tr,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-br,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tc,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-ml,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mc{background-color:transparent;background-image:url(images/btn/btn-plain-toolbar-small-disabled-fbg.gif)}.x-nbr .x-btn-plain-toolbar-small{background-image:none}.x-btn-disabled.x-btn-plain-toolbar-small{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first .x-btn-plain-toolbar-small-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle .x-btn-plain-toolbar-small-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last .x-btn-plain-toolbar-small-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first .x-btn-plain-toolbar-small-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle .x-btn-plain-toolbar-small-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last .x-btn-plain-toolbar-small-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-small:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-small:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-small:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small:after{border-width:1px;border-color:#4297d4}.x-button-plain-toolbar-small-cell > .x-grid-cell-inner{padding-top:0px;padding-bottom:0px}.x-button-plain-toolbar-small-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-small{vertical-align:top}.x-btn-plain-toolbar-medium{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:transparent}.x-btn-plain-toolbar-medium-mc{background-image:url(images/btn/btn-plain-toolbar-medium-fbg.gif);background-position:0 top;background-color:transparent}.x-nbr .x-btn-plain-toolbar-medium{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-plain-toolbar-medium-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-plain-toolbar-medium-tl{background-position:0 -6px}.x-btn-plain-toolbar-medium-tr{background-position:right -9px}.x-btn-plain-toolbar-medium-bl{background-position:0 -12px}.x-btn-plain-toolbar-medium-br{background-position:right -15px}.x-btn-plain-toolbar-medium-ml{background-position:0 top}.x-btn-plain-toolbar-medium-mr{background-position:right top}.x-btn-plain-toolbar-medium-tc{background-position:0 0}.x-btn-plain-toolbar-medium-bc{background-position:0 -3px}.x-btn-plain-toolbar-medium-tr,.x-btn-plain-toolbar-medium-br,.x-btn-plain-toolbar-medium-mr{padding-right:3px}.x-btn-plain-toolbar-medium-tl,.x-btn-plain-toolbar-medium-bl,.x-btn-plain-toolbar-medium-ml{padding-left:3px}.x-btn-plain-toolbar-medium-tc{height:3px}.x-btn-plain-toolbar-medium-bc{height:3px}.x-btn-plain-toolbar-medium-mc{padding:1px 1px 1px 1px}.x-btn-plain-toolbar-medium{border-color:transparent}.x-btn-button-plain-toolbar-medium{min-height:24px}.x-ie9m .x-btn-button-plain-toolbar-medium{min-height:auto;height:24px}.x-btn-inner-plain-toolbar-medium{font:bold 14px/18px tahoma, verdana, sans-serif;color:#666;padding:0 8px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium,.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium{max-width:calc(100% - 24px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium,.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium{max-width:calc(100% - 23px)}.x-ie10p .x-btn-inner-plain-toolbar-medium{max-width:none}.x-btn-icon-el-plain-toolbar-medium{font-size:24px;height:24px;color:#666;line-height:24px}.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium,.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium{width:24px}.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium,.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium{min-width:24px}.x-btn-icon-el-plain-toolbar-medium.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-plain-toolbar-medium.x-btn-glyph{color:#b3b3b3}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium{margin-right:0}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium{margin-left:0}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium{margin-right:8px}.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-medium,.x-btn-split-bottom > .x-btn-button-plain-toolbar-medium{padding-bottom:3px}.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-right:after{width:24px;background-image:url(images/button/plain-toolbar-medium-arrow.png);padding-right:24px}.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-bottom:after{height:18px;background-image:url(images/button/plain-toolbar-medium-arrow.png)}.x-btn-wrap-plain-toolbar-medium.x-btn-split-right:after{width:28px;background-image:url(images/button/plain-toolbar-medium-s-arrow.png);padding-right:28px}.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom:after{height:24px;background-image:url(images/button/plain-toolbar-medium-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium{margin-right:8px}.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-medium{background-image:none;background-color:transparent;-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn-plain-toolbar-medium .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:31px;pointer-events:none}.x-keyboard-mode .x-btn-plain-toolbar-medium.x-arrow-focus .x-btn-arrow-el{border:1px solid #4297d4}.x-btn-over.x-btn-plain-toolbar-medium{border-color:#d8d8d8;background-image:none;background-color:#ececec;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec));background-image:-webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:linear-gradient(top,#eee, #ececec 50%, #e0e0e0 51%, #ececec)}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-plain-toolbar-medium,.x-btn.x-btn-pressed.x-btn-plain-toolbar-medium{border-color:#cfcfcf;background-image:none;background-color:#e2e2e2;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5));background-image:-webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:linear-gradient(top,#e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-plain-toolbar-medium{background-image:none;background-color:transparent}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-br,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mc{background-color:transparent;background-image:url(images/btn/btn-plain-toolbar-medium-focus-fbg.gif)}.x-btn-over .x-btn-plain-toolbar-medium-tl,.x-btn-over .x-btn-plain-toolbar-medium-bl,.x-btn-over .x-btn-plain-toolbar-medium-tr,.x-btn-over .x-btn-plain-toolbar-medium-br,.x-btn-over .x-btn-plain-toolbar-medium-tc,.x-btn-over .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-over-corners.gif)}.x-btn-over .x-btn-plain-toolbar-medium-ml,.x-btn-over .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-over-sides.gif)}.x-btn-over .x-btn-plain-toolbar-medium-mc{background-color:#ececec;background-image:url(images/btn/btn-plain-toolbar-medium-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mc{background-color:#ececec;background-image:url(images/btn/btn-plain-toolbar-medium-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tr,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-br,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tc,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-br,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-ml,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-ml,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-plain-toolbar-medium-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-plain-toolbar-medium-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tr,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-br,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tc,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-ml,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mc{background-color:transparent;background-image:url(images/btn/btn-plain-toolbar-medium-disabled-fbg.gif)}.x-nbr .x-btn-plain-toolbar-medium{background-image:none}.x-btn-disabled.x-btn-plain-toolbar-medium{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first .x-btn-plain-toolbar-medium-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle .x-btn-plain-toolbar-medium-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last .x-btn-plain-toolbar-medium-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first .x-btn-plain-toolbar-medium-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle .x-btn-plain-toolbar-medium-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last .x-btn-plain-toolbar-medium-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-medium:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-medium:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium:after{border-width:1px;border-color:#4297d4}.x-button-plain-toolbar-medium-cell > .x-grid-cell-inner{padding-top:0;padding-bottom:0}.x-button-plain-toolbar-medium-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-medium{vertical-align:top}.x-btn-plain-toolbar-large{-webkit-border-radius:3px;-moz-border-radius:3px;-ms-border-radius:3px;-o-border-radius:3px;border-radius:3px;padding:3px 3px 3px 3px;border-width:1px;border-style:solid;background-image:none;background-color:transparent}.x-btn-plain-toolbar-large-mc{background-image:url(images/btn/btn-plain-toolbar-large-fbg.gif);background-position:0 top;background-color:transparent}.x-nbr .x-btn-plain-toolbar-large{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;background-image:none;box-shadow:none !important}.x-btn-plain-toolbar-large-frameInfo{font-family:th-3-3-3-3-1-1-1-1-3-3-3-3}.x-btn-plain-toolbar-large-tl{background-position:0 -6px}.x-btn-plain-toolbar-large-tr{background-position:right -9px}.x-btn-plain-toolbar-large-bl{background-position:0 -12px}.x-btn-plain-toolbar-large-br{background-position:right -15px}.x-btn-plain-toolbar-large-ml{background-position:0 top}.x-btn-plain-toolbar-large-mr{background-position:right top}.x-btn-plain-toolbar-large-tc{background-position:0 0}.x-btn-plain-toolbar-large-bc{background-position:0 -3px}.x-btn-plain-toolbar-large-tr,.x-btn-plain-toolbar-large-br,.x-btn-plain-toolbar-large-mr{padding-right:3px}.x-btn-plain-toolbar-large-tl,.x-btn-plain-toolbar-large-bl,.x-btn-plain-toolbar-large-ml{padding-left:3px}.x-btn-plain-toolbar-large-tc{height:3px}.x-btn-plain-toolbar-large-bc{height:3px}.x-btn-plain-toolbar-large-mc{padding:1px 1px 1px 1px}.x-btn-plain-toolbar-large{border-color:transparent}.x-btn-button-plain-toolbar-large{min-height:32px}.x-ie9m .x-btn-button-plain-toolbar-large{min-height:auto;height:32px}.x-btn-inner-plain-toolbar-large{font:bold 16px/20px tahoma, verdana, sans-serif;color:#666;padding:0 10px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-large,.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-large{max-width:calc(100% - 32px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-large,.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-large{max-width:calc(100% - 31px)}.x-ie10p .x-btn-inner-plain-toolbar-large{max-width:none}.x-btn-icon-el-plain-toolbar-large{font-size:32px;height:32px;color:#666;line-height:32px}.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large,.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large{width:32px}.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large,.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large{min-width:32px}.x-btn-icon-el-plain-toolbar-large.x-btn-glyph{opacity:0.5}.x-ie8 .x-btn-icon-el-plain-toolbar-large.x-btn-glyph{color:#b3b3b3}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large{margin-right:0}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large{margin-left:0}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large{margin-bottom:5px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large{margin-top:5px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large{padding-right:5px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large{margin-right:10px}.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-large,.x-btn-split-bottom > .x-btn-button-plain-toolbar-large{padding-bottom:3px}.x-btn-wrap-plain-toolbar-large.x-btn-arrow-right:after{width:28px;background-image:url(images/button/plain-toolbar-large-arrow.png);padding-right:28px}.x-btn-wrap-plain-toolbar-large.x-btn-arrow-bottom:after{height:20px;background-image:url(images/button/plain-toolbar-large-arrow.png)}.x-btn-wrap-plain-toolbar-large.x-btn-split-right:after{width:35px;background-image:url(images/button/plain-toolbar-large-s-arrow.png);padding-right:35px}.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom:after{height:29px;background-image:url(images/button/plain-toolbar-large-s-arrow-b.png)}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large{padding-right:5px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large{margin-right:10px}.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-large{background-image:none;background-color:transparent;-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn-plain-toolbar-large .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:38px;pointer-events:none}.x-keyboard-mode .x-btn-plain-toolbar-large.x-arrow-focus .x-btn-arrow-el{border:1px solid #4297d4}.x-btn-over.x-btn-plain-toolbar-large{border-color:#d8d8d8;background-image:none;background-color:#ececec;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #eee), color-stop(50%, #ececec), color-stop(51%, #e0e0e0), color-stop(0%, #ececec));background-image:-webkit-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-moz-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-o-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:-ms-linear-gradient(top, #eee, #ececec 50%, #e0e0e0 51%, #ececec);background-image:linear-gradient(top,#eee, #ececec 50%, #e0e0e0 51%, #ececec)}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-large{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-plain-toolbar-large,.x-btn.x-btn-pressed.x-btn-plain-toolbar-large{border-color:#cfcfcf;background-image:none;background-color:#e2e2e2;background-image:-webkit-gradient(linear, top, bottom, color-stop(0%, #e2e2e2), color-stop(50%, #d6d6d6), color-stop(51%, #e2e2e2), color-stop(0%, #e5e5e5));background-image:-webkit-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-moz-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-o-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:-ms-linear-gradient(top, #e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5);background-image:linear-gradient(top,#e2e2e2, #d6d6d6 50%, #e2e2e2 51%, #e5e5e5)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large{-webkit-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;-moz-box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset;box-shadow:#4297d4 0 1px 0px 0 inset, #4297d4 0 -1px 0px 0 inset, #4297d4 -1px 0 0px 0 inset, #4297d4 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-plain-toolbar-large{background-image:none;background-color:transparent}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tr,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-br,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tc,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-ml,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mc{background-color:transparent;background-image:url(images/btn/btn-plain-toolbar-large-focus-fbg.gif)}.x-btn-over .x-btn-plain-toolbar-large-tl,.x-btn-over .x-btn-plain-toolbar-large-bl,.x-btn-over .x-btn-plain-toolbar-large-tr,.x-btn-over .x-btn-plain-toolbar-large-br,.x-btn-over .x-btn-plain-toolbar-large-tc,.x-btn-over .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-over-corners.gif)}.x-btn-over .x-btn-plain-toolbar-large-ml,.x-btn-over .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-over-sides.gif)}.x-btn-over .x-btn-plain-toolbar-large-mc{background-color:#ececec;background-image:url(images/btn/btn-plain-toolbar-large-over-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mc{background-color:#ececec;background-image:url(images/btn/btn-plain-toolbar-large-focus-over-fbg.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tr,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-br,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tc,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-br,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-ml,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-ml,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-plain-toolbar-large-pressed-fbg.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mc{background-color:#e2e2e2;background-image:url(images/btn/btn-plain-toolbar-large-focus-pressed-fbg.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tr,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-br,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tc,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-ml,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mc{background-color:transparent;background-image:url(images/btn/btn-plain-toolbar-large-disabled-fbg.gif)}.x-nbr .x-btn-plain-toolbar-large{background-image:none}.x-btn-disabled.x-btn-plain-toolbar-large{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first .x-btn-plain-toolbar-large-mc{padding-right:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle .x-btn-plain-toolbar-large-mc{padding-right:3px !important;padding-left:3px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last .x-btn-plain-toolbar-large-mc{padding-left:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first .x-btn-plain-toolbar-large-mc{padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle .x-btn-plain-toolbar-large-mc{padding-top:3px !important;padding-bottom:3px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last .x-btn-plain-toolbar-large-mc{padding-top:3px !important}.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-large:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-large:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-large:after{border-width:1px;border-color:#4297d4}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large:after{border-width:1px;border-color:#4297d4}.x-button-plain-toolbar-large-cell > .x-grid-cell-inner{padding-top:0;padding-bottom:0}.x-button-plain-toolbar-large-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-large{vertical-align:top}.x-btn-plain-toolbar-small-disabled .x-btn-icon-el,.x-btn-plain-toolbar-medium-disabled .x-btn-icon-el,.x-btn-plain-toolbar-large-disabled .x-btn-icon-el{background-color:#fff}.x-ie8 .x-btn-plain-toolbar-small-disabled .x-btn-icon-el,.x-ie8 .x-btn-plain-toolbar-medium-disabled .x-btn-icon-el,.x-ie8 .x-btn-plain-toolbar-large-disabled .x-btn-icon-el{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-panel-light{border-color:#e0ebf3;padding:0}.x-panel-light.x-masked{border-color:#f6f9fb}.x-panel-header-light{font-size:13px;border:1px solid #e0ebf3}.x-panel-header-light .x-tool-tool-el{color:#666}.x-panel-header-light .x-tool-img{background-image:url(images/tools/tool-sprites-dark.png)}.x-panel-header-light .x-tool-tool-el{background-color:#e0ebf3}.x-panel-header-light-horizontal{padding:9px 9px 10px}.x-panel-header-light-horizontal .x-panel-header-light-tab-bar{margin-top:-9px;margin-bottom:-10px}.x-panel-header-light-horizontal.x-header-noborder{padding:10px 10px 10px 10px}.x-panel-header-light-horizontal.x-header-noborder .x-panel-header-light-tab-bar{margin-top:-10px;margin-bottom:-10px}.x-panel-header-light-vertical{padding:9px 9px 9px 10px}.x-panel-header-light-vertical .x-panel-header-light-tab-bar{margin-right:-9px;margin-left:-10px}.x-panel-header-light-vertical.x-header-noborder{padding:10px 10px 10px 10px}.x-panel-header-light-vertical.x-header-noborder .x-panel-header-light-tab-bar{margin-right:-10px;margin-left:-10px}.x-panel-header-title-light{color:#666;font-size:13px;font-weight:bold;font-family: tahoma, verdana, sans-serif;line-height:16px}.x-keyboard-mode .x-panel-header-title-light.x-title-focus{outline:1px solid #157fcc;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus,.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus,.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after,.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #157fcc;pointer-events:none}.x-panel-header-title-light > .x-title-text-light{text-transform:none;padding:0}.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-top{height:22px;padding-bottom:6px}.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-right{width:22px;padding-left:6px}.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-bottom{height:22px;padding-top:6px}.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-left{width:22px;padding-right:6px}.x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light{width:16px;height:16px;font-size:16px;color:#666;background-position:center center}.x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light.x-title-glyph{opacity:0.5}.x-ie8 .x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light.x-title-glyph{color:#a3a8ac}.x-panel-body-light{background:#fff;border-color:#e0ebf3;color:#000;font-size:13px;font-weight:normal;font-family: tahoma, verdana, sans-serif;border-width:1px;border-style:solid}.x-panel-header-light{background-image:none;background-color:#e0ebf3}.x-panel-header-light-vertical{background-image:none;background-color:#e0ebf3}.x-panel .x-panel-header-light-collapsed-border-top{border-bottom-width:1px !important}.x-panel .x-panel-header-light-collapsed-border-right{border-left-width:1px !important}.x-panel .x-panel-header-light-collapsed-border-bottom{border-top-width:1px !important}.x-panel .x-panel-header-light-collapsed-border-left{border-right-width:1px !important}.x-panel-header-light-horizontal .x-tool-after-title{margin:0 0 0 6px}.x-panel-header-light-horizontal .x-tool-before-title{margin:0 6px 0 0}.x-panel-header-light-vertical .x-tool-after-title{margin:6px 0 0 0}.x-panel-header-light-vertical .x-tool-before-title{margin:0 0 6px 0}.x-keyboard-mode .x-panel-header-light .x-tool-focus{outline:1px solid #157fcc;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus,.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus,.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus:after,.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #157fcc;pointer-events:none}.x-panel-light-resizable .x-panel-handle{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-panel-light-outer-border-l{border-left-color:#e0ebf3 !important;border-left-width:1px !important}.x-panel-light-outer-border-b{border-bottom-color:#e0ebf3 !important;border-bottom-width:1px !important}.x-panel-light-outer-border-bl{border-bottom-color:#e0ebf3 !important;border-bottom-width:1px !important;border-left-color:#e0ebf3 !important;border-left-width:1px !important}.x-panel-light-outer-border-r{border-right-color:#e0ebf3 !important;border-right-width:1px !important}.x-panel-light-outer-border-rl{border-right-color:#e0ebf3 !important;border-right-width:1px !important;border-left-color:#e0ebf3 !important;border-left-width:1px !important}.x-panel-light-outer-border-rb{border-right-color:#e0ebf3 !important;border-right-width:1px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:1px !important}.x-panel-light-outer-border-rbl{border-right-color:#e0ebf3 !important;border-right-width:1px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:1px !important;border-left-color:#e0ebf3 !important;border-left-width:1px !important}.x-panel-light-outer-border-t{border-top-color:#e0ebf3 !important;border-top-width:1px !important}.x-panel-light-outer-border-tl{border-top-color:#e0ebf3 !important;border-top-width:1px !important;border-left-color:#e0ebf3 !important;border-left-width:1px !important}.x-panel-light-outer-border-tb{border-top-color:#e0ebf3 !important;border-top-width:1px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:1px !important}.x-panel-light-outer-border-tbl{border-top-color:#e0ebf3 !important;border-top-width:1px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:1px !important;border-left-color:#e0ebf3 !important;border-left-width:1px !important}.x-panel-light-outer-border-tr{border-top-color:#e0ebf3 !important;border-top-width:1px !important;border-right-color:#e0ebf3 !important;border-right-width:1px !important}.x-panel-light-outer-border-trl{border-top-color:#e0ebf3 !important;border-top-width:1px !important;border-right-color:#e0ebf3 !important;border-right-width:1px !important;border-left-color:#e0ebf3 !important;border-left-width:1px !important}.x-panel-light-outer-border-trb{border-top-color:#e0ebf3 !important;border-top-width:1px !important;border-right-color:#e0ebf3 !important;border-right-width:1px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:1px !important}.x-panel-light-outer-border-trbl{border-color:#e0ebf3 !important;border-width:1px !important}.x-panel-light-framed{border-color:#e0ebf3;padding:0}.x-panel-light-framed.x-masked{border-color:#f6f9fb}.x-panel-header-light-framed{font-size:13px;border:5px solid #e0ebf3}.x-panel-header-light-framed .x-tool-tool-el{color:#666}.x-panel-header-light-framed .x-tool-img{background-image:url(images/tools/tool-sprites-dark.png)}.x-panel-header-light-framed .x-tool-tool-el{background-color:#e0ebf3}.x-panel-header-light-framed-horizontal{padding:5px 5px 5px 5px}.x-panel-header-light-framed-horizontal .x-panel-header-light-framed-tab-bar{margin-top:-5px;margin-bottom:-5px}.x-panel-header-light-framed-horizontal.x-header-noborder{padding:10px 10px 5px 10px}.x-panel-header-light-framed-horizontal.x-header-noborder .x-panel-header-light-framed-tab-bar{margin-top:-10px;margin-bottom:-5px}.x-panel-header-light-framed-vertical{padding:5px 5px 5px 5px}.x-panel-header-light-framed-vertical .x-panel-header-light-framed-tab-bar{margin-right:-5px;margin-left:-5px}.x-panel-header-light-framed-vertical.x-header-noborder{padding:10px 10px 10px 5px}.x-panel-header-light-framed-vertical.x-header-noborder .x-panel-header-light-framed-tab-bar{margin-right:-10px;margin-left:-5px}.x-panel-header-title-light-framed{color:#666;font-size:13px;font-weight:bold;font-family: tahoma, verdana, sans-serif;line-height:16px}.x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus{outline:1px solid #157fcc;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus,.x-ie10p .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus,.x-edge .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after,.x-edge .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #157fcc;pointer-events:none}.x-panel-header-title-light-framed > .x-title-text-light-framed{text-transform:none;padding:0}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-top{height:22px;padding-bottom:6px}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-right{width:22px;padding-left:6px}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-bottom{height:22px;padding-top:6px}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-left{width:22px;padding-right:6px}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed{width:16px;height:16px;font-size:16px;color:#666;background-position:center center}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed.x-title-glyph{opacity:0.5}.x-ie8 .x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed.x-title-glyph{color:#a3a8ac}.x-panel-body-light-framed{background:#fff;border-color:#e0ebf3;color:#000;font-size:13px;font-weight:normal;font-family: tahoma, verdana, sans-serif;border-width:1px;border-style:solid}.x-panel-light-framed{-webkit-border-radius:4px;-moz-border-radius:4px;-ms-border-radius:4px;-o-border-radius:4px;border-radius:4px;padding:0px 0px 0px 0px;border-width:5px;border-style:solid;background-color:#fff}.x-panel-light-framed-mc{background-color:#fff}.x-nbr .x-panel-light-framed{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-light-framed-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-0-0-0-0}.x-panel-light-framed-tl{background-position:0 -10px}.x-panel-light-framed-tr{background-position:right -15px}.x-panel-light-framed-bl{background-position:0 -20px}.x-panel-light-framed-br{background-position:right -25px}.x-panel-light-framed-ml{background-position:0 top}.x-panel-light-framed-mr{background-position:right top}.x-panel-light-framed-tc{background-position:0 0}.x-panel-light-framed-bc{background-position:0 -5px}.x-panel-light-framed-tr,.x-panel-light-framed-br,.x-panel-light-framed-mr{padding-right:5px}.x-panel-light-framed-tl,.x-panel-light-framed-bl,.x-panel-light-framed-ml{padding-left:5px}.x-panel-light-framed-tc{height:5px}.x-panel-light-framed-bc{height:5px}.x-panel-light-framed-tl,.x-panel-light-framed-bl,.x-panel-light-framed-tr,.x-panel-light-framed-br,.x-panel-light-framed-tc,.x-panel-light-framed-bc,.x-panel-light-framed-ml,.x-panel-light-framed-mr{background-image:url(images/panel/panel-light-framed-corners.gif)}.x-panel-light-framed-ml,.x-panel-light-framed-mr{background-image:url(images/panel/panel-light-framed-sides.gif);background-repeat:repeat-y}.x-panel-light-framed-mc{padding:0px 0px 0px 0px}.x-panel-header-light-framed-top{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:5px 5px 5px 5px;border-width:5px 5px 0 5px;border-style:solid;background-color:#e0ebf3}.x-panel-header-light-framed-top-mc{background-color:#e0ebf3}.x-nbr .x-panel-header-light-framed-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-top-frameInfo{font-family:dh-5-5-0-5-5-5-0-5-5-5-5-5}.x-panel-header-light-framed-top-tl{background-position:0 -10px}.x-panel-header-light-framed-top-tr{background-position:right -15px}.x-panel-header-light-framed-top-bl{background-position:0 -20px}.x-panel-header-light-framed-top-br{background-position:right -25px}.x-panel-header-light-framed-top-ml{background-position:0 top}.x-panel-header-light-framed-top-mr{background-position:right top}.x-panel-header-light-framed-top-tc{background-position:0 0}.x-panel-header-light-framed-top-bc{background-position:0 -5px}.x-panel-header-light-framed-top-tr,.x-panel-header-light-framed-top-br,.x-panel-header-light-framed-top-mr{padding-right:5px}.x-panel-header-light-framed-top-tl,.x-panel-header-light-framed-top-bl,.x-panel-header-light-framed-top-ml{padding-left:5px}.x-panel-header-light-framed-top-tc{height:5px}.x-panel-header-light-framed-top-bc{height:0}.x-panel-header-light-framed-top-tl,.x-panel-header-light-framed-top-bl,.x-panel-header-light-framed-top-tr,.x-panel-header-light-framed-top-br,.x-panel-header-light-framed-top-tc,.x-panel-header-light-framed-top-bc,.x-panel-header-light-framed-top-ml,.x-panel-header-light-framed-top-mr{background-image:url(images/panel-header/panel-header-light-framed-top-corners.gif)}.x-panel-header-light-framed-top-ml,.x-panel-header-light-framed-top-mr{background-image:url(images/panel-header/panel-header-light-framed-top-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-top-mc{padding:5px 5px 5px 5px}.x-panel-header-light-framed-right{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:5px 5px 5px 5px;border-width:5px 5px 5px 0;border-style:solid;background-color:#e0ebf3}.x-panel-header-light-framed-right-mc{background-color:#e0ebf3}.x-nbr .x-panel-header-light-framed-right{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-right-frameInfo{font-family:dh-5-5-5-0-5-5-5-0-5-5-5-5}.x-panel-header-light-framed-right-tl{background-position:0 -10px}.x-panel-header-light-framed-right-tr{background-position:right -15px}.x-panel-header-light-framed-right-bl{background-position:0 -20px}.x-panel-header-light-framed-right-br{background-position:right -25px}.x-panel-header-light-framed-right-ml{background-position:right 0}.x-panel-header-light-framed-right-mr{background-position:right 0}.x-panel-header-light-framed-right-tc{background-position:0 0}.x-panel-header-light-framed-right-bc{background-position:0 -5px}.x-panel-header-light-framed-right-tr,.x-panel-header-light-framed-right-br,.x-panel-header-light-framed-right-mr{padding-right:5px}.x-panel-header-light-framed-right-tl,.x-panel-header-light-framed-right-bl,.x-panel-header-light-framed-right-ml{padding-left:0}.x-panel-header-light-framed-right-tc{height:5px}.x-panel-header-light-framed-right-bc{height:5px}.x-panel-header-light-framed-right-tl,.x-panel-header-light-framed-right-bl,.x-panel-header-light-framed-right-tr,.x-panel-header-light-framed-right-br,.x-panel-header-light-framed-right-tc,.x-panel-header-light-framed-right-bc,.x-panel-header-light-framed-right-ml,.x-panel-header-light-framed-right-mr{background-image:url(images/panel-header/panel-header-light-framed-right-corners.gif)}.x-panel-header-light-framed-right-ml,.x-panel-header-light-framed-right-mr{background-image:url(images/panel-header/panel-header-light-framed-right-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-right-mc{padding:5px 5px 5px 5px}.x-panel-header-light-framed-bottom{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:0 5px 5px 5px;border-style:solid;background-color:#e0ebf3}.x-panel-header-light-framed-bottom-mc{background-color:#e0ebf3}.x-nbr .x-panel-header-light-framed-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-bottom-frameInfo{font-family:dh-0-5-5-5-0-5-5-5-5-5-5-5}.x-panel-header-light-framed-bottom-tl{background-position:0 -10px}.x-panel-header-light-framed-bottom-tr{background-position:right -15px}.x-panel-header-light-framed-bottom-bl{background-position:0 -20px}.x-panel-header-light-framed-bottom-br{background-position:right -25px}.x-panel-header-light-framed-bottom-ml{background-position:0 bottom}.x-panel-header-light-framed-bottom-mr{background-position:right bottom}.x-panel-header-light-framed-bottom-tc{background-position:0 0}.x-panel-header-light-framed-bottom-bc{background-position:0 -5px}.x-panel-header-light-framed-bottom-tr,.x-panel-header-light-framed-bottom-br,.x-panel-header-light-framed-bottom-mr{padding-right:5px}.x-panel-header-light-framed-bottom-tl,.x-panel-header-light-framed-bottom-bl,.x-panel-header-light-framed-bottom-ml{padding-left:5px}.x-panel-header-light-framed-bottom-tc{height:0}.x-panel-header-light-framed-bottom-bc{height:5px}.x-panel-header-light-framed-bottom-tl,.x-panel-header-light-framed-bottom-bl,.x-panel-header-light-framed-bottom-tr,.x-panel-header-light-framed-bottom-br,.x-panel-header-light-framed-bottom-tc,.x-panel-header-light-framed-bottom-bc,.x-panel-header-light-framed-bottom-ml,.x-panel-header-light-framed-bottom-mr{background-image:url(images/panel-header/panel-header-light-framed-bottom-corners.gif)}.x-panel-header-light-framed-bottom-ml,.x-panel-header-light-framed-bottom-mr{background-image:url(images/panel-header/panel-header-light-framed-bottom-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-bottom-mc{padding:5px 5px 5px 5px}.x-panel-header-light-framed-left{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px 0 5px 5px;border-style:solid;background-color:#e0ebf3}.x-panel-header-light-framed-left-mc{background-color:#e0ebf3}.x-nbr .x-panel-header-light-framed-left{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-left-frameInfo{font-family:dh-5-0-5-5-5-0-5-5-5-5-5-5}.x-panel-header-light-framed-left-tl{background-position:0 -10px}.x-panel-header-light-framed-left-tr{background-position:right -15px}.x-panel-header-light-framed-left-bl{background-position:0 -20px}.x-panel-header-light-framed-left-br{background-position:right -25px}.x-panel-header-light-framed-left-ml{background-position:left 0}.x-panel-header-light-framed-left-mr{background-position:left 0}.x-panel-header-light-framed-left-tc{background-position:0 0}.x-panel-header-light-framed-left-bc{background-position:0 -5px}.x-panel-header-light-framed-left-tr,.x-panel-header-light-framed-left-br,.x-panel-header-light-framed-left-mr{padding-right:0}.x-panel-header-light-framed-left-tl,.x-panel-header-light-framed-left-bl,.x-panel-header-light-framed-left-ml{padding-left:5px}.x-panel-header-light-framed-left-tc{height:5px}.x-panel-header-light-framed-left-bc{height:5px}.x-panel-header-light-framed-left-tl,.x-panel-header-light-framed-left-bl,.x-panel-header-light-framed-left-tr,.x-panel-header-light-framed-left-br,.x-panel-header-light-framed-left-tc,.x-panel-header-light-framed-left-bc,.x-panel-header-light-framed-left-ml,.x-panel-header-light-framed-left-mr{background-image:url(images/panel-header/panel-header-light-framed-left-corners.gif)}.x-panel-header-light-framed-left-ml,.x-panel-header-light-framed-left-mr{background-image:url(images/panel-header/panel-header-light-framed-left-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-left-mc{padding:5px 5px 5px 5px}.x-panel-header-light-framed-collapsed-top{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#e0ebf3}.x-panel-header-light-framed-collapsed-top-mc{background-color:#e0ebf3}.x-nbr .x-panel-header-light-framed-collapsed-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-collapsed-top-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-panel-header-light-framed-collapsed-top-tl{background-position:0 -10px}.x-panel-header-light-framed-collapsed-top-tr{background-position:right -15px}.x-panel-header-light-framed-collapsed-top-bl{background-position:0 -20px}.x-panel-header-light-framed-collapsed-top-br{background-position:right -25px}.x-panel-header-light-framed-collapsed-top-ml{background-position:0 top}.x-panel-header-light-framed-collapsed-top-mr{background-position:right top}.x-panel-header-light-framed-collapsed-top-tc{background-position:0 0}.x-panel-header-light-framed-collapsed-top-bc{background-position:0 -5px}.x-panel-header-light-framed-collapsed-top-tr,.x-panel-header-light-framed-collapsed-top-br,.x-panel-header-light-framed-collapsed-top-mr{padding-right:5px}.x-panel-header-light-framed-collapsed-top-tl,.x-panel-header-light-framed-collapsed-top-bl,.x-panel-header-light-framed-collapsed-top-ml{padding-left:5px}.x-panel-header-light-framed-collapsed-top-tc{height:5px}.x-panel-header-light-framed-collapsed-top-bc{height:5px}.x-panel-header-light-framed-collapsed-top-tl,.x-panel-header-light-framed-collapsed-top-bl,.x-panel-header-light-framed-collapsed-top-tr,.x-panel-header-light-framed-collapsed-top-br,.x-panel-header-light-framed-collapsed-top-tc,.x-panel-header-light-framed-collapsed-top-bc,.x-panel-header-light-framed-collapsed-top-ml,.x-panel-header-light-framed-collapsed-top-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-top-corners.gif)}.x-panel-header-light-framed-collapsed-top-ml,.x-panel-header-light-framed-collapsed-top-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-top-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-collapsed-top-mc{padding:5px 5px 5px 5px}.x-panel-header-light-framed-collapsed-right{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#e0ebf3}.x-panel-header-light-framed-collapsed-right-mc{background-color:#e0ebf3}.x-nbr .x-panel-header-light-framed-collapsed-right{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-collapsed-right-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-panel-header-light-framed-collapsed-right-tl{background-position:0 -10px}.x-panel-header-light-framed-collapsed-right-tr{background-position:right -15px}.x-panel-header-light-framed-collapsed-right-bl{background-position:0 -20px}.x-panel-header-light-framed-collapsed-right-br{background-position:right -25px}.x-panel-header-light-framed-collapsed-right-ml{background-position:right 0}.x-panel-header-light-framed-collapsed-right-mr{background-position:right 0}.x-panel-header-light-framed-collapsed-right-tc{background-position:0 0}.x-panel-header-light-framed-collapsed-right-bc{background-position:0 -5px}.x-panel-header-light-framed-collapsed-right-tr,.x-panel-header-light-framed-collapsed-right-br,.x-panel-header-light-framed-collapsed-right-mr{padding-right:5px}.x-panel-header-light-framed-collapsed-right-tl,.x-panel-header-light-framed-collapsed-right-bl,.x-panel-header-light-framed-collapsed-right-ml{padding-left:5px}.x-panel-header-light-framed-collapsed-right-tc{height:5px}.x-panel-header-light-framed-collapsed-right-bc{height:5px}.x-panel-header-light-framed-collapsed-right-tl,.x-panel-header-light-framed-collapsed-right-bl,.x-panel-header-light-framed-collapsed-right-tr,.x-panel-header-light-framed-collapsed-right-br,.x-panel-header-light-framed-collapsed-right-tc,.x-panel-header-light-framed-collapsed-right-bc,.x-panel-header-light-framed-collapsed-right-ml,.x-panel-header-light-framed-collapsed-right-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-right-corners.gif)}.x-panel-header-light-framed-collapsed-right-ml,.x-panel-header-light-framed-collapsed-right-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-right-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-collapsed-right-mc{padding:5px 5px 5px 5px}.x-panel-header-light-framed-collapsed-bottom{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#e0ebf3}.x-panel-header-light-framed-collapsed-bottom-mc{background-color:#e0ebf3}.x-nbr .x-panel-header-light-framed-collapsed-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-collapsed-bottom-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-panel-header-light-framed-collapsed-bottom-tl{background-position:0 -10px}.x-panel-header-light-framed-collapsed-bottom-tr{background-position:right -15px}.x-panel-header-light-framed-collapsed-bottom-bl{background-position:0 -20px}.x-panel-header-light-framed-collapsed-bottom-br{background-position:right -25px}.x-panel-header-light-framed-collapsed-bottom-ml{background-position:0 bottom}.x-panel-header-light-framed-collapsed-bottom-mr{background-position:right bottom}.x-panel-header-light-framed-collapsed-bottom-tc{background-position:0 0}.x-panel-header-light-framed-collapsed-bottom-bc{background-position:0 -5px}.x-panel-header-light-framed-collapsed-bottom-tr,.x-panel-header-light-framed-collapsed-bottom-br,.x-panel-header-light-framed-collapsed-bottom-mr{padding-right:5px}.x-panel-header-light-framed-collapsed-bottom-tl,.x-panel-header-light-framed-collapsed-bottom-bl,.x-panel-header-light-framed-collapsed-bottom-ml{padding-left:5px}.x-panel-header-light-framed-collapsed-bottom-tc{height:5px}.x-panel-header-light-framed-collapsed-bottom-bc{height:5px}.x-panel-header-light-framed-collapsed-bottom-tl,.x-panel-header-light-framed-collapsed-bottom-bl,.x-panel-header-light-framed-collapsed-bottom-tr,.x-panel-header-light-framed-collapsed-bottom-br,.x-panel-header-light-framed-collapsed-bottom-tc,.x-panel-header-light-framed-collapsed-bottom-bc,.x-panel-header-light-framed-collapsed-bottom-ml,.x-panel-header-light-framed-collapsed-bottom-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif)}.x-panel-header-light-framed-collapsed-bottom-ml,.x-panel-header-light-framed-collapsed-bottom-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-collapsed-bottom-mc{padding:5px 5px 5px 5px}.x-panel-header-light-framed-collapsed-left{-moz-border-radius-topleft:4px;-webkit-border-top-left-radius:4px;border-top-left-radius:4px;-moz-border-radius-topright:4px;-webkit-border-top-right-radius:4px;border-top-right-radius:4px;-moz-border-radius-bottomright:4px;-webkit-border-bottom-right-radius:4px;border-bottom-right-radius:4px;-moz-border-radius-bottomleft:4px;-webkit-border-bottom-left-radius:4px;border-bottom-left-radius:4px;padding:5px 5px 5px 5px;border-width:5px;border-style:solid;background-color:#e0ebf3}.x-panel-header-light-framed-collapsed-left-mc{background-color:#e0ebf3}.x-nbr .x-panel-header-light-framed-collapsed-left{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-collapsed-left-frameInfo{font-family:dh-5-5-5-5-5-5-5-5-5-5-5-5}.x-panel-header-light-framed-collapsed-left-tl{background-position:0 -10px}.x-panel-header-light-framed-collapsed-left-tr{background-position:right -15px}.x-panel-header-light-framed-collapsed-left-bl{background-position:0 -20px}.x-panel-header-light-framed-collapsed-left-br{background-position:right -25px}.x-panel-header-light-framed-collapsed-left-ml{background-position:left 0}.x-panel-header-light-framed-collapsed-left-mr{background-position:left 0}.x-panel-header-light-framed-collapsed-left-tc{background-position:0 0}.x-panel-header-light-framed-collapsed-left-bc{background-position:0 -5px}.x-panel-header-light-framed-collapsed-left-tr,.x-panel-header-light-framed-collapsed-left-br,.x-panel-header-light-framed-collapsed-left-mr{padding-right:5px}.x-panel-header-light-framed-collapsed-left-tl,.x-panel-header-light-framed-collapsed-left-bl,.x-panel-header-light-framed-collapsed-left-ml{padding-left:5px}.x-panel-header-light-framed-collapsed-left-tc{height:5px}.x-panel-header-light-framed-collapsed-left-bc{height:5px}.x-panel-header-light-framed-collapsed-left-tl,.x-panel-header-light-framed-collapsed-left-bl,.x-panel-header-light-framed-collapsed-left-tr,.x-panel-header-light-framed-collapsed-left-br,.x-panel-header-light-framed-collapsed-left-tc,.x-panel-header-light-framed-collapsed-left-bc,.x-panel-header-light-framed-collapsed-left-ml,.x-panel-header-light-framed-collapsed-left-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-left-corners.gif)}.x-panel-header-light-framed-collapsed-left-ml,.x-panel-header-light-framed-collapsed-left-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-left-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-collapsed-left-mc{padding:5px 5px 5px 5px}.x-panel .x-panel-header-light-framed-top{border-bottom-width:5px !important}.x-panel .x-panel-header-light-framed-right{border-left-width:5px !important}.x-panel .x-panel-header-light-framed-bottom{border-top-width:5px !important}.x-panel .x-panel-header-light-framed-left{border-right-width:5px !important}.x-nbr .x-panel-header-light-framed-collapsed-top{border-bottom-width:0 !important}.x-nbr .x-panel-header-light-framed-collapsed-right{border-left-width:0 !important}.x-nbr .x-panel-header-light-framed-collapsed-bottom{border-top-width:0 !important}.x-nbr .x-panel-header-light-framed-collapsed-left{border-right-width:0 !important}.x-panel-header-light-framed-horizontal .x-tool-after-title{margin:0 0 0 6px}.x-panel-header-light-framed-horizontal .x-tool-before-title{margin:0 6px 0 0}.x-panel-header-light-framed-vertical .x-tool-after-title{margin:6px 0 0 0}.x-panel-header-light-framed-vertical .x-tool-before-title{margin:0 0 6px 0}.x-keyboard-mode .x-panel-header-light-framed .x-tool-focus{outline:1px solid #157fcc;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus,.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus,.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after,.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #157fcc;pointer-events:none}.x-panel-light-framed-resizable{overflow:visible}.x-panel-light-framed-resizable .x-panel-handle{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-panel-light-framed-resizable .x-panel-handle-north-br{top:-5px}.x-panel-light-framed-resizable .x-panel-handle-south-br{bottom:-5px}.x-panel-light-framed-resizable .x-panel-handle-east-br{right:-5px}.x-panel-light-framed-resizable .x-panel-handle-west-br{left:-5px}.x-panel-light-framed-resizable .x-panel-handle-northwest-br{left:-5px;top:-5px}.x-panel-light-framed-resizable .x-panel-handle-northeast-br{right:-5px;top:-5px}.x-panel-light-framed-resizable .x-panel-handle-southeast-br{right:-5px;bottom:-5px}.x-panel-light-framed-resizable .x-panel-handle-southwest-br{left:-5px;bottom:-5px}.x-panel-light-framed-outer-border-l{border-left-color:#e0ebf3 !important;border-left-width:5px !important}.x-panel-light-framed-outer-border-b{border-bottom-color:#e0ebf3 !important;border-bottom-width:5px !important}.x-panel-light-framed-outer-border-bl{border-bottom-color:#e0ebf3 !important;border-bottom-width:5px !important;border-left-color:#e0ebf3 !important;border-left-width:5px !important}.x-panel-light-framed-outer-border-r{border-right-color:#e0ebf3 !important;border-right-width:5px !important}.x-panel-light-framed-outer-border-rl{border-right-color:#e0ebf3 !important;border-right-width:5px !important;border-left-color:#e0ebf3 !important;border-left-width:5px !important}.x-panel-light-framed-outer-border-rb{border-right-color:#e0ebf3 !important;border-right-width:5px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:5px !important}.x-panel-light-framed-outer-border-rbl{border-right-color:#e0ebf3 !important;border-right-width:5px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:5px !important;border-left-color:#e0ebf3 !important;border-left-width:5px !important}.x-panel-light-framed-outer-border-t{border-top-color:#e0ebf3 !important;border-top-width:5px !important}.x-panel-light-framed-outer-border-tl{border-top-color:#e0ebf3 !important;border-top-width:5px !important;border-left-color:#e0ebf3 !important;border-left-width:5px !important}.x-panel-light-framed-outer-border-tb{border-top-color:#e0ebf3 !important;border-top-width:5px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:5px !important}.x-panel-light-framed-outer-border-tbl{border-top-color:#e0ebf3 !important;border-top-width:5px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:5px !important;border-left-color:#e0ebf3 !important;border-left-width:5px !important}.x-panel-light-framed-outer-border-tr{border-top-color:#e0ebf3 !important;border-top-width:5px !important;border-right-color:#e0ebf3 !important;border-right-width:5px !important}.x-panel-light-framed-outer-border-trl{border-top-color:#e0ebf3 !important;border-top-width:5px !important;border-right-color:#e0ebf3 !important;border-right-width:5px !important;border-left-color:#e0ebf3 !important;border-left-width:5px !important}.x-panel-light-framed-outer-border-trb{border-top-color:#e0ebf3 !important;border-top-width:5px !important;border-right-color:#e0ebf3 !important;border-right-width:5px !important;border-bottom-color:#e0ebf3 !important;border-bottom-width:5px !important}.x-panel-light-framed-outer-border-trbl{border-color:#e0ebf3 !important;border-width:5px !important}.x-form-file-wrap .x-form-trigger-wrap{border:0}.x-form-file-wrap .x-form-trigger-wrap .x-form-text{border:1px solid;border-color:#c2c2c2 #dadada #dadada;height:24px}.x-form-file-wrap .x-form-trigger-wrap .x-form-text.x-form-invalid-field{border-color:#cf4c35}.x-html-editor-container{border:1px solid;border-color:#c2c2c2 #dadada #dadada}.x-grid-header-ct{border:1px solid #c2c2c2}.x-column-header-trigger{background-color:#eff6fb;border-left:1px solid #c2c2c2}.x-column-header-last{border-right-width:0}.x-column-header-last .x-column-header-over .x-column-header-trigger{border-right:1px solid #c2c2c2}.x-resizable-handle{background-repeat:no-repeat}.x-resizable-handle-east-over,.x-resizable-handle-west-over{background-position:center}.x-resizable-handle-south-over,.x-resizable-handle-north-over{background-position:center}.x-resizable-handle-southeast-over{background-position:-2px -2px}.x-resizable-handle-northwest-over{background-position:2px 2px}.x-resizable-handle-northeast-over{background-position:-2px 2px}.x-resizable-handle-southwest-over{background-position:2px -2px}.x-resizable-pinned .x-resizable-handle-east,.x-resizable-pinned .x-resizable-handle-west{background-position:center}.x-resizable-pinned .x-resizable-handle-south,.x-resizable-pinned .x-resizable-handle-north{background-position:center}.x-resizable-pinned .x-resizable-handle-southeast{background-position:-2px -2px}.x-resizable-pinned .x-resizable-handle-northwest{background-position:2px 2px}.x-resizable-pinned .x-resizable-handle-northeast{background-position:-2px 2px}.x-resizable-pinned .x-resizable-handle-southwest{background-position:2px -2px} \ No newline at end of file diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/Readme.md b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/Readme.md new file mode 100644 index 0000000..4d76a0f --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/Readme.md @@ -0,0 +1,3 @@ +# theme-neutral/resources + +This folder contains static resources (typically an `"images"` folder as well). diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/magnify.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/magnify.png new file mode 100644 index 0000000..b807c42 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/magnify.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/fade-blue.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/fade-blue.png new file mode 100644 index 0000000..4dbf08b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/fade-blue.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/fader.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/fader.png new file mode 100644 index 0000000..be8c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/fader.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/icon16_error.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/icon16_error.png new file mode 100644 index 0000000..5f168d3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/icon16_error.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/icon16_info.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/icon16_info.png new file mode 100644 index 0000000..6c6b32d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/resources/theme-neutral/images/window/toast/icon16_info.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/theme-neptune-debug.js b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/theme-neptune-debug.js new file mode 100644 index 0000000..bf5770b --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/theme-neptune-debug.js @@ -0,0 +1,397 @@ +Ext.define('Ext.theme.neptune.Component', { + override: 'Ext.Component', + initComponent: function() { + this.callParent(); + if (this.dock && this.border === undefined) { + this.border = false; + } + }, + privates: { + initStyles: function() { + var me = this, + hasOwnBorder = me.hasOwnProperty('border'), + border = me.border; + if (me.dock) { + // prevent the superclass method from setting the border style. We want to + // allow dock layout to decide which borders to suppress. + me.border = null; + } + me.callParent(arguments); + if (hasOwnBorder) { + me.border = border; + } else { + delete me.border; + } + } + } +}, function() { + Ext.namespace('Ext.theme.is').Neptune = true; + Ext.theme.name = 'Neptune'; +}); + +Ext.define('Ext.theme.neptune.resizer.Splitter', { + override: 'Ext.resizer.Splitter', + size: 8 +}); + +Ext.define('Ext.theme.neptune.toolbar.Toolbar', { + override: 'Ext.toolbar.Toolbar', + usePlainButtons: false, + border: false +}); + +Ext.define('Ext.theme.neptune.layout.component.Dock', { + override: 'Ext.layout.component.Dock', + /** + * This table contains the border removal classes indexed by the sum of the edges to + * remove. Each edge is assigned a value: + * + * * `left` = 1 + * * `bottom` = 2 + * * `right` = 4 + * * `top` = 8 + * + * @private + */ + noBorderClassTable: [ + 0, + // TRBL + Ext.baseCSSPrefix + 'noborder-l', + // 0001 = 1 + Ext.baseCSSPrefix + 'noborder-b', + // 0010 = 2 + Ext.baseCSSPrefix + 'noborder-bl', + // 0011 = 3 + Ext.baseCSSPrefix + 'noborder-r', + // 0100 = 4 + Ext.baseCSSPrefix + 'noborder-rl', + // 0101 = 5 + Ext.baseCSSPrefix + 'noborder-rb', + // 0110 = 6 + Ext.baseCSSPrefix + 'noborder-rbl', + // 0111 = 7 + Ext.baseCSSPrefix + 'noborder-t', + // 1000 = 8 + Ext.baseCSSPrefix + 'noborder-tl', + // 1001 = 9 + Ext.baseCSSPrefix + 'noborder-tb', + // 1010 = 10 + Ext.baseCSSPrefix + 'noborder-tbl', + // 1011 = 11 + Ext.baseCSSPrefix + 'noborder-tr', + // 1100 = 12 + Ext.baseCSSPrefix + 'noborder-trl', + // 1101 = 13 + Ext.baseCSSPrefix + 'noborder-trb', + // 1110 = 14 + Ext.baseCSSPrefix + 'noborder-trbl' + ], + // 1111 = 15 + /** + * The numeric values assigned to each edge indexed by the `dock` config value. + * @private + */ + edgeMasks: { + top: 8, + right: 4, + bottom: 2, + left: 1 + }, + handleItemBorders: function() { + var me = this, + edges = 0, + maskT = 8, + maskR = 4, + maskB = 2, + maskL = 1, + owner = me.owner, + bodyBorder = owner.bodyBorder, + ownerBorder = owner.border, + collapsed = me.collapsed, + edgeMasks = me.edgeMasks, + noBorderCls = me.noBorderClassTable, + dockedItemsGen = owner.dockedItems.generation, + b, borderCls, docked, edgesTouched, i, ln, item, dock, lastValue, mask, addCls, removeCls; + if (me.initializedBorders === dockedItemsGen) { + return; + } + addCls = []; + removeCls = []; + borderCls = me.getBorderCollapseTable(); + noBorderCls = me.getBorderClassTable ? me.getBorderClassTable() : noBorderCls; + me.initializedBorders = dockedItemsGen; + // Borders have to be calculated using expanded docked item collection. + me.collapsed = false; + docked = me.getDockedItems('visual'); + me.collapsed = collapsed; + for (i = 0 , ln = docked.length; i < ln; i++) { + item = docked[i]; + if (item.ignoreBorderManagement) { + // headers in framed panels ignore border management, so we do not want + // to set "satisfied" on the edge in question + + continue; + } + dock = item.dock; + mask = edgesTouched = 0; + addCls.length = 0; + removeCls.length = 0; + if (dock !== 'bottom') { + if (edges & maskT) { + // if (not touching the top edge) + b = item.border; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskT; + } + } + if (b === false) { + mask += maskT; + } + } + if (dock !== 'left') { + if (edges & maskR) { + // if (not touching the right edge) + b = item.border; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskR; + } + } + if (b === false) { + mask += maskR; + } + } + if (dock !== 'top') { + if (edges & maskB) { + // if (not touching the bottom edge) + b = item.border; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskB; + } + } + if (b === false) { + mask += maskB; + } + } + if (dock !== 'right') { + if (edges & maskL) { + // if (not touching the left edge) + b = item.border; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskL; + } + } + if (b === false) { + mask += maskL; + } + } + if ((lastValue = item.lastBorderMask) !== mask) { + item.lastBorderMask = mask; + if (lastValue) { + removeCls[0] = noBorderCls[lastValue]; + } + if (mask) { + addCls[0] = noBorderCls[mask]; + } + } + if ((lastValue = item.lastBorderCollapse) !== edgesTouched) { + item.lastBorderCollapse = edgesTouched; + if (lastValue) { + removeCls[removeCls.length] = borderCls[lastValue]; + } + if (edgesTouched) { + addCls[addCls.length] = borderCls[edgesTouched]; + } + } + if (removeCls.length) { + item.removeCls(removeCls); + } + if (addCls.length) { + item.addCls(addCls); + } + // mask can use += but edges must use |= because there can be multiple items + // on an edge but the mask is reset per item + edges |= edgeMasks[dock]; + } + // = T, R, B or L (8, 4, 2 or 1) + mask = edgesTouched = 0; + addCls.length = 0; + removeCls.length = 0; + if (edges & maskT) { + // if (not touching the top edge) + b = bodyBorder; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskT; + } + } + if (b === false) { + mask += maskT; + } + if (edges & maskR) { + // if (not touching the right edge) + b = bodyBorder; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskR; + } + } + if (b === false) { + mask += maskR; + } + if (edges & maskB) { + // if (not touching the bottom edge) + b = bodyBorder; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskB; + } + } + if (b === false) { + mask += maskB; + } + if (edges & maskL) { + // if (not touching the left edge) + b = bodyBorder; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskL; + } + } + if (b === false) { + mask += maskL; + } + if ((lastValue = me.lastBodyBorderMask) !== mask) { + me.lastBodyBorderMask = mask; + if (lastValue) { + removeCls[0] = noBorderCls[lastValue]; + } + if (mask) { + addCls[0] = noBorderCls[mask]; + } + } + if ((lastValue = me.lastBodyBorderCollapse) !== edgesTouched) { + me.lastBodyBorderCollapse = edgesTouched; + if (lastValue) { + removeCls[removeCls.length] = borderCls[lastValue]; + } + if (edgesTouched) { + addCls[addCls.length] = borderCls[edgesTouched]; + } + } + if (removeCls.length) { + owner.removeBodyCls(removeCls); + } + if (addCls.length) { + owner.addBodyCls(addCls); + } + }, + onRemove: function(item) { + var me = this, + lastBorderMask = item.lastBorderMask, + lastBorderCollapse = item.lastBorderCollapse; + if (!item.destroyed && !item.ignoreBorderManagement) { + if (lastBorderMask) { + item.lastBorderMask = 0; + item.removeCls(me.noBorderClassTable[lastBorderMask]); + } + if (lastBorderCollapse) { + item.lastBorderCollapse = 0; + item.removeCls(me.getBorderCollapseTable()[lastBorderCollapse]); + } + } + me.callParent([ + item + ]); + } +}); + +Ext.define('Ext.theme.neptune.panel.Panel', { + override: 'Ext.panel.Panel', + border: false, + bodyBorder: false, + initBorderProps: Ext.emptyFn, + initBodyBorder: function() { + // The superclass method converts a truthy bodyBorder into a number and sets + // an inline border-width style on the body element. This prevents that from + // happening if borderBody === true so that the body will get its border-width + // the stylesheet. + if (this.bodyBorder !== true) { + this.callParent(); + } + } +}); + +Ext.define('Ext.theme.neptune.container.ButtonGroup', { + override: 'Ext.container.ButtonGroup', + usePlainButtons: false +}); + +Ext.define('Ext.theme.neptune.toolbar.Paging', { + override: 'Ext.toolbar.Paging', + defaultButtonUI: 'plain-toolbar', + inputItemWidth: 40 +}); + +Ext.define('Ext.theme.neptune.picker.Month', { + override: 'Ext.picker.Month', + // Monthpicker contains logic that reduces the margins of the month items if it detects + // that the text has wrapped. This can happen in the classic theme in certain + // locales such as zh_TW. In order to work around this, Month picker measures + // the month items to see if the height is greater than "measureMaxHeight". + // In neptune the height of the items is larger, so we must increase this value. + // While the actual height of the month items in neptune is 24px, we will only + // determine that the text has wrapped if the height of the item exceeds 36px. + // this allows theme developers some leeway to increase the month item size in + // a neptune-derived theme. + measureMaxHeight: 36 +}); + +Ext.define('Ext.theme.neptune.form.field.HtmlEditor', { + override: 'Ext.form.field.HtmlEditor', + defaultButtonUI: 'plain-toolbar' +}); + +Ext.define('Ext.theme.neptune.panel.Table', { + override: 'Ext.panel.Table', + lockableBodyBorder: true, + initComponent: function() { + var me = this; + me.callParent(); + if (!me.hasOwnProperty('bodyBorder') && !me.hideHeaders && (me.lockableBodyBorder || !me.lockable)) { + me.bodyBorder = true; + } + } +}); + +Ext.define('Ext.theme.neptune.grid.RowEditor', { + override: 'Ext.grid.RowEditor', + buttonUI: 'default-toolbar' +}); + +Ext.define('Ext.theme.neptune.grid.column.RowNumberer', { + override: 'Ext.grid.column.RowNumberer', + width: 25 +}); + +Ext.define('Ext.theme.neptune.menu.Separator', { + override: 'Ext.menu.Separator', + border: true +}); + +Ext.define('Ext.theme.neptune.menu.Menu', { + override: 'Ext.menu.Menu', + showSeparator: false +}); + diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/theme-neptune.js b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/theme-neptune.js new file mode 100644 index 0000000..313d61d --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-neptune/theme-neptune.js @@ -0,0 +1 @@ +Ext.define('Ext.theme.neptune.Component',{override:'Ext.Component',initComponent:function(){this.callParent();if(this.dock&&this.border===undefined){this.border=!1}},privates:{initStyles:function(){var a=this,b=a.hasOwnProperty('border'),c=a.border;if(a.dock){a.border=null}a.callParent(arguments);if(b){a.border=c}else {delete a.border}}}},function(){Ext.namespace('Ext.theme.is').Neptune=!0;Ext.theme.name='Neptune'});Ext.define('Ext.theme.neptune.resizer.Splitter',{override:'Ext.resizer.Splitter',size:8});Ext.define('Ext.theme.neptune.toolbar.Toolbar',{override:'Ext.toolbar.Toolbar',usePlainButtons:!1,border:!1});Ext.define('Ext.theme.neptune.layout.component.Dock',{override:'Ext.layout.component.Dock',noBorderClassTable:[0,Ext.baseCSSPrefix+'noborder-l',Ext.baseCSSPrefix+'noborder-b',Ext.baseCSSPrefix+'noborder-bl',Ext.baseCSSPrefix+'noborder-r',Ext.baseCSSPrefix+'noborder-rl',Ext.baseCSSPrefix+'noborder-rb',Ext.baseCSSPrefix+'noborder-rbl',Ext.baseCSSPrefix+'noborder-t',Ext.baseCSSPrefix+'noborder-tl',Ext.baseCSSPrefix+'noborder-tb',Ext.baseCSSPrefix+'noborder-tbl',Ext.baseCSSPrefix+'noborder-tr',Ext.baseCSSPrefix+'noborder-trl',Ext.baseCSSPrefix+'noborder-trb',Ext.baseCSSPrefix+'noborder-trbl'],edgeMasks:{top:8,right:4,bottom:2,left:1},handleItemBorders:function(){var d=this,i=0,o=8,n=4,l=2,m=1,r=d.owner,s=r.bodyBorder,j=r.border,x=d.collapsed,y=d.edgeMasks,k=d.noBorderClassTable,v=r.dockedItems.generation,a,q,u,b,t,w,g,p,h,c,f,e;if(d.initializedBorders===v){return}f=[];e=[];q=d.getBorderCollapseTable();k=d.getBorderClassTable?d.getBorderClassTable():k;d.initializedBorders=v;d.collapsed=!1;u=d.getDockedItems('visual');d.collapsed=x;for(t=0,w=u.length;t + + + +Created by FontForge 20120731 at Mon Oct 24 17:37:40 2016 + By ,,, +Copyright Dave Gandy 2016. All rights reserved. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.ttf new file mode 100644 index 0000000..35acda2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.woff b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.woff new file mode 100644 index 0000000..400014a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.woff differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.woff2 b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.woff2 new file mode 100644 index 0000000..4d13fc6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-awesome/fonts/fontawesome-webfont.woff2 differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.eot b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.eot new file mode 100644 index 0000000..02bb429 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.eot differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.svg b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.svg new file mode 100644 index 0000000..42f4e83 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.svg @@ -0,0 +1,41 @@ + + + +Generated by IcoMoon + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.ttf new file mode 100644 index 0000000..74a8112 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.woff b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.woff new file mode 100644 index 0000000..a794f9a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/font-ext/fonts/ExtJS.woff differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Bold.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Bold.ttf new file mode 100644 index 0000000..fd79d43 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Bold.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-BoldItalic.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-BoldItalic.ttf new file mode 100644 index 0000000..9bc8009 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-BoldItalic.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-ExtraBold.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-ExtraBold.ttf new file mode 100644 index 0000000..21f6f84 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-ExtraBold.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-ExtraBoldItalic.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-ExtraBoldItalic.ttf new file mode 100644 index 0000000..31cb688 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-ExtraBoldItalic.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Italic.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Italic.ttf new file mode 100644 index 0000000..c90da48 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Italic.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Light.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Light.ttf new file mode 100644 index 0000000..0d38189 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Light.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-LightItalic.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-LightItalic.ttf new file mode 100644 index 0000000..68299c4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-LightItalic.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Regular.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Regular.ttf new file mode 100644 index 0000000..db43334 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Regular.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Semibold.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Semibold.ttf new file mode 100644 index 0000000..1a7679e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-Semibold.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-SemiboldItalic.ttf b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-SemiboldItalic.ttf new file mode 100644 index 0000000..59b6d16 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/fonts/OpenSans-SemiboldItalic.ttf differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow-open-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow-open-rtl.png new file mode 100644 index 0000000..d9968ae Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow-open-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow-open.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow-open.png new file mode 100644 index 0000000..04b1132 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow-open.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow-rtl.png new file mode 100644 index 0000000..90f717b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow.png new file mode 100644 index 0000000..51d2861 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-open-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-open-rtl.png new file mode 100644 index 0000000..a8801df Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-open-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-open.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-open.png new file mode 100644 index 0000000..19a6673 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-open.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-over-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-over-rtl.png new file mode 100644 index 0000000..db04b9d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-over-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-over.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-over.png new file mode 100644 index 0000000..5106cdf Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-over.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-rtl.png new file mode 100644 index 0000000..658194b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow.png new file mode 100644 index 0000000..d3d375c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/breadcrumb/default-split-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-corners.gif new file mode 100644 index 0000000..c8f6651 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-notitle-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-notitle-corners.gif new file mode 100644 index 0000000..4a712ba Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-notitle-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-notitle-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-notitle-sides.gif new file mode 100644 index 0000000..88156ca Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-notitle-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-sides.gif new file mode 100644 index 0000000..9228d0a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn-group/btn-group-default-framed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-corners.gif new file mode 100644 index 0000000..e4ae352 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-disabled-corners.gif new file mode 100644 index 0000000..192baa8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-disabled-sides.gif new file mode 100644 index 0000000..fe9ebdb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-corners.gif new file mode 100644 index 0000000..2cf5edb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-over-corners.gif new file mode 100644 index 0000000..5f3e289 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-over-sides.gif new file mode 100644 index 0000000..d6bad24 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-pressed-corners.gif new file mode 100644 index 0000000..d803a4b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-pressed-sides.gif new file mode 100644 index 0000000..7ffb20f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-sides.gif new file mode 100644 index 0000000..42279d9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-over-corners.gif new file mode 100644 index 0000000..4231f6e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-over-sides.gif new file mode 100644 index 0000000..951ed68 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-pressed-corners.gif new file mode 100644 index 0000000..046409f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-pressed-sides.gif new file mode 100644 index 0000000..0973bb7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-sides.gif new file mode 100644 index 0000000..2ae4bed Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-large-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-corners.gif new file mode 100644 index 0000000..e4ae352 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-disabled-corners.gif new file mode 100644 index 0000000..192baa8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-disabled-sides.gif new file mode 100644 index 0000000..fe9ebdb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-corners.gif new file mode 100644 index 0000000..2cf5edb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-over-corners.gif new file mode 100644 index 0000000..5f3e289 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-over-sides.gif new file mode 100644 index 0000000..d6bad24 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-pressed-corners.gif new file mode 100644 index 0000000..d803a4b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-pressed-sides.gif new file mode 100644 index 0000000..7ffb20f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-sides.gif new file mode 100644 index 0000000..42279d9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-over-corners.gif new file mode 100644 index 0000000..4231f6e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-over-sides.gif new file mode 100644 index 0000000..951ed68 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-pressed-corners.gif new file mode 100644 index 0000000..046409f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-pressed-sides.gif new file mode 100644 index 0000000..0973bb7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-sides.gif new file mode 100644 index 0000000..f8f8b81 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-medium-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-corners.gif new file mode 100644 index 0000000..e4ae352 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-disabled-corners.gif new file mode 100644 index 0000000..192baa8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-disabled-sides.gif new file mode 100644 index 0000000..fe9ebdb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-corners.gif new file mode 100644 index 0000000..2cf5edb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-over-corners.gif new file mode 100644 index 0000000..5f3e289 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-over-sides.gif new file mode 100644 index 0000000..d6bad24 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-pressed-corners.gif new file mode 100644 index 0000000..d803a4b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-pressed-sides.gif new file mode 100644 index 0000000..7ffb20f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-sides.gif new file mode 100644 index 0000000..42279d9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-over-corners.gif new file mode 100644 index 0000000..4231f6e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-over-sides.gif new file mode 100644 index 0000000..951ed68 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-pressed-corners.gif new file mode 100644 index 0000000..046409f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-pressed-sides.gif new file mode 100644 index 0000000..0973bb7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-sides.gif new file mode 100644 index 0000000..0b2b180 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-small-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-corners.gif new file mode 100644 index 0000000..ad37011 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-disabled-corners.gif new file mode 100644 index 0000000..56d6218 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-disabled-sides.gif new file mode 100644 index 0000000..de517ca Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-corners.gif new file mode 100644 index 0000000..f23d569 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-over-corners.gif new file mode 100644 index 0000000..bd6917d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-over-sides.gif new file mode 100644 index 0000000..ea3c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-pressed-corners.gif new file mode 100644 index 0000000..b804484 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-pressed-sides.gif new file mode 100644 index 0000000..38745e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-sides.gif new file mode 100644 index 0000000..03350a6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-sides.gif new file mode 100644 index 0000000..6847cc4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-large-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-corners.gif new file mode 100644 index 0000000..ad37011 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-disabled-corners.gif new file mode 100644 index 0000000..56d6218 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-disabled-sides.gif new file mode 100644 index 0000000..de517ca Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-corners.gif new file mode 100644 index 0000000..f23d569 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-over-corners.gif new file mode 100644 index 0000000..bd6917d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-over-sides.gif new file mode 100644 index 0000000..ea3c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif new file mode 100644 index 0000000..b804484 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif new file mode 100644 index 0000000..38745e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-sides.gif new file mode 100644 index 0000000..03350a6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-sides.gif new file mode 100644 index 0000000..7092cbc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-medium-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-corners.gif new file mode 100644 index 0000000..ad37011 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-disabled-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-disabled-corners.gif new file mode 100644 index 0000000..56d6218 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-disabled-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-disabled-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-disabled-sides.gif new file mode 100644 index 0000000..de517ca Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-disabled-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-corners.gif new file mode 100644 index 0000000..f23d569 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-over-corners.gif new file mode 100644 index 0000000..bd6917d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-over-sides.gif new file mode 100644 index 0000000..ea3c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-pressed-corners.gif new file mode 100644 index 0000000..b804484 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-pressed-sides.gif new file mode 100644 index 0000000..38745e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-sides.gif new file mode 100644 index 0000000..03350a6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-focus-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-sides.gif new file mode 100644 index 0000000..d6e6314 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-default-toolbar-small-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-over-corners.gif new file mode 100644 index 0000000..bd6917d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-over-sides.gif new file mode 100644 index 0000000..ea3c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif new file mode 100644 index 0000000..b804484 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif new file mode 100644 index 0000000..38745e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-large-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-over-corners.gif new file mode 100644 index 0000000..bd6917d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-over-sides.gif new file mode 100644 index 0000000..ea3c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif new file mode 100644 index 0000000..b804484 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif new file mode 100644 index 0000000..38745e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-medium-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-over-corners.gif new file mode 100644 index 0000000..bd6917d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-over-sides.gif new file mode 100644 index 0000000..ea3c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif new file mode 100644 index 0000000..b804484 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif new file mode 100644 index 0000000..38745e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-over-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-over-corners.gif new file mode 100644 index 0000000..43583d2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-over-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-over-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-over-sides.gif new file mode 100644 index 0000000..08b322e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-over-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-pressed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-pressed-corners.gif new file mode 100644 index 0000000..17da952 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-pressed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-pressed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-pressed-sides.gif new file mode 100644 index 0000000..9e87438 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/btn/btn-plain-toolbar-small-pressed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-arrow-rtl.png new file mode 100644 index 0000000..76beeab Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-arrow.png new file mode 100644 index 0000000..32674e4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..79677a4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow-b.png new file mode 100644 index 0000000..9f3928a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow-rtl.png new file mode 100644 index 0000000..7985050 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow.png new file mode 100644 index 0000000..06ad27b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-large-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-arrow-rtl.png new file mode 100644 index 0000000..d54d3a0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-arrow.png new file mode 100644 index 0000000..e565db4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..f2fb53b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow-b.png new file mode 100644 index 0000000..ee39ae2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow-rtl.png new file mode 100644 index 0000000..fb11140 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow.png new file mode 100644 index 0000000..c1d1875 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-arrow-rtl.png new file mode 100644 index 0000000..3538445 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-arrow.png new file mode 100644 index 0000000..17a9beb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..2f8b2e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow-b.png new file mode 100644 index 0000000..afd13fb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow-rtl.png new file mode 100644 index 0000000..f59b792 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow.png new file mode 100644 index 0000000..eaffbdc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-arrow-rtl.png new file mode 100644 index 0000000..d8f0151 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-arrow.png new file mode 100644 index 0000000..31fc36e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..379d2d9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow-b.png new file mode 100644 index 0000000..dcfe8ea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow-rtl.png new file mode 100644 index 0000000..612a6b1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow.png new file mode 100644 index 0000000..731b207 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-large-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-arrow-rtl.png new file mode 100644 index 0000000..1648e51 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-arrow.png new file mode 100644 index 0000000..65fdd03 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..8d2232b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow-b.png new file mode 100644 index 0000000..2489479 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow-rtl.png new file mode 100644 index 0000000..c81c5f2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow.png new file mode 100644 index 0000000..0a6857a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-arrow-rtl.png new file mode 100644 index 0000000..8919138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-arrow.png new file mode 100644 index 0000000..b56c2a6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..1142351 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow-b.png new file mode 100644 index 0000000..bb1b08e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow-rtl.png new file mode 100644 index 0000000..9e9e16b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow.png new file mode 100644 index 0000000..9a72857 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/default-toolbar-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-arrow-rtl.png new file mode 100644 index 0000000..3d68e7e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-arrow.png new file mode 100644 index 0000000..17a9beb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-s-arrow-b.png new file mode 100644 index 0000000..afd13fb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-s-arrow-rtl.png new file mode 100644 index 0000000..f59b792 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-s-arrow.png new file mode 100644 index 0000000..eaffbdc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/grid-cell-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-arrow-rtl.png new file mode 100644 index 0000000..d8f0151 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-arrow.png new file mode 100644 index 0000000..31fc36e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..379d2d9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow-b.png new file mode 100644 index 0000000..dcfe8ea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow-rtl.png new file mode 100644 index 0000000..612a6b1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow.png new file mode 100644 index 0000000..731b207 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-large-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-arrow-rtl.png new file mode 100644 index 0000000..1648e51 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-arrow.png new file mode 100644 index 0000000..65fdd03 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..8d2232b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow-b.png new file mode 100644 index 0000000..2489479 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow-rtl.png new file mode 100644 index 0000000..c81c5f2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow.png new file mode 100644 index 0000000..0a6857a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-arrow-rtl.png new file mode 100644 index 0000000..8919138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-arrow.png new file mode 100644 index 0000000..b56c2a6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..1142351 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow-b.png new file mode 100644 index 0000000..bb1b08e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow-rtl.png new file mode 100644 index 0000000..9e9e16b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow.png new file mode 100644 index 0000000..9a72857 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/button/plain-toolbar-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/datepicker/arrow-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/datepicker/arrow-left.png new file mode 100644 index 0000000..fc09f9a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/datepicker/arrow-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/datepicker/arrow-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/datepicker/arrow-right.png new file mode 100644 index 0000000..a22b876 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/datepicker/arrow-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/datepicker/month-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/datepicker/month-arrow.png new file mode 100644 index 0000000..f0b572f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/datepicker/month-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/dd/drop-add.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/dd/drop-add.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/dd/drop-add.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/dd/drop-no.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/dd/drop-no.png new file mode 100644 index 0000000..02e219a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/dd/drop-no.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/dd/drop-yes.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/dd/drop-yes.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/dd/drop-yes.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/editor/tb-sprite.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/editor/tb-sprite.png new file mode 100644 index 0000000..9886118 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/editor/tb-sprite.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/fieldset/collapse-tool.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/fieldset/collapse-tool.png new file mode 100644 index 0000000..97eb83f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/fieldset/collapse-tool.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/checkbox.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/checkbox.png new file mode 100644 index 0000000..fc2709c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/checkbox.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/clear-trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/clear-trigger-rtl.png new file mode 100644 index 0000000..73e1dbe Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/clear-trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/clear-trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/clear-trigger.png new file mode 100644 index 0000000..73e1dbe Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/clear-trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/date-trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/date-trigger-rtl.png new file mode 100644 index 0000000..9489493 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/date-trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/date-trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/date-trigger.png new file mode 100644 index 0000000..9489493 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/date-trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/exclamation.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/exclamation.png new file mode 100644 index 0000000..3e6e3d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/exclamation.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/radio.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/radio.png new file mode 100644 index 0000000..86644bb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/radio.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/search-trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/search-trigger-rtl.png new file mode 100644 index 0000000..15e15f5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/search-trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/search-trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/search-trigger.png new file mode 100644 index 0000000..15e15f5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/search-trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/spinner-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/spinner-rtl.png new file mode 100644 index 0000000..28d140f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/spinner-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/spinner.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/spinner.png new file mode 100644 index 0000000..28d140f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/spinner.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/tag-field-item-close.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/tag-field-item-close.png new file mode 100644 index 0000000..bcb2834 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/tag-field-item-close.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/trigger-rtl.png new file mode 100644 index 0000000..b4e2d5c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/trigger.png new file mode 100644 index 0000000..b4e2d5c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/form/trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif new file mode 100644 index 0000000..4227275 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif new file mode 100644 index 0000000..b0bbe70 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif new file mode 100644 index 0000000..d3c49a2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif new file mode 100644 index 0000000..b0bbe70 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/col-move-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/col-move-bottom.png new file mode 100644 index 0000000..9782219 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/col-move-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/col-move-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/col-move-top.png new file mode 100644 index 0000000..6e28535 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/col-move-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/columns.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/columns.png new file mode 100644 index 0000000..70a5c87 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/columns.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dd-insert-arrow-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dd-insert-arrow-left.png new file mode 100644 index 0000000..e8177d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dd-insert-arrow-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dd-insert-arrow-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dd-insert-arrow-right.png new file mode 100644 index 0000000..d610f9d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dd-insert-arrow-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dirty-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dirty-rtl.png new file mode 100644 index 0000000..5f84122 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dirty-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dirty.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dirty.png new file mode 100644 index 0000000..fc06fdd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/dirty.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/drop-no.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/drop-no.png new file mode 100644 index 0000000..02e219a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/drop-no.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/drop-yes.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/drop-yes.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/drop-yes.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/equals.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/equals.png new file mode 100644 index 0000000..c1060ca Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/equals.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/find.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/find.png new file mode 100644 index 0000000..dbfbc16 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/find.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/greater_than.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/greater_than.png new file mode 100644 index 0000000..be41c9a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/greater_than.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/less_than.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/less_than.png new file mode 100644 index 0000000..80aacdd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/filters/less_than.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/group-by.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/group-by.png new file mode 100644 index 0000000..8508ade Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/group-by.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/group-collapse.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/group-collapse.png new file mode 100644 index 0000000..49fcc4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/group-collapse.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/group-expand.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/group-expand.png new file mode 100644 index 0000000..d65a7df Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/group-expand.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hd-pop.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hd-pop.png new file mode 100644 index 0000000..3ad96ef Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hd-pop.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-asc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-asc.png new file mode 100644 index 0000000..a206d35 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-asc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-desc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-desc.png new file mode 100644 index 0000000..55a714e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-desc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-lock.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-lock.png new file mode 100644 index 0000000..b293e10 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-lock.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-unlock.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-unlock.png new file mode 100644 index 0000000..e9e9df5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/hmenu-unlock.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/loading.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/loading.gif new file mode 100644 index 0000000..81b0f12 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/loading.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-first.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-first.png new file mode 100644 index 0000000..7691f32 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-first.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-last.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-last.png new file mode 100644 index 0000000..49b13d7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-last.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-next.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-next.png new file mode 100644 index 0000000..c3e72ba Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-next.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-prev.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-prev.png new file mode 100644 index 0000000..cace90b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/page-prev.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/pick-button.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/pick-button.png new file mode 100644 index 0000000..acaface Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/pick-button.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/refresh.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/refresh.png new file mode 100644 index 0000000..5320ddd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/refresh.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/sort_asc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/sort_asc.png new file mode 100644 index 0000000..a206d35 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/sort_asc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/sort_desc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/sort_desc.png new file mode 100644 index 0000000..55a714e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/grid/sort_desc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/loadmask/loading.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/loadmask/loading.gif new file mode 100644 index 0000000..8471b4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/loadmask/loading.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/magnify.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/magnify.png new file mode 100644 index 0000000..b807c42 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/magnify.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-checked.png new file mode 100644 index 0000000..4f5157d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-group-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-group-checked.png new file mode 100644 index 0000000..a9f0b80 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-group-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menu-parent-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menu-parent-left.png new file mode 100644 index 0000000..d457564 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menu-parent-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menu-parent.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menu-parent.png new file mode 100644 index 0000000..2d2331e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menu-parent.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-checked.png new file mode 100644 index 0000000..4f5157d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-group-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-group-checked.png new file mode 100644 index 0000000..a9f0b80 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-group-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-menu-parent-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-menu-parent-left.png new file mode 100644 index 0000000..9992618 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-menu-parent-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-menu-parent.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-menu-parent.png new file mode 100644 index 0000000..cb3a569 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-menu-parent.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-scroll-bottom.png new file mode 100644 index 0000000..69c61f6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-scroll-top.png new file mode 100644 index 0000000..ca7e3e1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-unchecked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-unchecked.png new file mode 100644 index 0000000..bce8817 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-menubar-unchecked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-scroll-bottom.png new file mode 100644 index 0000000..d89a459 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-scroll-top.png new file mode 100644 index 0000000..bbbf4af Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-unchecked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-unchecked.png new file mode 100644 index 0000000..bce8817 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/menu/default-unchecked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-bottom-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-bottom-sides.gif new file mode 100644 index 0000000..28f3c3f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif new file mode 100644 index 0000000..28f3c3f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners-rtl.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-left-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners-rtl.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-right-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-top-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-top-sides.gif new file mode 100644 index 0000000..28f3c3f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-collapsed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-left-corners-rtl.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-left-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-left-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-right-corners-rtl.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-right-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-right-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-top-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-top-sides.gif new file mode 100644 index 0000000..28f3c3f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-default-framed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-bottom-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-bottom-sides.gif new file mode 100644 index 0000000..4185518 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif new file mode 100644 index 0000000..4185518 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners-rtl.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-left-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners-rtl.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-right-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-top-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-top-sides.gif new file mode 100644 index 0000000..4185518 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-collapsed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-left-corners-rtl.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-left-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-left-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-right-corners-rtl.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-right-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-right-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-top-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-top-sides.gif new file mode 100644 index 0000000..4185518 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel-header/panel-header-light-framed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-default-framed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-default-framed-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-default-framed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-default-framed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-default-framed-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-default-framed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-light-framed-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-light-framed-corners.gif new file mode 100644 index 0000000..8aa2138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-light-framed-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-light-framed-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-light-framed-sides.gif new file mode 100644 index 0000000..57a02b7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/panel/panel-light-framed-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-error.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-error.png new file mode 100644 index 0000000..458c098 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-error.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-info.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-info.png new file mode 100644 index 0000000..cbccd11 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-info.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-question.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-question.png new file mode 100644 index 0000000..cac922e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-question.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-warning.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-warning.png new file mode 100644 index 0000000..042ca05 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/shared/icon-warning.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/e-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/e-handle.png new file mode 100644 index 0000000..2fe5cb1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/e-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/ne-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/ne-handle.png new file mode 100644 index 0000000..8d8eb63 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/ne-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/nw-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/nw-handle.png new file mode 100644 index 0000000..9835bea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/nw-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/s-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/s-handle.png new file mode 100644 index 0000000..06f914e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/s-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/se-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/se-handle.png new file mode 100644 index 0000000..5a2c695 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/se-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/sw-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/sw-handle.png new file mode 100644 index 0000000..7f68f40 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/sizer/sw-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-bg.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-bg.png new file mode 100644 index 0000000..1ade292 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-bg.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-thumb.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-thumb.png new file mode 100644 index 0000000..d8a03de Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-thumb.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-v-bg.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-v-bg.png new file mode 100644 index 0000000..c24663e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-v-bg.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-v-thumb.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-v-thumb.png new file mode 100644 index 0000000..d8a03de Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/slider/slider-v-thumb.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-more-left.png new file mode 100644 index 0000000..83b0288 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-more.png new file mode 100644 index 0000000..83b0288 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-bottom.png new file mode 100644 index 0000000..813a4d5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-left.png new file mode 100644 index 0000000..9120ea4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-right.png new file mode 100644 index 0000000..67fd5a4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-top.png new file mode 100644 index 0000000..01ad4ee Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-plain-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-bottom.png new file mode 100644 index 0000000..ffff826 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-left.png new file mode 100644 index 0000000..2c35294 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-right.png new file mode 100644 index 0000000..82dfe01 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-top.png new file mode 100644 index 0000000..b2fabfc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab-bar/default-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-active-fbg.gif new file mode 100644 index 0000000..7ab3e2a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-focus-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-focus-active-fbg.gif new file mode 100644 index 0000000..7ab3e2a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-focus-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-bottom-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-close.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-close.png new file mode 100644 index 0000000..46cc89f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-close.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-active-fbg.gif new file mode 100644 index 0000000..e6f77b8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-focus-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-focus-active-fbg.gif new file mode 100644 index 0000000..e6f77b8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-focus-over-fbg.gif new file mode 100644 index 0000000..e11bf81 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-over-fbg.gif new file mode 100644 index 0000000..e11bf81 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-left-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-active-fbg.gif new file mode 100644 index 0000000..e6f77b8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-focus-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-focus-active-fbg.gif new file mode 100644 index 0000000..e6f77b8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-focus-over-fbg.gif new file mode 100644 index 0000000..e11bf81 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-over-fbg.gif new file mode 100644 index 0000000..e11bf81 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-right-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-active-fbg.gif new file mode 100644 index 0000000..7ab3e2a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-focus-active-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-focus-active-fbg.gif new file mode 100644 index 0000000..7ab3e2a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-focus-active-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-focus-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-focus-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-focus-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-over-fbg.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-over-fbg.gif new file mode 100644 index 0000000..48a5a75 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tab/tab-default-top-over-fbg.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-default-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-default-corners.gif new file mode 100644 index 0000000..9c4d49d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-default-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-default-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-default-sides.gif new file mode 100644 index 0000000..b935f3d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-default-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-form-invalid-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-form-invalid-corners.gif new file mode 100644 index 0000000..9c4d49d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-form-invalid-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-form-invalid-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-form-invalid-sides.gif new file mode 100644 index 0000000..b935f3d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tip/tip-form-invalid-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-bottom.png new file mode 100644 index 0000000..6741161 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-top.png new file mode 100644 index 0000000..2a26ba9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/default-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/toolbar/footer-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tools/tool-sprites-dark.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tools/tool-sprites-dark.png new file mode 100644 index 0000000..474088b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tools/tool-sprites-dark.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tools/tool-sprites.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tools/tool-sprites.png new file mode 100644 index 0000000..17fbc0f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tools/tool-sprites.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/arrows-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/arrows-rtl.png new file mode 100644 index 0000000..4aae887 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/arrows-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/arrows.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/arrows.png new file mode 100644 index 0000000..de10dd6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/arrows.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-above.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-above.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-above.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-add.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-add.gif new file mode 100644 index 0000000..b22cd14 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-add.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-add.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-add.png new file mode 100644 index 0000000..c9d24fd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-add.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-append.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-append.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-append.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-below.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-below.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-below.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-between.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-between.gif new file mode 100644 index 0000000..f5a042d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-between.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-between.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-between.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-between.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-no.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-no.gif new file mode 100644 index 0000000..9d9c6a9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-no.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-no.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-no.png new file mode 100644 index 0000000..bb89cfc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-no.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-over.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-over.gif new file mode 100644 index 0000000..2e514e7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-over.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-over.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-over.png new file mode 100644 index 0000000..70d1807 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-over.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-under.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-under.gif new file mode 100644 index 0000000..8535ef4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-under.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-under.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-under.png new file mode 100644 index 0000000..3ba23b3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-under.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-yes.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-yes.gif new file mode 100644 index 0000000..8aacb30 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-yes.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-yes.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-yes.png new file mode 100644 index 0000000..83d0dbc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/drop-yes.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-minus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-minus-rtl.png new file mode 100644 index 0000000..2ffe7b2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-minus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-minus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-minus.png new file mode 100644 index 0000000..b39a71d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-minus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-plus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-plus-rtl.png new file mode 100644 index 0000000..bea9892 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-plus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-plus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-plus.png new file mode 100644 index 0000000..630438f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-plus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-rtl.png new file mode 100644 index 0000000..1d0821b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end.png new file mode 100644 index 0000000..2eb0ed0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-end.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-line-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-line-rtl.png new file mode 100644 index 0000000..e26b768 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-line-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-line.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-line.png new file mode 100644 index 0000000..ac37424 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-line.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus-nl-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus-nl-rtl.png new file mode 100644 index 0000000..1008a54 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus-nl-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus-nl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus-nl.png new file mode 100644 index 0000000..f2a805d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus-nl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus-rtl.png new file mode 100644 index 0000000..cefb704 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus.png new file mode 100644 index 0000000..a256b48 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-minus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus-nl-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus-nl-rtl.png new file mode 100644 index 0000000..e1e6ece Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus-nl-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus-nl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus-nl.png new file mode 100644 index 0000000..3a401ea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus-nl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus-rtl.png new file mode 100644 index 0000000..487f27a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus.png new file mode 100644 index 0000000..03e202a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-plus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-rtl.png new file mode 100644 index 0000000..166e163 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow.png new file mode 100644 index 0000000..4bf9ae5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/elbow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder-open-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder-open-rtl.png new file mode 100644 index 0000000..bb896d8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder-open-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder-open.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder-open.png new file mode 100644 index 0000000..50397da Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder-open.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder-rtl.png new file mode 100644 index 0000000..3b17672 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder.png new file mode 100644 index 0000000..4b02054 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/folder.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/leaf-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/leaf-rtl.png new file mode 100644 index 0000000..b2e6f6e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/leaf-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/leaf.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/leaf.png new file mode 100644 index 0000000..6acb635 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/leaf.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/loading.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/loading.gif new file mode 100644 index 0000000..81b0f12 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/tree/loading.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-bottom.png new file mode 100644 index 0000000..241209e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-left.png new file mode 100644 index 0000000..1c40b78 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-right.png new file mode 100644 index 0000000..505c329 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-top.png new file mode 100644 index 0000000..4a378a3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/util/splitter/mini-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-bottom-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-bottom-sides.gif new file mode 100644 index 0000000..28f3c3f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-bottom-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-bottom-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-bottom-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-bottom-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-bottom-sides.gif new file mode 100644 index 0000000..28f3c3f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-bottom-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-left-corners-rtl.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-left-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-left-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-right-corners-rtl.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-right-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-right-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-top-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-top-sides.gif new file mode 100644 index 0000000..28f3c3f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-collapsed-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-left-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-left-corners-rtl.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-left-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-left-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-left-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-left-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-left-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-left-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-left-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-right-corners-rtl.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-right-corners-rtl.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-right-corners-rtl.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-right-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-right-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-right-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-right-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-right-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-right-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-top-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-top-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-top-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-top-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-top-sides.gif new file mode 100644 index 0000000..28f3c3f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window-header/window-header-default-top-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/fade-blue.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/fade-blue.png new file mode 100644 index 0000000..4dbf08b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/fade-blue.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/fader.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/fader.png new file mode 100644 index 0000000..be8c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/fader.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/icon16_error.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/icon16_error.png new file mode 100644 index 0000000..5f168d3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/icon16_error.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/icon16_info.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/icon16_info.png new file mode 100644 index 0000000..6c6b32d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/toast/icon16_info.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/window-default-corners.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/window-default-corners.gif new file mode 100644 index 0000000..7ec3c06 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/window-default-corners.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/window-default-sides.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/window-default-sides.gif new file mode 100644 index 0000000..bd0ab3e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/images/window/window-default-sides.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-base/Readme.md b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-base/Readme.md new file mode 100644 index 0000000..a0d00c3 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-base/Readme.md @@ -0,0 +1,3 @@ +# theme-base/resources + +This folder contains static resources (typically an `"images"` folder as well). diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/Readme.md b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/Readme.md new file mode 100644 index 0000000..e618474 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/Readme.md @@ -0,0 +1,3 @@ +# theme-neptune/resources + +This folder contains static resources (typically an `"images"` folder as well). diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow-open-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow-open-rtl.png new file mode 100644 index 0000000..d9968ae Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow-open-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow-open.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow-open.png new file mode 100644 index 0000000..04b1132 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow-open.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow-rtl.png new file mode 100644 index 0000000..90f717b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow.png new file mode 100644 index 0000000..51d2861 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-open-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-open-rtl.png new file mode 100644 index 0000000..a8801df Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-open-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-open.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-open.png new file mode 100644 index 0000000..19a6673 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-open.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-over-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-over-rtl.png new file mode 100644 index 0000000..db04b9d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-over-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-over.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-over.png new file mode 100644 index 0000000..5106cdf Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-over.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-rtl.png new file mode 100644 index 0000000..658194b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow.png new file mode 100644 index 0000000..d3d375c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/breadcrumb/default-split-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-arrow-rtl.png new file mode 100644 index 0000000..76beeab Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-arrow.png new file mode 100644 index 0000000..32674e4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..79677a4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow-b.png new file mode 100644 index 0000000..9f3928a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow-rtl.png new file mode 100644 index 0000000..7985050 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow.png new file mode 100644 index 0000000..06ad27b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-large-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-arrow-rtl.png new file mode 100644 index 0000000..d54d3a0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-arrow.png new file mode 100644 index 0000000..e565db4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..f2fb53b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow-b.png new file mode 100644 index 0000000..ee39ae2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow-rtl.png new file mode 100644 index 0000000..fb11140 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow.png new file mode 100644 index 0000000..c1d1875 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-arrow-rtl.png new file mode 100644 index 0000000..3538445 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-arrow.png new file mode 100644 index 0000000..17a9beb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..2f8b2e5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow-b.png new file mode 100644 index 0000000..afd13fb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow-rtl.png new file mode 100644 index 0000000..f59b792 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow.png new file mode 100644 index 0000000..eaffbdc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-arrow-rtl.png new file mode 100644 index 0000000..d8f0151 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-arrow.png new file mode 100644 index 0000000..31fc36e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..379d2d9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow-b.png new file mode 100644 index 0000000..dcfe8ea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow-rtl.png new file mode 100644 index 0000000..612a6b1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow.png new file mode 100644 index 0000000..731b207 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-large-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-arrow-rtl.png new file mode 100644 index 0000000..1648e51 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-arrow.png new file mode 100644 index 0000000..65fdd03 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..8d2232b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow-b.png new file mode 100644 index 0000000..2489479 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow-rtl.png new file mode 100644 index 0000000..c81c5f2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow.png new file mode 100644 index 0000000..0a6857a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-arrow-rtl.png new file mode 100644 index 0000000..8919138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-arrow.png new file mode 100644 index 0000000..b56c2a6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..1142351 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow-b.png new file mode 100644 index 0000000..bb1b08e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow-rtl.png new file mode 100644 index 0000000..9e9e16b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow.png new file mode 100644 index 0000000..9a72857 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/default-toolbar-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-arrow-rtl.png new file mode 100644 index 0000000..3d68e7e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-arrow.png new file mode 100644 index 0000000..17a9beb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-s-arrow-b.png new file mode 100644 index 0000000..afd13fb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-s-arrow-rtl.png new file mode 100644 index 0000000..f59b792 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-s-arrow.png new file mode 100644 index 0000000..eaffbdc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/grid-cell-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-arrow-rtl.png new file mode 100644 index 0000000..d8f0151 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-arrow.png new file mode 100644 index 0000000..31fc36e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow-b-rtl.png new file mode 100644 index 0000000..379d2d9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow-b.png new file mode 100644 index 0000000..dcfe8ea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow-rtl.png new file mode 100644 index 0000000..612a6b1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow.png new file mode 100644 index 0000000..731b207 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-large-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-arrow-rtl.png new file mode 100644 index 0000000..1648e51 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-arrow.png new file mode 100644 index 0000000..65fdd03 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow-b-rtl.png new file mode 100644 index 0000000..8d2232b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow-b.png new file mode 100644 index 0000000..2489479 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow-rtl.png new file mode 100644 index 0000000..c81c5f2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow.png new file mode 100644 index 0000000..0a6857a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-medium-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-arrow-rtl.png new file mode 100644 index 0000000..8919138 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-arrow.png new file mode 100644 index 0000000..b56c2a6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow-b-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow-b-rtl.png new file mode 100644 index 0000000..1142351 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow-b-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow-b.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow-b.png new file mode 100644 index 0000000..bb1b08e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow-b.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow-rtl.png new file mode 100644 index 0000000..9e9e16b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow.png new file mode 100644 index 0000000..9a72857 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/button/plain-toolbar-small-s-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/datepicker/arrow-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/datepicker/arrow-left.png new file mode 100644 index 0000000..fc09f9a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/datepicker/arrow-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/datepicker/arrow-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/datepicker/arrow-right.png new file mode 100644 index 0000000..a22b876 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/datepicker/arrow-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/datepicker/month-arrow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/datepicker/month-arrow.png new file mode 100644 index 0000000..f0b572f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/datepicker/month-arrow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/dd/drop-add.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/dd/drop-add.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/dd/drop-add.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/dd/drop-no.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/dd/drop-no.png new file mode 100644 index 0000000..02e219a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/dd/drop-no.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/dd/drop-yes.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/dd/drop-yes.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/dd/drop-yes.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/editor/tb-sprite.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/editor/tb-sprite.png new file mode 100644 index 0000000..9886118 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/editor/tb-sprite.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/fieldset/collapse-tool.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/fieldset/collapse-tool.png new file mode 100644 index 0000000..97eb83f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/fieldset/collapse-tool.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/checkbox.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/checkbox.png new file mode 100644 index 0000000..fc2709c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/checkbox.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/clear-trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/clear-trigger-rtl.png new file mode 100644 index 0000000..73e1dbe Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/clear-trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/clear-trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/clear-trigger.png new file mode 100644 index 0000000..73e1dbe Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/clear-trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/date-trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/date-trigger-rtl.png new file mode 100644 index 0000000..9489493 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/date-trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/date-trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/date-trigger.png new file mode 100644 index 0000000..9489493 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/date-trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/exclamation.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/exclamation.png new file mode 100644 index 0000000..3e6e3d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/exclamation.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/radio.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/radio.png new file mode 100644 index 0000000..86644bb Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/radio.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/search-trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/search-trigger-rtl.png new file mode 100644 index 0000000..15e15f5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/search-trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/search-trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/search-trigger.png new file mode 100644 index 0000000..15e15f5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/search-trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/spinner-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/spinner-rtl.png new file mode 100644 index 0000000..28d140f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/spinner-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/spinner.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/spinner.png new file mode 100644 index 0000000..28d140f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/spinner.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/tag-field-item-close.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/tag-field-item-close.png new file mode 100644 index 0000000..bcb2834 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/tag-field-item-close.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/trigger-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/trigger-rtl.png new file mode 100644 index 0000000..b4e2d5c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/trigger-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/trigger.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/trigger.png new file mode 100644 index 0000000..b4e2d5c Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/form/trigger.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/col-move-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/col-move-bottom.png new file mode 100644 index 0000000..9782219 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/col-move-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/col-move-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/col-move-top.png new file mode 100644 index 0000000..6e28535 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/col-move-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/columns.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/columns.png new file mode 100644 index 0000000..70a5c87 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/columns.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dd-insert-arrow-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dd-insert-arrow-left.png new file mode 100644 index 0000000..e8177d0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dd-insert-arrow-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dd-insert-arrow-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dd-insert-arrow-right.png new file mode 100644 index 0000000..d610f9d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dd-insert-arrow-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dirty-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dirty-rtl.png new file mode 100644 index 0000000..5f84122 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dirty-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dirty.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dirty.png new file mode 100644 index 0000000..fc06fdd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/dirty.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/drop-no.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/drop-no.png new file mode 100644 index 0000000..02e219a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/drop-no.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/drop-yes.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/drop-yes.png new file mode 100644 index 0000000..a7b8f28 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/drop-yes.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/equals.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/equals.png new file mode 100644 index 0000000..c1060ca Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/equals.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/find.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/find.png new file mode 100644 index 0000000..dbfbc16 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/find.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/greater_than.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/greater_than.png new file mode 100644 index 0000000..be41c9a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/greater_than.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/less_than.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/less_than.png new file mode 100644 index 0000000..80aacdd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/filters/less_than.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/group-by.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/group-by.png new file mode 100644 index 0000000..8508ade Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/group-by.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/group-collapse.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/group-collapse.png new file mode 100644 index 0000000..49fcc4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/group-collapse.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/group-expand.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/group-expand.png new file mode 100644 index 0000000..d65a7df Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/group-expand.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hd-pop.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hd-pop.png new file mode 100644 index 0000000..3ad96ef Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hd-pop.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-asc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-asc.png new file mode 100644 index 0000000..a206d35 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-asc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-desc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-desc.png new file mode 100644 index 0000000..55a714e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-desc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-lock.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-lock.png new file mode 100644 index 0000000..b293e10 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-lock.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-unlock.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-unlock.png new file mode 100644 index 0000000..e9e9df5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/hmenu-unlock.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/loading.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/loading.gif new file mode 100644 index 0000000..81b0f12 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/loading.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-first.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-first.png new file mode 100644 index 0000000..7691f32 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-first.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-last.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-last.png new file mode 100644 index 0000000..49b13d7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-last.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-next.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-next.png new file mode 100644 index 0000000..c3e72ba Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-next.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-prev.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-prev.png new file mode 100644 index 0000000..cace90b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/page-prev.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/pick-button.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/pick-button.png new file mode 100644 index 0000000..acaface Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/pick-button.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/refresh.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/refresh.png new file mode 100644 index 0000000..5320ddd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/refresh.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/sort_asc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/sort_asc.png new file mode 100644 index 0000000..a206d35 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/sort_asc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/sort_desc.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/sort_desc.png new file mode 100644 index 0000000..55a714e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/grid/sort_desc.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/loadmask/loading.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/loadmask/loading.gif new file mode 100644 index 0000000..8471b4f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/loadmask/loading.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-checked.png new file mode 100644 index 0000000..4f5157d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-group-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-group-checked.png new file mode 100644 index 0000000..a9f0b80 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-group-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menu-parent-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menu-parent-left.png new file mode 100644 index 0000000..d457564 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menu-parent-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menu-parent.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menu-parent.png new file mode 100644 index 0000000..2d2331e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menu-parent.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-checked.png new file mode 100644 index 0000000..4f5157d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-group-checked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-group-checked.png new file mode 100644 index 0000000..a9f0b80 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-group-checked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-menu-parent-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-menu-parent-left.png new file mode 100644 index 0000000..9992618 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-menu-parent-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-menu-parent.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-menu-parent.png new file mode 100644 index 0000000..cb3a569 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-menu-parent.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-scroll-bottom.png new file mode 100644 index 0000000..69c61f6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-scroll-top.png new file mode 100644 index 0000000..ca7e3e1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-unchecked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-unchecked.png new file mode 100644 index 0000000..bce8817 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-menubar-unchecked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-scroll-bottom.png new file mode 100644 index 0000000..d89a459 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-scroll-top.png new file mode 100644 index 0000000..bbbf4af Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-unchecked.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-unchecked.png new file mode 100644 index 0000000..bce8817 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/menu/default-unchecked.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-error.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-error.png new file mode 100644 index 0000000..458c098 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-error.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-info.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-info.png new file mode 100644 index 0000000..cbccd11 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-info.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-question.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-question.png new file mode 100644 index 0000000..cac922e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-question.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-warning.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-warning.png new file mode 100644 index 0000000..042ca05 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/shared/icon-warning.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/e-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/e-handle.png new file mode 100644 index 0000000..2fe5cb1 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/e-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/ne-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/ne-handle.png new file mode 100644 index 0000000..8d8eb63 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/ne-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/nw-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/nw-handle.png new file mode 100644 index 0000000..9835bea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/nw-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/s-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/s-handle.png new file mode 100644 index 0000000..06f914e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/s-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/se-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/se-handle.png new file mode 100644 index 0000000..5a2c695 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/se-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/sw-handle.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/sw-handle.png new file mode 100644 index 0000000..7f68f40 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/sizer/sw-handle.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-bg.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-bg.png new file mode 100644 index 0000000..1ade292 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-bg.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-thumb.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-thumb.png new file mode 100644 index 0000000..d8a03de Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-thumb.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-v-bg.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-v-bg.png new file mode 100644 index 0000000..c24663e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-v-bg.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-v-thumb.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-v-thumb.png new file mode 100644 index 0000000..d8a03de Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/slider/slider-v-thumb.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-more-left.png new file mode 100644 index 0000000..83b0288 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-more.png new file mode 100644 index 0000000..83b0288 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-bottom.png new file mode 100644 index 0000000..813a4d5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-left.png new file mode 100644 index 0000000..9120ea4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-right.png new file mode 100644 index 0000000..67fd5a4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-top.png new file mode 100644 index 0000000..01ad4ee Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-plain-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-bottom.png new file mode 100644 index 0000000..ffff826 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-left.png new file mode 100644 index 0000000..2c35294 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-right.png new file mode 100644 index 0000000..82dfe01 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-top.png new file mode 100644 index 0000000..b2fabfc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab-bar/default-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab/tab-default-close.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab/tab-default-close.png new file mode 100644 index 0000000..46cc89f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tab/tab-default-close.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-bottom.png new file mode 100644 index 0000000..6741161 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-top.png new file mode 100644 index 0000000..2a26ba9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/default-scroll-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-more-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-more-left.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-more-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-more.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-more.png new file mode 100644 index 0000000..b6756e6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-more.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-scroll-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-scroll-left.png new file mode 100644 index 0000000..5ff969e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-scroll-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-scroll-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-scroll-right.png new file mode 100644 index 0000000..6fed21a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/toolbar/footer-scroll-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tools/tool-sprites-dark.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tools/tool-sprites-dark.png new file mode 100644 index 0000000..474088b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tools/tool-sprites-dark.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tools/tool-sprites.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tools/tool-sprites.png new file mode 100644 index 0000000..17fbc0f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tools/tool-sprites.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/arrows-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/arrows-rtl.png new file mode 100644 index 0000000..4aae887 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/arrows-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/arrows.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/arrows.png new file mode 100644 index 0000000..de10dd6 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/arrows.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-above.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-above.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-above.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-add.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-add.gif new file mode 100644 index 0000000..b22cd14 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-add.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-add.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-add.png new file mode 100644 index 0000000..c9d24fd Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-add.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-append.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-append.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-append.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-below.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-below.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-below.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-between.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-between.gif new file mode 100644 index 0000000..f5a042d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-between.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-between.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-between.png new file mode 100644 index 0000000..5782531 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-between.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-no.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-no.gif new file mode 100644 index 0000000..9d9c6a9 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-no.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-no.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-no.png new file mode 100644 index 0000000..bb89cfc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-no.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-over.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-over.gif new file mode 100644 index 0000000..2e514e7 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-over.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-over.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-over.png new file mode 100644 index 0000000..70d1807 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-over.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-under.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-under.gif new file mode 100644 index 0000000..8535ef4 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-under.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-under.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-under.png new file mode 100644 index 0000000..3ba23b3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-under.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-yes.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-yes.gif new file mode 100644 index 0000000..8aacb30 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-yes.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-yes.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-yes.png new file mode 100644 index 0000000..83d0dbc Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/drop-yes.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-minus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-minus-rtl.png new file mode 100644 index 0000000..2ffe7b2 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-minus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-minus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-minus.png new file mode 100644 index 0000000..b39a71d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-minus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-plus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-plus-rtl.png new file mode 100644 index 0000000..bea9892 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-plus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-plus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-plus.png new file mode 100644 index 0000000..630438f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-plus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-rtl.png new file mode 100644 index 0000000..1d0821b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end.png new file mode 100644 index 0000000..2eb0ed0 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-end.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-line-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-line-rtl.png new file mode 100644 index 0000000..e26b768 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-line-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-line.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-line.png new file mode 100644 index 0000000..ac37424 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-line.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus-nl-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus-nl-rtl.png new file mode 100644 index 0000000..1008a54 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus-nl-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus-nl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus-nl.png new file mode 100644 index 0000000..f2a805d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus-nl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus-rtl.png new file mode 100644 index 0000000..cefb704 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus.png new file mode 100644 index 0000000..a256b48 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-minus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus-nl-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus-nl-rtl.png new file mode 100644 index 0000000..e1e6ece Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus-nl-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus-nl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus-nl.png new file mode 100644 index 0000000..3a401ea Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus-nl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus-rtl.png new file mode 100644 index 0000000..487f27a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus.png new file mode 100644 index 0000000..03e202a Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-plus.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-rtl.png new file mode 100644 index 0000000..166e163 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow.png new file mode 100644 index 0000000..4bf9ae5 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/elbow.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder-open-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder-open-rtl.png new file mode 100644 index 0000000..bb896d8 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder-open-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder-open.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder-open.png new file mode 100644 index 0000000..50397da Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder-open.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder-rtl.png new file mode 100644 index 0000000..3b17672 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder.png new file mode 100644 index 0000000..4b02054 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/folder.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/leaf-rtl.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/leaf-rtl.png new file mode 100644 index 0000000..b2e6f6e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/leaf-rtl.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/leaf.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/leaf.png new file mode 100644 index 0000000..6acb635 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/leaf.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/loading.gif b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/loading.gif new file mode 100644 index 0000000..81b0f12 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/tree/loading.gif differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-bottom.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-bottom.png new file mode 100644 index 0000000..241209e Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-bottom.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-left.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-left.png new file mode 100644 index 0000000..1c40b78 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-left.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-right.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-right.png new file mode 100644 index 0000000..505c329 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-right.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-top.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-top.png new file mode 100644 index 0000000..4a378a3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neptune/images/util/splitter/mini-top.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/Readme.md b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/Readme.md new file mode 100644 index 0000000..4d76a0f --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/Readme.md @@ -0,0 +1,3 @@ +# theme-neutral/resources + +This folder contains static resources (typically an `"images"` folder as well). diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/magnify.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/magnify.png new file mode 100644 index 0000000..b807c42 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/magnify.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/fade-blue.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/fade-blue.png new file mode 100644 index 0000000..4dbf08b Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/fade-blue.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/fader.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/fader.png new file mode 100644 index 0000000..be8c27f Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/fader.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/icon16_error.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/icon16_error.png new file mode 100644 index 0000000..5f168d3 Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/icon16_error.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/icon16_info.png b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/icon16_info.png new file mode 100644 index 0000000..6c6b32d Binary files /dev/null and b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-neutral/images/window/toast/icon16_info.png differ diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all-debug.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all-debug.css new file mode 100644 index 0000000..94968f7 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all-debug.css @@ -0,0 +1,2 @@ +@import 'theme-triton-all-debug_1.css'; +@import 'theme-triton-all-debug_2.css'; diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all-debug_1.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all-debug_1.css new file mode 100644 index 0000000..72fab4c --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all-debug_1.css @@ -0,0 +1,15798 @@ +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:5 */ +.x-size-monitored { + /** + * @class Ext.util.SizeMonitor + */ + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:9 */ +.x-size-monitors { + position: absolute; + left: 0; + top: 0; + width: 100%; + height: 100%; + visibility: hidden; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:18 */ +.x-size-monitors > * { + width: 100%; + height: 100%; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:25 */ +.x-size-monitors.scroll > *.shrink::after { + content: ''; + display: block; + width: 200%; + height: 200%; + min-width: 1px; + min-height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:34 */ +.x-size-monitors.scroll > *.expand::after { + content: ''; + display: block; + width: 100000px; + height: 100000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:44 */ +.x-size-monitors.overflowchanged > *.shrink > * { + width: 100%; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:51 */ +.x-size-monitors.overflowchanged > *.expand > * { + width: 200%; + height: 200%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:59 */ +.x-size-change-detector { + visibility: hidden; + position: absolute; + left: 0; + top: 0; + z-index: -1; + width: 100%; + height: 100%; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:70 */ +.x-size-change-detector > * { + visibility: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:74 */ +.x-size-change-detector-shrink > * { + width: 200%; + height: 200%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/SizeMonitor.scss:79 */ +.x-size-change-detector-expand > * { + width: 100000px; + height: 100000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:5 */ +@-webkit-keyframes x-paint-monitor-helper { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:6 */ + from { + /** + * @class Ext.util.PaintMonitor + */ + /** + * @class Ext.util.PaintMonitor + */ + zoom: 1; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:9 */ + to { + zoom: 1; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:14 */ +@keyframes x-paint-monitor-helper { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:15 */ + from { + zoom: 1; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:18 */ + to { + zoom: 1; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:23 */ +.x-paint-monitored { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:27 */ +.x-paint-monitor { + width: 0 !important; + height: 0 !important; + visibility: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:32 */ +.x-paint-monitor.cssanimation { + -webkit-animation-duration: 0.0001ms; + -webkit-animation-name: x-paint-monitor-helper; + animation-duration: 0.0001ms; + animation-name: x-paint-monitor-helper; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:39 */ +.x-paint-monitor.overflowchange { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/util/PaintMonitor.scss:42 */ +.x-paint-monitor.overflowchange::after { + content: ''; + display: block; + width: 1px !important; + height: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:2 */ +.x-unselectable { + user-select: none; + -o-user-select: none; + -ms-user-select: none; + -moz-user-select: -moz-none; + -webkit-user-select: none; + -webkit-tap-highlight-color: transparent; + -webkit-user-drag: none; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:7 */ +.x-hidden-clip { + position: absolute !important; + clip: rect(0, 0, 0, 0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:12 */ +.x-hidden-display { + display: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:16 */ +.x-hidden-offsets, +.x-hidden { + display: block !important; + visibility: hidden !important; + position: absolute !important; + top: -10000px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:26 */ +.x-hidden-opacity { + opacity: 0 !important; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:31 */ +.x-hidden-visibility { + visibility: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:36 */ +.x-pressed .x-ripple-transition, +.x-pressing .x-ripple-transition { + transition: background-color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1), color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:40 */ +.x-pressed .x-ripple-transition .x-icon-el, +.x-pressed .x-ripple-transition .x-arrow-el, +.x-pressing .x-ripple-transition .x-icon-el, +.x-pressing .x-ripple-transition .x-arrow-el { + transition: background-color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1), color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:45 */ +.x-rippling { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:48 */ +.x-rippling.x-component-confirm .x-ripple { + background-color: green; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:52 */ +.x-rippling.x-component-decline .x-ripple { + background-color: red; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:57 */ +.x-rippling.x-rippling-unbound { + overflow: visible !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:59 */ +.x-rippling.x-rippling-unbound .x-ripple-container { + overflow: visible; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:68 */ +.x-safari .x-rippling:not(.x-rippling-unbound) .x-ripple-container { + -webkit-transform: rotate(0); + -moz-transform: rotate(0); + -ms-transform: rotate(0); + -o-transform: rotate(0); + transform: rotate(0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:72 */ +.x-ripple-container { + overflow: hidden; + position: absolute; + top: 0; + bottom: 0; + left: 0; + right: 0; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:83 */ +.x-ripple-wrapper { + z-index: 1000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:88 */ +.x-button-fab .x-ripple-container, +.x-button-round .x-ripple-container { + border-radius: 10000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:93 */ +.x-splitButton-fab .x-ripple-container, +.x-splitButton-round .x-ripple-container { + border-radius: 10000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:97 */ +.x-ripple { + position: absolute; + border-radius: 50%; + background-color: white; + -webkit-transform: scale(1, 1); + -moz-transform: scale(1, 1); + -ms-transform: scale(1, 1); + -o-transform: scale(1, 1); + transform: scale(1, 1); + opacity: 0.4; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:106 */ +.x-rippling.x-rippling-unbound .x-ripple { + -webkit-animation: x-ripple-unbound-animation 0.3s ease-out forwards; + animation: x-ripple-unbound-animation 0.3s ease-out forwards; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:110 */ +.x-rippling:not(.x-rippling-unbound) .x-ripple { + -webkit-animation: x-ripple-animation 0.35s ease-out forwards; + animation: x-ripple-animation 0.35s ease-out forwards; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/etc/mixins/animation.scss:17 */ +@-webkit-keyframes x-ripple-animation { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:115 */ + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:119 */ + 75% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0.2; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:123 */ + 100% { + -webkit-transform: scale(2.35, 2.35); + -moz-transform: scale(2.35, 2.35); + -ms-transform: scale(2.35, 2.35); + -o-transform: scale(2.35, 2.35); + transform: scale(2.35, 2.35); + opacity: 0; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/etc/mixins/animation.scss:20 */ +@keyframes x-ripple-animation { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:115 */ + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:119 */ + 75% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0.2; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:123 */ + 100% { + -webkit-transform: scale(2.35, 2.35); + -moz-transform: scale(2.35, 2.35); + -ms-transform: scale(2.35, 2.35); + -o-transform: scale(2.35, 2.35); + transform: scale(2.35, 2.35); + opacity: 0; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/etc/mixins/animation.scss:17 */ +@-webkit-keyframes x-ripple-unbound-animation { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:130 */ + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:134 */ + 75% { + -webkit-transform: scale(1.75, 1.75); + -moz-transform: scale(1.75, 1.75); + -ms-transform: scale(1.75, 1.75); + -o-transform: scale(1.75, 1.75); + transform: scale(1.75, 1.75); + opacity: 0.2; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:138 */ + 100% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/etc/mixins/animation.scss:20 */ +@keyframes x-ripple-unbound-animation { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:130 */ + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:134 */ + 75% { + -webkit-transform: scale(1.75, 1.75); + -moz-transform: scale(1.75, 1.75); + -ms-transform: scale(1.75, 1.75); + -o-transform: scale(1.75, 1.75); + transform: scale(1.75, 1.75); + opacity: 0.2; + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/Element.scss:138 */ + 100% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/ProgressBase.scss:1 */ +.x-progress { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/ProgressBase.scss:6 */ +.x-progress-bar { + height: 100%; + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/ProgressBase.scss:11 */ +.x-progress-text { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/ProgressBase.scss:15 */ +.x-progress-bar { + overflow: hidden; + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:1 */ +.x-scroller { + -webkit-overflow-scrolling: touch; + overflow-anchor: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:6 */ +.x-scroller-spacer { + position: absolute; + top: 0; + overflow: hidden; + height: 1px; + width: 1px; + font-size: 0; + line-height: 0; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:17 */ +.x-scroller-snappable { + -ms-scroll-snap-type: mandatory; + -webkit-scroll-snap-type: mandatory; + scroll-snap-type: mandatory; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:23 */ +.x-no-scrollbars { + -ms-overflow-style: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/scroll/Scroller.scss:26 */ +.x-no-scrollbars::-webkit-scrollbar { + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/TouchAction.scss:1 */ +.x-touch-action-pan-y { + overflow-x: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/dom/TouchAction.scss:5 */ +.x-touch-action-pan-x { + overflow-y: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/drag/Source.scss:4 */ +.x-drag-body { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/drag/Source.scss:6 */ +.x-drag-body * { + -webkit-user-select: none; + -moz-user-select: none; + user-select: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/drag/Source.scss:11 */ +.x-drag-dragging { + z-index: 1000000!important; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:576 */ +.x-treelist { + background-color: #fff; + background-position: 16px 0%; + overflow: hidden; + padding: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:589 */ +.x-treelist-container, +.x-treelist-root-container { + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:594 */ +.x-treelist-toolstrip { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:599 */ +.x-treelist-micro > .x-treelist-toolstrip { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:602 */ +.x-treelist-micro > .x-treelist-root-container { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:607 */ +.x-treelist-item, +.x-treelist-container, +.x-treelist-root-container { + position: relative; + overflow: hidden; + list-style: none; + padding: 0; + margin: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:617 */ +.x-treelist-item-tool, +.x-treelist-row, +.x-treelist-item-wrap { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:623 */ +.x-treelist-item-icon, +.x-treelist-item-expander { + display: none; + position: absolute; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:630 */ +.x-treelist-item-expander { + right: 0; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:635 */ +.x-treelist-expander-only .x-treelist-item-expandable > * > .x-treelist-item-wrap > * { + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:639 */ +.x-treelist-item-text { + cursor: pointer; + white-space: nowrap; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:645 */ +.x-treelist-item-collapsed > .x-treelist-container { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:649 */ +.x-treelist-item-expandable > * > * > .x-treelist-item-expander, +.x-treelist-item-icon { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:654 */ +.x-treelist-item-floated > * > * > .x-treelist-item-expander, +.x-treelist-item-floated > * > * > .x-treelist-item-icon { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:659 */ +.x-treelist-expander-first .x-treelist-item-expander { + left: 0; + right: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:103 */ +.x-treelist-toolstrip { + background-color: #f8f8f8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:134 */ +.x-treelist-item-selected > .x-treelist-row { + background-color: #ffefbb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:138 */ +.x-treelist-item-selected > .x-treelist-row-over { + background-color: #ffefbb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:143 */ +.x-treelist-item-tool { + padding-left: 6px; + padding-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:166 */ +.x-treelist-item-icon:before, +.x-treelist-item-tool:before, +.x-treelist-item-expander { + line-height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:178 */ +.x-treelist-item-icon, +.x-treelist-item-tool, +.x-treelist-item-expander { + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:188 */ +.x-treelist-item-loading .x-treelist-item-icon { + background-image: url(images/tree/loading.gif); + color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:193 */ +.x-treelist-item-icon, +.x-treelist-item-tool { + color: #5fa2dd; + font-size: 16px; + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:206 */ +.x-treelist-item-tool { + width: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:216 */ +.x-treelist-item-expander { + color: #5fa2dd; + font-size: 16px; + width: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:232 */ +.x-treelist-item-expander:after { + content: "\f0da"; + font: 16px/32px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:240 */ +.x-treelist-item-expanded > * > * > .x-treelist-item-expander:after { + content: "\f0d7"; + font: 16px/32px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:253 */ +.x-treelist-item-text { + color: #404040; + margin-left: 22px; + margin-right: 18px; + font-size: 13px; + line-height: 32px; + text-overflow: ellipsis; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:270 */ +.x-treelist-row { + padding-left: 6px; + padding-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:301 */ +.x-treelist-item-floated .x-treelist-container { + width: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:304 */ +.x-treelist-item-floated > .x-treelist-row { + background-color: #f8f8f8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:308 */ +.x-treelist-item-floated > .x-treelist-container { + margin-left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:311 */ +.x-big .x-treelist-item-floated > .x-treelist-container { + margin-left: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:317 */ +.x-treelist-item-floated > * > * > .x-treelist-item-text { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:321 */ +.x-treelist-item-floated > * .x-treelist-row { + cursor: pointer; + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:326 */ +.x-treelist-item-floated .x-treelist-row:before { + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:330 */ +.x-treelist-item-floated > .x-treelist-row-over { + background-color: #f8f8f8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:333 */ +.x-treelist-item-floated > .x-treelist-row-over > * > .x-treelist-item-text { + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:346 */ +.x-treelist-item-expanded > .x-treelist-item-expander:after { + content: "\f0d7"; + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:351 */ +.x-treelist-item-collapsed > * > .x-treelist-item-expander:after { + content: "\f0da"; + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:357 */ +.x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-icon { + color: #5fa2dd; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:361 */ +.x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-text { + color: #404040; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:365 */ +.x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-expander { + color: #5fa2dd; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:372 */ +.x-treelist-row-over { + background-color: #eaeff4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:376 */ +.x-treelist-row-over > * > .x-treelist-item-icon { + color: #5fa2dd; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:380 */ +.x-treelist-row-over > * > .x-treelist-item-text { + color: #404040; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:384 */ +.x-treelist-row-over > * > .x-treelist-item-expander { + color: #5fa2dd; + transition: color 0.5s; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:391 */ +.x-treelist-expander-first .x-treelist-item-icon { + left: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:400 */ +.x-treelist-expander-first .x-treelist-item-text { + margin-left: 40px; + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:410 */ +.x-treelist-expander-first .x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 21px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:420 */ +.x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:495 */ +.x-treelist-nav { + background-color: #32404e; + background-position: 24px 0%; + padding: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:103 */ +.x-treelist-nav .x-treelist-toolstrip { + background-color: #32404e; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:112 */ +.x-treelist-nav .x-treelist-item-selected.x-treelist-item-tool { + color: #f0f0f0; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:134 */ +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row { + background-color: #3f505f; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:143 */ +.x-treelist-nav .x-treelist-item-tool { + padding-left: 10px; + padding-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:150 */ +.x-treelist-nav .x-treelist-item-tool-floated:after { + height: 44px; + position: absolute; + top: 0; + left: 0; + content: " "; + width: 4px; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:166 */ +.x-treelist-nav .x-treelist-item-icon:before, +.x-treelist-nav .x-treelist-item-tool:before, +.x-treelist-nav .x-treelist-item-expander { + line-height: 44px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:178 */ +.x-treelist-nav .x-treelist-item-icon, +.x-treelist-nav .x-treelist-item-tool, +.x-treelist-nav .x-treelist-item-expander { + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:188 */ +.x-treelist-nav .x-treelist-item-loading .x-treelist-item-icon { + background-image: url(images/tree/loading.gif); + color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:193 */ +.x-treelist-nav .x-treelist-item-icon, +.x-treelist-nav .x-treelist-item-tool { + color: #adb3b8; + font-size: 18px; + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:206 */ +.x-treelist-nav .x-treelist-item-tool { + width: 44px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:216 */ +.x-treelist-nav .x-treelist-item-expander { + color: #adb3b8; + font-size: 16px; + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:253 */ +.x-treelist-nav .x-treelist-item-text { + color: #adb3b8; + margin-left: 30px; + margin-right: 24px; + font-size: 16px; + line-height: 44px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:270 */ +.x-treelist-nav .x-treelist-row { + padding-left: 10px; + padding-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:276 */ +.x-treelist-nav .x-treelist-row-over:before, +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before { + content: " "; + position: absolute; + display: block; + left: 0; + top: 0; + width: 6px; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:287 */ +.x-treelist-nav .x-treelist-row-over:before { + background-color: #89bae6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:291 */ +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row-over:before { + background-color: #89bae6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:295 */ +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:301 */ +.x-treelist-nav .x-treelist-item-floated .x-treelist-container { + width: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:304 */ +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row { + background-color: #32404e; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:308 */ +.x-treelist-nav .x-treelist-item-floated > .x-treelist-container { + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:311 */ +.x-big .x-treelist-nav .x-treelist-item-floated > .x-treelist-container { + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:317 */ +.x-treelist-nav .x-treelist-item-floated > * > * > .x-treelist-item-text { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:321 */ +.x-treelist-nav .x-treelist-item-floated > * .x-treelist-row { + cursor: pointer; + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:326 */ +.x-treelist-nav .x-treelist-item-floated .x-treelist-row:before { + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:330 */ +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row-over { + background-color: #32404e; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:333 */ +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row-over > * > .x-treelist-item-text { + color: #adb3b8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:339 */ +.x-treelist-nav .x-treelist-item-expanded { + background-color: #2c3845; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:357 */ +.x-treelist-nav .x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-icon { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:361 */ +.x-treelist-nav .x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-text { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:365 */ +.x-treelist-nav .x-treelist-highlight-path .x-treelist-item-over > * > * > .x-treelist-item-expander { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:372 */ +.x-treelist-nav .x-treelist-row-over { + background-color: #4f606f; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:376 */ +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-icon { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:380 */ +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-text { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:384 */ +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-expander { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:391 */ +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-icon { + left: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:400 */ +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-text { + margin-left: 54px; + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:410 */ +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 27px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/core/sass/src/list/TreeItem.scss:420 */ +.x-treelist-nav .x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:14 */ +.x-body { + margin: 0; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:23 */ +@-ms-viewport { + width: device-width; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:28 */ +img { + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:32 */ +.x-border-box, +.x-border-box * { + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:46 */ +.x-ltr { + direction: ltr; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:50 */ +.x-clear { + overflow: hidden; + clear: both; + font-size: 0; + line-height: 0; + display: table; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:58 */ +.x-layer { + position: absolute !important; + top: 0; + left: 0; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:72 */ +.x-fixed-layer { + position: fixed !important; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:77 */ +.x-shim { + position: absolute; + left: 0; + top: 0; + overflow: hidden; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:90 */ +.x-hidden-clip { + position: absolute !important; + clip: rect(0, 0, 0, 0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:95 */ +.x-masked-relative { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:101 */ +.x-ie-shadow { + background-color: #777; + position: absolute; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:108 */ +.x-selectable { + cursor: auto; + -moz-user-select: text; + -webkit-user-select: text; + -ms-user-select: text; + user-select: text; + -o-user-select: text; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:123 */ +.x-list-plain { + list-style-type: none; + margin: 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:130 */ +.x-table-plain { + border-collapse: collapse; + border-spacing: 0; + font-size: 1em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:138 */ +.x-frame-tl, +.x-frame-tr, +.x-frame-tc, +.x-frame-bl, +.x-frame-br, +.x-frame-bc { + overflow: hidden; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:148 */ +.x-frame-tc, +.x-frame-bc { + background-repeat: repeat-x; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:157 */ +td.x-frame-tl, +td.x-frame-tr, +td.x-frame-bl, +td.x-frame-br { + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:164 */ +.x-frame-mc { + background-repeat: repeat-x; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:169 */ +.x-proxy-el { + position: absolute; + background: #b4b4b4; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:176 */ +.x-css-shadow { + position: absolute; + -webkit-border-radius: 5px; + -moz-border-radius: 5px; + -ms-border-radius: 5px; + -o-border-radius: 5px; + border-radius: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:181 */ +.x-item-disabled, +.x-item-disabled * { + cursor: default; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:187 */ +.x-component, +.x-container { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:197 */ +:focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:206 */ +.x-body .x-sync-repaint:before, +.x-body .x-sync-repaint:after { + content: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:215 */ +.x-position-relative { + position: relative !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/Component.scss:221 */ +.x-tab-guard { + position: absolute; + clip: rect(0, 0, 0, 0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Container.scss:3 */ +.x-box-item { + position: absolute !important; + left: 0; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Auto.scss:1 */ +.x-autocontainer-outerCt { + display: table; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Auto.scss:4 */ +.x-mobile-safari .x-autocontainer-outerCt { + transform: translateZ(0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Auto.scss:14 */ +.x-clipped .x-autocontainer-outerCt { + transform: initial; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Auto.scss:18 */ +.x-autocontainer-innerCt { + display: table-cell; + height: 100%; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/LoadMask.scss:1 */ +.x-mask { + z-index: 100; + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + /* + * IE and FF will add an outline to focused elements, + * which we don't want when using our own focus treatment + */ + outline: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/LoadMask.scss:21 */ +.x-ie8 .x-mask { + /* + * IE8 will treat partially transparent divs as invalid click targets, + * allowing mouse events to reach elements beneath the mask. Placing + * a 1x1 transparent gif as the link el background will cure this. + */ + background-image: url(data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/LoadMask.scss:27 */ +.x-mask-fixed { + position: fixed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/LoadMask.scss:31 */ +.x-mask-msg { + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/ProgressBar.scss:1 */ +.x-progress { + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:21 */ +.x-btn { + display: inline-block; + outline: 0; + cursor: pointer; + white-space: nowrap; + text-decoration: none; + vertical-align: top; + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:33 */ +.x-btn > .x-frame { + height: 100%; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:39 */ +.x-btn-wrap { + height: 100%; + width: 100%; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: stretch; + -ms-flex-align: stretch; + align-items: stretch; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:47 */ +.x-btn-wrap.x-btn-arrow-bottom, +.x-btn-wrap.x-btn-split-bottom { + -webkit-box-orient: vertical; + -ms-flex-direction: column; + flex-direction: column; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:53 */ +.x-ie9m .x-btn-wrap { + display: table; + border-spacing: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:64 */ +.x-btn-button { + white-space: nowrap; + line-height: 0; + position: relative; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: center; + -ms-flex-align: center; + align-items: center; + -webkit-box-flex: 1; + -ms-flex: 1 1 auto; + flex: 1 1 auto; + min-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:76 */ +.x-btn-button.x-btn-icon-top, +.x-btn-button.x-btn-icon-bottom { + -webkit-box-orient: vertical; + -ms-flex-direction: column; + flex-direction: column; + -webkit-box-align: stretch; + -ms-flex-align: stretch; + align-items: stretch; + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:85 */ +.x-ie10p .x-btn-button.x-btn-icon-top, +.x-ie10p .x-btn-button.x-btn-icon-bottom { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:92 */ +.x-ie9m .x-btn-button { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:103 */ +.x-btn-inner { + overflow: hidden; + text-overflow: ellipsis; + -ms-flex-negative: 1; + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:112 */ +.x-ie9m .x-btn-inner { + display: inline-block; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:122 */ +.x-btn-icon.x-btn-no-text > .x-btn-inner { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:127 */ +.x-btn-icon-el { + display: none; + vertical-align: middle; + text-align: center; + background-position: center center; + background-repeat: no-repeat; + flex-shrink: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:137 */ +.x-btn-icon > .x-btn-icon-el { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:142 */ +.x-ie9m .x-btn-icon-left > .x-btn-icon-el, +.x-ie9m .x-btn-icon-right > .x-btn-icon-el { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:159 */ +.x-btn-button-center { + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:161 */ +.x-ie9m .x-btn-button-center { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:169 */ +.x-btn-button-center.x-btn-icon-top, +.x-btn-button-center.x-btn-icon-bottom { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:175 */ +.x-btn-button-left { + text-align: left; + -webkit-box-pack: start; + -ms-flex-pack: start; + justify-content: flex-start; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:188 */ +.x-btn-button-right { + text-align: right; + -webkit-box-pack: end; + -ms-flex-pack: end; + justify-content: flex-end; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:202 */ +.x-btn-arrow:after, +.x-btn-split:after { + display: block; + background-repeat: no-repeat; + content: ''; + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:216 */ +.x-btn-arrow-right:after, +.x-btn-split-right:after { + background-position: right center; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: center; + -ms-flex-align: center; + align-items: center; + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:226 */ +.x-ie9m .x-btn-arrow-right:after, +.x-ie9m .x-btn-split-right:after { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:246 */ +.x-btn-arrow-bottom:after, +.x-btn-split-bottom:after { + background-position: center bottom; + content: '\00a0'; + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:259 */ +.x-ie9m .x-btn-arrow-bottom:after, +.x-ie9m .x-btn-split-bottom:after { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:269 */ +.x-btn-split-right > .x-btn-button:after { + position: absolute; + display: block; + top: -100%; + right: 0; + height: 300%; + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:286 */ +.x-btn-split-bottom > .x-btn-button:after { + position: absolute; + display: block; + bottom: 0; + left: -100%; + font-size: 0; + width: 300%; + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:297 */ +.x-btn-mc { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:1 */ +.x-segmented-button { + display: table; + table-layout: fixed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:6 */ +.x-segmented-button-item { + display: table-cell; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:10 */ +.x-segmented-button-item > .x-frame { + width: 100%; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:17 */ +.x-segmented-button-item .x-btn-mc { + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:23 */ +.x-segmented-button-item-horizontal { + display: table-cell; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:30 */ +.x-segmented-button-item-horizontal.x-segmented-button-first { + border-top-right-radius: 0; + border-bottom-right-radius: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:35 */ +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-tr, +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-mr, +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-br { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:43 */ +.x-segmented-button-item-horizontal.x-segmented-button-middle { + border-radius: 0; + border-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:48 */ +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tl, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tr, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-ml, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-mr, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-bl, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-br { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:59 */ +.x-segmented-button-item-horizontal.x-segmented-button-last { + border-left: 0; + border-top-left-radius: 0; + border-bottom-left-radius: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:65 */ +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-tl, +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-ml, +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-bl { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:74 */ +.x-segmented-button-row { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:79 */ +.x-segmented-button-item-vertical.x-segmented-button-first { + border-bottom-right-radius: 0; + border-bottom-left-radius: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:84 */ +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bl, +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bc, +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-br { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:92 */ +.x-segmented-button-item-vertical.x-segmented-button-middle { + border-radius: 0; + border-top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:97 */ +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tl, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tc, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tr, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bl, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bc, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-br { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:108 */ +.x-segmented-button-item-vertical.x-segmented-button-last { + border-top: 0; + border-top-right-radius: 0; + border-top-left-radius: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/button/Segmented.scss:114 */ +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tl, +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tc, +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tr { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:1 */ +.x-title-icon { + background-repeat: no-repeat; + background-position: 0 0; + vertical-align: middle; + line-height: 1; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:9 */ +.x-title { + display: table; + table-layout: fixed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:21 */ +.x-title-text { + display: table-cell; + overflow: hidden; + white-space: nowrap; + -o-text-overflow: ellipsis; + text-overflow: ellipsis; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:30 */ +.x-title-align-left { + text-align: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:39 */ +.x-title-align-center { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:43 */ +.x-title-align-right { + text-align: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:52 */ +.x-title-rotate-right { + -webkit-transform: rotate(90deg); + -webkit-transform-origin: 0 0; + -moz-transform: rotate(90deg); + -moz-transform-origin: 0 0; + -ms-transform: rotate(90deg); + -ms-transform-origin: 0 0; + transform: rotate(90deg); + transform-origin: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/rotate-element.scss:41 */ +.x-ie8 .x-title-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:62 */ +.x-title-rotate-left { + -webkit-transform: rotate(270deg); + -webkit-transform-origin: 100% 0; + -moz-transform: rotate(270deg); + -moz-transform-origin: 100% 0; + -ms-transform: rotate(270deg); + -ms-transform-origin: 100% 0; + transform: rotate(270deg); + transform-origin: 100% 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/rotate-element.scss:41 */ +.x-ie8 .x-title-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:75 */ +.x-horizontal.x-header .x-title-rotate-right.x-title-align-left > .x-title-item { + vertical-align: bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:79 */ +.x-horizontal.x-header .x-title-rotate-right.x-title-align-center > .x-title-item { + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:83 */ +.x-horizontal.x-header .x-title-rotate-right.x-title-align-right > .x-title-item { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:89 */ +.x-horizontal.x-header .x-title-rotate-left.x-title-align-left > .x-title-item { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:93 */ +.x-horizontal.x-header .x-title-rotate-left.x-title-align-center > .x-title-item { + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:97 */ +.x-horizontal.x-header .x-title-rotate-left.x-title-align-right > .x-title-item { + vertical-align: bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:105 */ +.x-vertical.x-header .x-title-rotate-none.x-title-align-left > .x-title-item { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:109 */ +.x-vertical.x-header .x-title-rotate-none.x-title-align-center > .x-title-item { + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:113 */ +.x-vertical.x-header .x-title-rotate-none.x-title-align-right > .x-title-item { + vertical-align: bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:120 */ +.x-title-icon-wrap { + display: table-cell; + text-align: center; + vertical-align: middle; + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:125 */ +.x-title-icon-wrap.x-title-icon-top, +.x-title-icon-wrap.x-title-icon-bottom { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Title.scss:131 */ +.x-title-icon { + display: inline-block; + vertical-align: middle; + background-position: center; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Tool.scss:1 */ +.x-tool { + font-size: 16px; + line-height: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Header.scss:4 */ +.x-header > .x-box-inner, +.x-panel-header-mc > .x-box-inner, +.x-window-header-mc > .x-box-inner { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:1 */ +.x-splitter { + font-size: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:5 */ +.x-splitter-horizontal { + cursor: e-resize; + cursor: row-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:10 */ +.x-splitter-vertical { + cursor: e-resize; + cursor: col-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:15 */ +.x-splitter-collapsed, +.x-splitter-horizontal-noresize, +.x-splitter-vertical-noresize { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:21 */ +.x-splitter-active { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:25 */ +.x-collapse-el { + position: absolute; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Splitter.scss:30 */ +.x-splitter-focus { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:1 */ +.x-box-layout-ct { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:5 */ +.x-box-target { + position: absolute; + width: 20000px; + top: 0; + left: 0; + min-height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:32 */ +.x-box-inner { + overflow: hidden; + position: relative; + left: 0; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:39 */ +.x-box-scroller { + position: absolute; + background-repeat: no-repeat; + background-position: center; + line-height: 0; + font-size: 0; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:48 */ +.x-box-scroller-top { + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:52 */ +.x-box-scroller-right { + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:56 */ +.x-box-scroller-bottom { + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:60 */ +.x-box-scroller-left { + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:64 */ +.x-box-menu-body-horizontal { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:68 */ +.x-box-menu-after { + position: relative; + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:75 */ +.x-box-scroller-body-vertical, +.x-box-scroller-body-horizontal { + -ms-overflow-style: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:78 */ +.x-box-scroller-body-vertical .x-scroller, +.x-box-scroller-body-horizontal .x-scroller { + -ms-overflow-style: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Box.scss:81 */ +.x-box-scroller-body-vertical :not(.x-scroller)::-webkit-scrollbar, +.x-box-scroller-body-horizontal :not(.x-scroller)::-webkit-scrollbar { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Toolbar.scss:1 */ +.x-toolbar-text { + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Toolbar.scss:5 */ +.x-toolbar-separator { + display: block; + font-size: 1px; + overflow: hidden; + cursor: default; + border: 0; + width: 0; + height: 0; + line-height: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Toolbar.scss:16 */ +.x-toolbar-scroller { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Toolbar.scss:23 */ +.x-toolbar-plain { + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/DD.scss:3 */ +.x-dd-drag-proxy, +.x-dd-drag-current { + z-index: 1000000!important; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:1 */ +.x-dd-drag-proxy { + display: table; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:6 */ +.x-dd-drag-repair .x-dd-drag-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:10 */ +.x-dd-drag-repair .x-dd-drop-icon { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:15 */ +.x-dd-drag-ghost, +.x-dd-drop-icon { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:21 */ +.x-dd-drag-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=85)"; + opacity: 0.85; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/dd/StatusProxy.scss:26 */ +.x-dd-drop-icon { + height: 26px; + width: 26px; + background-color: transparent; + background-position: center; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:1 */ +.x-docked { + position: absolute !important; + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:7 */ +.x-docked-vertical { + position: static; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:11 */ +.x-docked-top { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:15 */ +.x-docked-bottom { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:19 */ +.x-docked-left { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:23 */ +.x-docked-right { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:27 */ +.x-docked-noborder-top { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:31 */ +.x-docked-noborder-right { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:35 */ +.x-docked-noborder-bottom { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:39 */ +.x-docked-noborder-left { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:45 */ +.x-noborder-l { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:48 */ +.x-noborder-b { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:51 */ +.x-noborder-bl { + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:55 */ +.x-noborder-r { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:58 */ +.x-noborder-rl { + border-right-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:62 */ +.x-noborder-rb { + border-right-width: 0 !important; + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:66 */ +.x-noborder-rbl { + border-right-width: 0 !important; + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:71 */ +.x-noborder-t { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:74 */ +.x-noborder-tl { + border-top-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:78 */ +.x-noborder-tb { + border-top-width: 0 !important; + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:82 */ +.x-noborder-tbl { + border-top-width: 0 !important; + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:87 */ +.x-noborder-tr { + border-top-width: 0 !important; + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:91 */ +.x-noborder-trl { + border-top-width: 0 !important; + border-right-width: 0 !important; + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:96 */ +.x-noborder-trb { + border-top-width: 0 !important; + border-right-width: 0 !important; + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/component/Dock.scss:101 */ +.x-noborder-trbl { + border-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:1 */ +.x-panel, +.x-plain { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:7 */ +.x-panel { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:13 */ +td.x-frame-mc { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:18 */ +.x-panel-bodyWrap { + overflow: hidden; + position: static; + height: 100%; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:25 */ +.x-panel-body { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:30 */ +.x-panel-header-plain, +.x-panel-body-plain { + border: 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:40 */ +.x-panel-collapsed-mini { + visibility: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Panel.scss:50 */ +.x-viewport > .x-body.x-panel > .x-panel-bodyWrap { + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Table.scss:1 */ +.x-table-layout { + font-size: 1em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/container/ButtonGroup.scss:1 */ +.x-btn-group { + position: relative; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/container/ButtonGroup.scss:6 */ +.x-btn-group-body { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/container/ButtonGroup.scss:8 */ +.x-btn-group-body .x-table-layout-cell { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:1 */ +.x-viewport, +.x-viewport > .x-body { + margin: 0; + padding: 0; + border: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:8 */ +.x-viewport { + width: 100%; + height: 100%; + position: static; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:16 */ +.x-viewport > .x-body { + position: fixed; + top: 0; + left: 0; + min-width: 100%; + min-height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:30 */ +@media print { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/plugin/Viewport.scss:33 */ + .x-viewport > .x-body { + position: static; + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Column.scss:1 */ +.x-column { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/SplitterTracker.scss:1 */ +.x-resizable-overlay { + position: absolute; + left: 0; + top: 0; + width: 100%; + height: 100%; + display: none; + z-index: 200000; + background-color: #fff; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/window/Window.scss:1 */ +.x-window { + outline: none; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/window/Window.scss:5 */ +.x-window .x-window-wrap { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/window/Window.scss:10 */ +.x-window-body { + position: relative; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:1 */ +.x-form-item { + display: table; + table-layout: fixed; + border-spacing: 0; + border-collapse: separate; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:10 */ +.x-form-item-label { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:14 */ +.x-form-item.x-form-item-no-label > .x-form-item-label { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:18 */ +.x-form-item-label, +.x-form-item-body { + display: table-cell; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:23 */ +.x-form-item-body { + vertical-align: middle; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:28 */ +.x-form-item-label-inner { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:32 */ +.x-form-item-label-top { + display: table-row; + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:35 */ +.x-form-item-label-top > .x-form-item-label-inner { + display: table-cell; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:39 */ +.x-form-item-label-top-side-error:after { + display: table-cell; + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:44 */ +.x-form-item-label-right { + text-align: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:53 */ +.x-form-error-wrap-side { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:58 */ +.x-form-error-wrap-under { + display: table-row; + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:61 */ +.x-form-error-wrap-under > .x-form-error-msg { + display: table-cell; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:66 */ +.x-form-error-wrap-under-side-label:before { + display: table-cell; + content: ''; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:72 */ +.x-form-invalid-icon { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/Labelable.scss:74 */ +.x-form-invalid-icon ul { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:1 */ +.x-form-trigger-wrap { + display: table; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:6 */ +.x-form-text-heighted .x-form-trigger-wrap { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:17 */ +.x-gecko .x-form-trigger-wrap { + display: -moz-inline-box; + display: inline-flex; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:27 */ +.x-form-type-text.x-has-min-height { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:32 */ +.x-form-type-text.x-has-min-height .x-form-text-field-body, +.x-form-type-text.x-has-min-height .x-form-trigger-wrap, +.x-form-type-text.x-has-min-height .x-form-text-wrap { + min-height: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:40 */ +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-field-body, +.x-ie8 .x-form-type-text.x-has-min-height .x-form-trigger-wrap, +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-wrap { + min-height: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:47 */ +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text { + min-height: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:52 */ +.x-form-type-text.x-has-min-height .x-form-text { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:57 */ +.x-form-text-wrap { + display: table-cell; + overflow: hidden; + height: 100%; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:65 */ +.x-gecko .x-form-text-wrap { + display: block; + -moz-box-flex: 1; + flex: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:72 */ +.x-form-text-wrap .x-placeholder-label { + position: absolute; + top: 0; + left: 0; + cursor: text; + white-space: nowrap; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:84 */ +.x-form-item-body.x-form-text-grow { + min-width: inherit; + max-width: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:89 */ +.x-form-text { + border: 0; + margin: 0; + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + display: block; + background: repeat-x 0 0; + width: 100%; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:99 */ +.x-form-trigger { + display: table-cell; + vertical-align: top; + cursor: pointer; + overflow: hidden; + background-repeat: no-repeat; + text-align: center; + line-height: 0; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:111 */ +.x-item-disabled .x-form-trigger { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:114 */ +.x-form-trigger.x-form-trigger-cmp { + background: none; + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Text.scss:131 */ +.x-gecko .x-form-trigger { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/TextArea.scss:2 */ +.x-form-textarea-body.x-form-text-grow > .x-form-trigger-wrap { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/TextArea.scss:7 */ +.x-form-textarea { + overflow: auto; + resize: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/TextArea.scss:12 */ +div.x-form-text-grow .x-form-textarea { + min-height: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/window/MessageBox.scss:2 */ +.x-message-box .x-form-display-field { + height: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldContainer.scss:4 */ +.x-safari .x-form-fieldcontainer { + table-layout: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldContainer.scss:12 */ +.x-ie8 .x-form-fieldcontainer > .x-form-item-body.x-field-container-body-vertical { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:1 */ +.x-form-cb-wrap { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:5 */ +.x-form-cb-wrap-inner { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:9 */ +.x-form-cb { + position: absolute; + left: 0; + right: auto; + vertical-align: top; + overflow: hidden; + padding: 0; + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:17 */ +.x-form-cb::-moz-focus-inner { + padding: 0; + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:23 */ +.x-form-cb-input { + position: absolute; + margin: 0; + padding: 0; + border: 0; + top: 0; + left: 0; + width: 100%; + height: 100%; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:43 */ +.x-form-cb-after { + /* allow for the component to be positioned after the label */ + left: auto; + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:57 */ +.x-form-cb-label { + /* some browsers like IE 10 need a block element to be able to measure +the height of a multi-line element */ + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Checkbox.scss:60 */ +.x-form-cb-label.x-form-cb-no-box-label { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:1 */ +.x-fieldset { + display: block; + /* preserve margins in IE */ + position: relative; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:7 */ +.x-fieldset-header { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:10 */ +.x-fieldset-header .x-form-item, +.x-fieldset-header .x-tool { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:15 */ +.x-fieldset-header .x-fieldset-header-text { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:19 */ +.x-fieldset-header .x-form-cb-wrap { + font-size: 0; + line-height: 0; + min-height: 0; + height: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:26 */ +.x-fieldset-header .x-form-cb { + margin: 0; + position: static; + display: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:35 */ +.x-fieldset-body { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:39 */ +.x-fieldset-collapsed { + padding-bottom: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:42 */ +.x-fieldset-collapsed > .x-fieldset-body { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/FieldSet.scss:47 */ +.x-fieldset-header-text-collapsible { + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/view/View.scss:2 */ +.x-keyboard-mode .x-view-item-focused { + outline: 1px dashed #5fa2dd !important; + outline-offset: -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/view/BoundList.scss:8 */ +.x-ie9 .x-boundlist-list-ct { + min-height: 0%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:1 */ +.x-datepicker { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:4 */ +.x-datepicker .x-monthpicker { + left: 0; + top: 0; + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:10 */ +.x-datepicker .x-monthpicker-months, +.x-datepicker .x-monthpicker-years { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:16 */ +.x-datepicker-inner { + table-layout: fixed; + width: 100%; + border-collapse: separate; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:22 */ +.x-datepicker-cell { + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:26 */ +.x-datepicker-header { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:30 */ +.x-datepicker-arrow { + position: absolute; + outline: none; + font-size: 0; + display: table; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:37 */ +.x-datepicker-arrow:before { + display: table-cell; + text-align: center; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:45 */ +.x-datepicker-column-header { + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:49 */ +.x-datepicker-date { + display: block; + text-decoration: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:54 */ +.x-monthpicker { + display: table; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:57 */ +.x-monthpicker-body { + height: 100%; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:62 */ +.x-monthpicker-months, +.x-monthpicker-years { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:67 */ +.x-monthpicker-item { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:71 */ +.x-monthpicker-item-inner { + display: block; + text-decoration: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:76 */ +.x-monthpicker-yearnav-button-ct { + float: left; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:81 */ +.x-monthpicker-yearnav-button { + display: inline-block; + outline: none; + font-size: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:87 */ +.x-monthpicker-buttons { + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:91 */ +.x-datepicker .x-monthpicker-buttons { + position: absolute; + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Date.scss:96 */ +.x-datepicker-month .x-btn-split > .x-btn-button:after { + content: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Display.scss:1 */ +.x-form-display-field-body { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Display.scss:3 */ +.x-form-display-field-body .x-form-display-field { + overflow-wrap: break-word; + word-wrap: break-word; + -ms-word-break: break-all; + /* This is dangerous in WebKit as it breaks things at random points */ + word-break: break-all; + /* Use this non-standard instead */ + word-break: break-word; + /* Adds a hyphen where the word breaks, if supported (No Blink) */ + -ms-hyphens: auto; + -moz-hyphens: auto; + -webkit-hyphens: auto; + hyphens: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/trigger/Component.scss:3 */ +.x-form-trigger.x-form-trigger-cmp:before { + content: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/File.scss:1 */ +.x-form-file-btn { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/File.scss:6 */ +.x-form-file-input { + border: 0; + position: absolute; + cursor: pointer; + top: 0; + right: 0; + width: 100%; + height: 100%; + overflow: hidden; + text-indent: -10000px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; + /* Yes, there's actually a good reason for this... + * If the configured buttonText is set to something longer than the default, + * then it will quickly exceed the width of the hidden file input's "Browse..." + * button, so part of the custom button's clickable area will be covered by + * the hidden file input's text box instead. This results in a text-selection + * mouse cursor over that part of the button, at least in Firefox, which is + * confusing to a user. Giving the hidden file input a huge font-size makes + * the native button part very large so it will cover the whole clickable area. + */ + font-size: 1000px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Hidden.scss:1 */ +.x-form-item-hidden { + margin: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tip/Tip.scss:1 */ +.x-tip { + position: absolute; + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tip/Tip.scss:6 */ +.x-tip-body { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tip/Tip.scss:11 */ +.x-tip-anchor { + position: absolute; + border-style: solid; + height: 0; + width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Color.scss:1 */ +.x-color-picker-item { + float: left; + text-decoration: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/picker/Color.scss:6 */ +.x-color-picker-item-inner { + display: block; + font-size: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/HtmlEditor.scss:1 */ +.x-html-editor-tb .x-toolbar { + position: static !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/HtmlEditor.scss:5 */ +.x-htmleditor-iframe, +.x-htmleditor-textarea { + display: block; + overflow: auto; + width: 100%; + height: 100%; + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:1 */ +.x-tagfield-body { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:5 */ +.x-tagfield { + height: auto!important; + /* The wrap has to accommodate the list, so override the .x-form-text height rule */ + cursor: text; + overflow-y: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:11 */ +.x-tagfield .x-tagfield-list { + padding: 0; + margin: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:16 */ +.x-tagfield-list.x-tagfield-singleselect { + white-space: nowrap; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:21 */ +.x-tagfield-input, +.x-tagfield-item { + vertical-align: top; + display: inline-block; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:27 */ +.x-tagfield-input-field { + font: inherit; + border: 0; + margin: 0; + background: none; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:35 */ +.x-tagfield-stacked .x-tagfield-item { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:39 */ +.x-tagfield-item { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:43 */ +.x-tagfield-item-close { + cursor: pointer; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:48 */ +.x-tagfield-arialist { + list-style-type: none; + position: absolute; + clip: rect(0, 0, 0, 0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/form/field/Tag.scss:54 */ +.x-tagfield-arialist-item { + list-style-type: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Fit.scss:1 */ +.x-fit-item { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:1 */ +.x-grid-view { + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:11 */ +.x-grid-row-table { + /* A grid *item* is a dataview item. It is encapsulated by a
. + * One item always corresponds to one store record + * But an item may contain more than one . + * ONE child row, will be the grid-row and will contain record data + */ + width: 0; + table-layout: fixed; + border: 0 none; + border-collapse: separate; + border-spacing: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:25 */ +.x-grid-item { + table-layout: fixed; + outline: none; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:34 */ +.x-ie10 .x-grid-item { + transform: translateZ(0); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:39 */ +.x-grid-row { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:43 */ +.x-grid-td { + overflow: hidden; + border-width: 0; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:49 */ +.x-grid-cell-inner { + overflow: hidden; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:55 */ +.x-wrap-cell .x-grid-cell-inner { + white-space: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/panel/Table.scss:60 */ +.x-grid-resize-marker { + position: absolute; + z-index: 5; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/view/Table.scss:3 */ +.x-grid-item-container { + min-height: 1px; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/header/DropZone.scss:1 */ +.x-col-move-top, +.x-col-move-bottom { + position: absolute; + top: 0; + line-height: 0; + font-size: 0; + overflow: hidden; + z-index: 20000; + background: no-repeat center top transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/header/Container.scss:1 */ +.x-grid-header-ct { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:1 */ +.x-column-header { + position: absolute; + overflow: hidden; + background-repeat: repeat-x; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:11 */ +.x-column-header-inner { + /* + * TODO: + * When IE8 retires, revisit https://jsbin.com/honawo/quiet for better way to center header text + */ + white-space: nowrap; + position: relative; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:17 */ +.x-leaf-column-header { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:19 */ +.x-leaf-column-header .x-column-header-text-container { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:26 */ +.x-column-header-text-container { + width: 100%; + display: table; + table-layout: fixed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:31 */ +.x-column-header-text-container.x-column-header-text-container-auto { + table-layout: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:36 */ +.x-column-header-text-wrapper { + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:41 */ +.x-column-header-text { + display: block; + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:50 */ +.x-column-header-sort-DESC .x-column-header-text, +.x-column-header-sort-ASC .x-column-header-text { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:57 */ +.x-column-header-text-inner { + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:60 */ +.x-column-header-inner-empty .x-column-header-text-inner { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:63 */ +.x-column-header-inner-empty .x-column-header-text-container { + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:76 */ +.x-column-header-trigger { + display: none; + height: 100%; + background-repeat: no-repeat; + position: absolute; + right: 0; + top: 0; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:86 */ +.x-ie9m .x-column-header-trigger { + z-index: 6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:101 */ +.x-column-header-over .x-column-header-trigger, +.x-column-header-open .x-column-header-trigger { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:106 */ +.x-column-header-align-right { + text-align: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:116 */ +.x-column-header-align-left { + text-align: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Column.scss:126 */ +.x-column-header-align-center { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Action.scss:1 */ +.x-grid-cell-inner-action-col { + line-height: 0; + font-size: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Action.scss:6 */ +.x-keyboard-mode .x-grid-cell-inner-action-col :focus { + outline: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Action.scss:12 */ +.x-action-col-icon { + display: inline-block; + line-height: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Check.scss:4 */ +.x-column-header-checkbox .x-column-header-text { + margin-bottom: 0.4em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Check.scss:9 */ +.x-column-header-checkbox .x-column-header-inner-empty .x-column-header-text { + margin-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Check.scss:15 */ +.x-grid-checkcolumn-cell-inner { + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/column/Check.scss:19 */ +.x-keyboard-mode .x-grid-checkcolumn-cell-inner :focus { + outline: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/Grouping.scss:1 */ +.x-group-hd-container { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/Grouping.scss:5 */ +.x-grid-group-hd { + white-space: nowrap; + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/Grouping.scss:10 */ +.x-grid-group-title { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/Grouping.scss:14 */ +.x-grid-group-title:before { + position: absolute; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/Grouping.scss:29 */ +.x-grid-row-body-hidden, +.x-grid-group-collapsed { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/feature/RowBody.scss:1 */ +.x-grid-row-body-hidden { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:1 */ +.x-menu { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:5 */ +.x-menu-body { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:9 */ +.x-menu-item { + white-space: nowrap; + overflow: hidden; + border-color: transparent; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:17 */ +.x-menu-item-cmp { + margin: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:20 */ +.x-menu-item-cmp .x-field-label-cell { + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:28 */ +.x-menu-icon-separator { + position: absolute; + top: 0px; + z-index: 0; + height: 100%; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:34 */ +.x-menu-plain .x-menu-icon-separator { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:39 */ +.x-menu-item-link { + -webkit-tap-highlight-color: transparent; + -webkit-touch-callout: none; + text-decoration: none; + outline: 0; + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:54 */ +.x-menu-item-link-href { + -webkit-touch-callout: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:58 */ +.x-menu-item-text { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/menu/Menu.scss:62 */ +.x-menu-item-icon, +.x-menu-item-icon-right, +.x-menu-item-arrow { + font-size: 0; + position: absolute; + text-align: center; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:1 */ +.x-grid-scroll-container { + position: absolute; + z-index: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:7 */ +.x-grid-scrollbar-clipper-floated, +.x-grid-scrollbar-floated { + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:12 */ +.x-grid-scroll-body { + width: 100%; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:17 */ +.x-grid-scrollbar-clipper { + overflow: hidden; + position: absolute; + top: 0; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:23 */ +.x-grid-scrollbar-clipper > .x-grid-view, +.x-grid-scrollbar-clipper > .x-tree-view { + overflow-y: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:29 */ +.x-grid-with-col-lines .x-grid-scrollbar-clipper-locked .x-grid-cell-last { + border-right-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:43 */ +.x-grid-scrollbar { + position: absolute; + bottom: 0; + left: 0; + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:56 */ +.x-grid-scrollbar-visible { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:61 */ +.x-grid-locking-body > .x-grid { + z-index: 2; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:65 */ +.x-grid-locking-body > .x-grid .x-docked { + pointer-events: auto; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:70 */ +.x-grid-locking-body .x-grid-body { + background: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:74 */ +.x-grid-locking-body > .x-splitter { + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:80 */ +.x-grid-locking-body > .x-splitter-active { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:84 */ +.x-grid-locking-body > .x-splitter-focus { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:90 */ +.x-grid-inner-locked.x-border-region-slide-in { + z-index: 3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/locking/Lockable.scss:92 */ +.x-grid-inner-locked.x-border-region-slide-in > .x-panel-bodyWrap > .x-grid-body > .x-grid-view, +.x-grid-inner-locked.x-border-region-slide-in > .x-panel-bodyWrap > .x-grid-body > .x-tree-view { + overflow-y: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/Editing.scss:7 */ +.x-grid-editor .x-form-cb-wrap { + /* + * Rules for fields which are rendered to fit inside grid cells. + * This includes cell and row editor fields and fields in widget columns. + */ + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/Editing.scss:12 */ +.x-grid-editor .x-form-cb { + position: static; + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/Editing.scss:20 */ +.x-grid-editor .x-form-display-field { + margin: 0; + white-space: nowrap; + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/Editing.scss:28 */ +.x-grid-editor div.x-form-action-col-field { + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowEditing.scss:1 */ +.x-grid-row-editor-wrap { + position: absolute; + overflow: visible; + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowEditing.scss:8 */ +.x-grid-row-editor { + position: absolute; + z-index: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowEditing.scss:15 */ +.x-grid-row-editor-buttons { + position: absolute; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowExpander.scss:1 */ +.x-grid-row-expander { + font-size: 0; + line-height: 0; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowExpander.scss:8 */ +.x-keyboard-mode .x-grid-row-expander:focus { + outline: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowExpander.scss:13 */ +.x-grid-hide-row-expander-spacer .x-grid-row-expander-spacer { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/plugin/RowExpander.scss:17 */ +.x-grid-row-expander-spacer { + border: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:1 */ +.x-ssm-row-numberer-hd { + cursor: se-resize!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:6 */ +.x-ssm-row-numberer-cell { + cursor: e-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:11 */ +.x-ssm-column-select .x-column-header { + cursor: s-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:16 */ +.x-ssm-extender-drag-handle { + position: absolute; + z-index: 1; + cursor: crosshair; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/grid/selection/SpreadsheetModel.scss:22 */ +.x-ssm-extender-mask { + position: absolute; + z-index: 1; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Absolute.scss:1 */ +.x-abs-layout-ct { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Absolute.scss:5 */ +.x-abs-layout-item { + position: absolute !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Border.scss:1 */ +.x-border-layout-ct { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Border.scss:5 */ +.x-border-layout-ct { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Border.scss:9 */ +.x-border-region-slide-in { + z-index: 6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Border.scss:13 */ +.x-region-collapsed-placeholder { + z-index: 4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Center.scss:1 */ +.x-center-layout-item { + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Center.scss:5 */ +.x-center-target { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:1 */ +.x-form-layout-wrap { + display: table; + width: 100%; + border-collapse: separate; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:7 */ +.x-form-layout-colgroup { + display: table-column-group; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:11 */ +.x-form-layout-column { + display: table-column; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:16 */ +.x-form-layout-auto-label > * > .x-form-item-label { + width: auto !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:20 */ +.x-form-layout-auto-label > * > .x-form-item-label > .x-form-item-label-inner { + width: auto !important; + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:26 */ +.x-form-layout-auto-label > * > .x-form-layout-label-column { + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:33 */ +.x-form-layout-sized-label > * > .x-form-item-label { + width: auto !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:40 */ +.x-form-form-item { + display: table-row; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:43 */ +.x-form-form-item > .x-form-item-label { + padding-left: 0 !important; + padding-right: 0 !important; + padding-bottom: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:51 */ +.x-form-form-item > .x-form-item-body { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/layout/container/Form.scss:60 */ +.x-form-form-item.x-form-item-no-label:before { + content: ' '; + display: table-cell; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/resizer/Resizer.scss:2 */ +.x-resizable-wrapped { + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:1 */ +.x-slider { + outline: none; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:6 */ +.x-slider-inner { + position: relative; + left: 0; + top: 0; + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:11 */ +.x-slider-vert .x-slider-inner { + background: repeat-y 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:16 */ +.x-slider-thumb { + position: absolute; + background: no-repeat 0 0; + cursor: default; + -webkit-user-callout: none; + display: table; + table-layout: fixed; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:19 */ +.x-slider-horz .x-slider-thumb { + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:22 */ +.x-slider-vert .x-slider-thumb { + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/slider/Multi.scss:35 */ +.x-slider-thumb:before { + display: table-cell; + vertical-align: middle; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:21 */ +.x-tab { + display: block; + outline: 0; + cursor: pointer; + white-space: nowrap; + text-decoration: none; + vertical-align: top; + overflow: hidden; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:33 */ +.x-tab > .x-frame { + height: 100%; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:39 */ +.x-tab-wrap { + height: 100%; + width: 100%; + display: table; + border-spacing: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:64 */ +.x-tab-button { + white-space: nowrap; + line-height: 0; + position: relative; + display: table-cell; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:103 */ +.x-tab-inner { + overflow: hidden; + text-overflow: ellipsis; + display: inline-block; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:122 */ +.x-tab-icon.x-tab-no-text > .x-tab-inner { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:127 */ +.x-tab-icon-el { + display: none; + vertical-align: middle; + text-align: center; + background-position: center center; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:148 */ +.x-tab-icon > .x-tab-icon-el { + display: inline-block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:152 */ +.x-tab-icon-top > .x-tab-icon-el, +.x-tab-icon-bottom > .x-tab-icon-el { + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:161 */ +.x-ie9m .x-tab-button-center { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:169 */ +.x-tab-button-center.x-tab-icon-top, +.x-tab-button-center.x-tab-icon-bottom { + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:175 */ +.x-tab-button-left { + text-align: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:188 */ +.x-tab-button-right { + text-align: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/var/button/Button.scss:297 */ +.x-tab-mc { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:13 */ +.x-tab { + z-index: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:17 */ +.x-tab-active { + z-index: 3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:21 */ +.x-tab-button { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:27 */ +.x-tab-close-btn { + display: block; + position: absolute; + overflow: hidden; + font-size: 0; + line-height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:35 */ +.x-tab-rotate-left { + -webkit-transform: rotate(270deg); + -webkit-transform-origin: 100% 0; + -moz-transform: rotate(270deg); + -moz-transform-origin: 100% 0; + -ms-transform: rotate(270deg); + -ms-transform-origin: 100% 0; + transform: rotate(270deg); + transform-origin: 100% 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/rotate-element.scss:41 */ +.x-ie8 .x-tab-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:45 */ +.x-tab-rotate-right { + -webkit-transform: rotate(90deg); + -webkit-transform-origin: 0 0; + -moz-transform: rotate(90deg); + -moz-transform-origin: 0 0; + -ms-transform: rotate(90deg); + -ms-transform-origin: 0 0; + transform: rotate(90deg); + transform-origin: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/rotate-element.scss:41 */ +.x-ie8 .x-tab-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Tab.scss:57 */ +.x-tab-tr, +.x-tab-br, +.x-tab-mr, +.x-tab-tl, +.x-tab-bl, +.x-tab-ml { + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:1 */ +.x-tab-bar { + z-index: 0; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:6 */ +.x-tab-bar-strip { + position: absolute; + line-height: 0; + font-size: 0; + z-index: 2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:12 */ +.x-tab-bar-top > .x-tab-bar-strip { + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:16 */ +.x-tab-bar-bottom > .x-tab-bar-strip { + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:20 */ +.x-tab-bar-left > .x-tab-bar-strip { + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:31 */ +.x-tab-bar-right > .x-tab-bar-strip { + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:43 */ +.x-tab-bar-horizontal .x-tab-bar-strip { + width: 100%; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:48 */ +.x-tab-bar-vertical { + display: table-cell; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:54 */ +.x-tab-bar-vertical .x-tab-bar-strip { + height: 100%; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:60 */ +.x-tab-bar-plain { + background: transparent !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tab/Bar.scss:64 */ +.x-box-scroller-plain { + background-color: transparent !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Breadcrumb.scss:1 */ +.x-breadcrumb-btn .x-box-target:first-child { + margin: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Breadcrumb.scss:7 */ +.x-breadcrumb-btn > .x-btn-split-right > .x-btn-button:after { + content: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/toolbar/Breadcrumb.scss:12 */ +.x-breadcrumb-btn.x-btn-over > .x-btn-split-right > .x-btn-button:after, +.x-breadcrumb-btn.x-btn-menu-active > .x-btn-split-right > .x-btn-button:after { + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:4 */ +.x-autowidth-table .x-grid-item-container { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:8 */ +.x-autowidth-table .x-grid-item { + table-layout: auto; + width: auto !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:14 */ +.x-tree-view { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:18 */ +.x-tree-elbow-img, +.x-tree-icon { + display: inline-block; + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:27 */ +.x-tree-checkbox { + display: inline-block; + vertical-align: top; + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/src/tree/View.scss:33 */ +.x-tree-animator-wrap { + overflow: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/Component.scss:1 */ +.x-body { + color: #404040; + font-size: 13px; + line-height: 17px; + font-weight: 300; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + background: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/Component.scss:18 */ +.x-animating-size, +.x-collapsed { + overflow: hidden!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/Component.scss:25 */ +.x-animating-size { + z-index: 10000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/Editor.scss:2 */ +.x-editor .x-form-item-body { + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:1 */ +.x-mask { + background-image: none; + background-color: rgba(208, 208, 208, 0.5); + cursor: default; + border-style: solid; + border-width: 1px; + border-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/background-opacity.scss:19 */ +.x-ie8 .x-mask { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#80d0d0d0, endColorstr=#80d0d0d0)"; + zoom: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:16 */ +body > .x-mask { + background-image: none; + background-color: rgba(0, 0, 0, 0.75); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/background-opacity.scss:19 */ +.x-ie8 body > .x-mask { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#bf000000, endColorstr=#bf000000)"; + zoom: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:23 */ +.x-keyboard-mode .x-mask.x-focus { + border-style: solid; + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:31 */ +.x-mask-msg { + padding: 10px; + background: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:49 */ +.x-mask-msg-inner { + padding: 0; + background-color: transparent; + color: #404040; + font: 300 13px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/LoadMask.scss:61 */ +.x-mask-msg-text { + padding: 25px 0 0; + background-image: url(images/loadmask/loading.gif); + background-repeat: no-repeat; + background-position: center 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:219 */ +.x-progress-default { + background-color: #ececec; + border-width: 0; + height: 24px; + border-color: #5fa2dd; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:234 */ +.x-progress-default .x-progress-bar-default { + background-image: none; + background-color: #7fb5e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:249 */ +.x-progress-default .x-progress-text { + color: #fff; + font-weight: 400; + font-size: 13px; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + text-align: center; + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:258 */ +.x-progress-default .x-progress-text-back { + color: #404040; + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-keyboard-mode .x-progress-default.x-progress-focus:after { + position: absolute; + content: ' '; + top: 0; + right: 0; + bottom: 0; + left: 0; + border: 0 solid #5fa2dd; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:285 */ +.x-progressbar-default-cell > .x-grid-cell-inner, +.x-progress-default-cell > .x-grid-cell-inner, +.x-progressbarwidget-default-cell > .x-grid-cell-inner { + padding-top: 4px; + padding-bottom: 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/ProgressBar.scss:288 */ +.x-progressbar-default-cell > .x-grid-cell-inner .x-progress-default, +.x-progress-default-cell > .x-grid-cell-inner .x-progress-default, +.x-progressbarwidget-default-cell > .x-grid-cell-inner .x-progress-default { + height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-small-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-small-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-small-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-small-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-small-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-small-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-small-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-small-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-small-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-small-tr, +.x-btn-default-small-br, +.x-btn-default-small-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-small-tl, +.x-btn-default-small-bl, +.x-btn-default-small-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-small-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-small-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-small-tl, +.x-btn-default-small-bl, +.x-btn-default-small-tr, +.x-btn-default-small-br, +.x-btn-default-small-tc, +.x-btn-default-small-bc, +.x-btn-default-small-ml, +.x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-small-ml, +.x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-small-mc { + padding: 7px 7px 7px 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-small { + border-color: #5897ce; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-small { + min-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-small { + min-height: auto; + height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-small { + font: 400 12px/16px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-small { + max-width: calc(100% - 16px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-small { + max-width: calc(100% - 15px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-small { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-small, +.x-btn-icon-right > .x-btn-icon-el-default-small { + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-small, +.x-btn-icon-bottom > .x-btn-icon-el-default-small { + min-width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-small.x-btn-glyph { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-small { + margin-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small { + margin-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-small { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-small { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-small, +.x-btn-split-bottom > .x-btn-button-default-small { + padding-bottom: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-default-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-default-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-default-small.x-btn-split-bottom { + margin-bottom: -7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-default-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-small { + background-image: none; + background-color: #5fa2dd; + -webkit-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + -moz-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #d3e0ec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-small { + border-color: #518bbd; + background-image: none; + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-small { + -webkit-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + -moz-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-small, +.x-btn.x-btn-pressed.x-btn-default-small { + border-color: #42719a; + background-image: none; + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-small { + -webkit-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + -moz-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-small { + background-image: none; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-small-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-small-tl, +.x-btn-over .x-btn-default-small-bl, +.x-btn-over .x-btn-default-small-tr, +.x-btn-over .x-btn-default-small-br, +.x-btn-over .x-btn-default-small-tc, +.x-btn-over .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-small-ml, +.x-btn-over .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-small-mc { + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mc { + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-small-tl, +.x-btn.x-btn-menu-active .x-btn-default-small-bl, +.x-btn.x-btn-menu-active .x-btn-default-small-tr, +.x-btn.x-btn-menu-active .x-btn-default-small-br, +.x-btn.x-btn-menu-active .x-btn-default-small-tc, +.x-btn.x-btn-menu-active .x-btn-default-small-bc, +.x-btn.x-btn-pressed .x-btn-default-small-tl, +.x-btn.x-btn-pressed .x-btn-default-small-bl, +.x-btn.x-btn-pressed .x-btn-default-small-tr, +.x-btn.x-btn-pressed .x-btn-default-small-br, +.x-btn.x-btn-pressed .x-btn-default-small-tc, +.x-btn.x-btn-pressed .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-small-ml, +.x-btn.x-btn-menu-active .x-btn-default-small-mr, +.x-btn.x-btn-pressed .x-btn-default-small-ml, +.x-btn.x-btn-pressed .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-small-mc, +.x-btn.x-btn-pressed .x-btn-default-small-mc { + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mc { + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-small-tl, +.x-btn.x-btn-disabled .x-btn-default-small-bl, +.x-btn.x-btn-disabled .x-btn-default-small-tr, +.x-btn.x-btn-disabled .x-btn-default-small-br, +.x-btn.x-btn-disabled .x-btn-default-small-tc, +.x-btn.x-btn-disabled .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-small-ml, +.x-btn.x-btn-disabled .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-small-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-small { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first .x-btn-default-small-mc { + padding-right: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle .x-btn-default-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last .x-btn-default-small-mc { + padding-left: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first .x-btn-default-small-mc { + padding-bottom: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle .x-btn-default-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last .x-btn-default-small-mc { + padding-top: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-small:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-small:after { + border-width: 1px; + border-color: #d3e0ec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-small:after { + border-width: 1px; + border-color: #d1dee9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-small:after { + border-width: 1px; + border-color: #ced8e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-small-cell > .x-grid-cell-inner >.x-btn-default-small { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-medium { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 8px 8px 8px; + border-width: 1px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-medium-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-medium-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-8-8-8-8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-medium-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-medium-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-medium-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-medium-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-medium-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-medium-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-medium-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-medium-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-medium-tr, +.x-btn-default-medium-br, +.x-btn-default-medium-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-medium-tl, +.x-btn-default-medium-bl, +.x-btn-default-medium-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-medium-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-medium-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-medium-tl, +.x-btn-default-medium-bl, +.x-btn-default-medium-tr, +.x-btn-default-medium-br, +.x-btn-default-medium-tc, +.x-btn-default-medium-bc, +.x-btn-default-medium-ml, +.x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-medium-ml, +.x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-medium-mc { + padding: 8px 8px 8px 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-medium { + border-color: #5897ce; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-medium { + min-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-medium { + min-height: auto; + height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-medium { + font: 400 14px/18px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #f0f0f0; + padding: 0 8px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-medium { + max-width: calc(100% - 20px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-medium { + max-width: calc(100% - 19px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-medium { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-medium { + font-size: 20px; + height: 20px; + color: #f0f0f0; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-medium, +.x-btn-icon-right > .x-btn-icon-el-default-medium { + width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-medium, +.x-btn-icon-bottom > .x-btn-icon-el-default-medium { + min-width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-medium.x-btn-glyph { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-medium { + margin-right: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium { + margin-left: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-medium { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-medium { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-medium, +.x-btn-split-bottom > .x-btn-button-default-medium { + padding-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-medium.x-btn-arrow-right:after { + width: 20px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-medium.x-btn-arrow-bottom:after { + height: 14px; + content: "\f0d7"; + font: 20px/14px FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-default-medium.x-btn-split-right > .x-btn-button { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-default-medium.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-medium.x-btn-split-right:after { + width: 26px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #f0f0f0; + padding-left: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-default-medium.x-btn-split-bottom { + margin-bottom: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-default-medium.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-medium.x-btn-split-bottom:after { + height: 24px; + content: "\f0d7"; + font: 20px/24px FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-medium { + background-image: none; + background-color: #5fa2dd; + -webkit-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + -moz-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 34px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #d3e0ec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-medium { + border-color: #518bbd; + background-image: none; + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-medium { + -webkit-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + -moz-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-medium, +.x-btn.x-btn-pressed.x-btn-default-medium { + border-color: #42719a; + background-image: none; + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-medium { + -webkit-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + -moz-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-medium { + background-image: none; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-medium-tl, +.x-btn-over .x-btn-default-medium-bl, +.x-btn-over .x-btn-default-medium-tr, +.x-btn-over .x-btn-default-medium-br, +.x-btn-over .x-btn-default-medium-tc, +.x-btn-over .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-medium-ml, +.x-btn-over .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-medium-mc { + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mc { + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-medium-tl, +.x-btn.x-btn-menu-active .x-btn-default-medium-bl, +.x-btn.x-btn-menu-active .x-btn-default-medium-tr, +.x-btn.x-btn-menu-active .x-btn-default-medium-br, +.x-btn.x-btn-menu-active .x-btn-default-medium-tc, +.x-btn.x-btn-menu-active .x-btn-default-medium-bc, +.x-btn.x-btn-pressed .x-btn-default-medium-tl, +.x-btn.x-btn-pressed .x-btn-default-medium-bl, +.x-btn.x-btn-pressed .x-btn-default-medium-tr, +.x-btn.x-btn-pressed .x-btn-default-medium-br, +.x-btn.x-btn-pressed .x-btn-default-medium-tc, +.x-btn.x-btn-pressed .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-medium-ml, +.x-btn.x-btn-menu-active .x-btn-default-medium-mr, +.x-btn.x-btn-pressed .x-btn-default-medium-ml, +.x-btn.x-btn-pressed .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-medium-mc, +.x-btn.x-btn-pressed .x-btn-default-medium-mc { + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mc { + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-medium-tl, +.x-btn.x-btn-disabled .x-btn-default-medium-bl, +.x-btn.x-btn-disabled .x-btn-default-medium-tr, +.x-btn.x-btn-disabled .x-btn-default-medium-br, +.x-btn.x-btn-disabled .x-btn-default-medium-tc, +.x-btn.x-btn-disabled .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-medium-ml, +.x-btn.x-btn-disabled .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-medium-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-medium { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-medium { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first .x-btn-default-medium-mc { + padding-right: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle .x-btn-default-medium-mc { + padding-right: 8px !important; + padding-left: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last .x-btn-default-medium-mc { + padding-left: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first .x-btn-default-medium-mc { + padding-bottom: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle .x-btn-default-medium-mc { + padding-top: 8px !important; + padding-bottom: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last .x-btn-default-medium-mc { + padding-top: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-medium:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-medium:after { + border-width: 1px; + border-color: #d3e0ec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-medium:after { + border-width: 1px; + border-color: #d1dee9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-medium:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-medium:after { + border-width: 1px; + border-color: #ced8e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-medium-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-medium-cell > .x-grid-cell-inner >.x-btn-default-medium { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-large-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-large-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-large-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-large-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-large-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-large-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-large-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-large-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-large-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-large-tr, +.x-btn-default-large-br, +.x-btn-default-large-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-large-tl, +.x-btn-default-large-bl, +.x-btn-default-large-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-large-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-large-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-large-tl, +.x-btn-default-large-bl, +.x-btn-default-large-tr, +.x-btn-default-large-br, +.x-btn-default-large-tc, +.x-btn-default-large-bc, +.x-btn-default-large-ml, +.x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-large-ml, +.x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-large-mc { + padding: 9px 9px 9px 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-large { + border-color: #5897ce; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-large { + min-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-large { + min-height: auto; + height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-large { + font: 400 16px/20px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #f0f0f0; + padding: 0 10px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-large { + max-width: calc(100% - 24px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-large { + max-width: calc(100% - 23px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-large { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-large { + font-size: 24px; + height: 24px; + color: #f0f0f0; + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-large, +.x-btn-icon-right > .x-btn-icon-el-default-large { + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-large, +.x-btn-icon-bottom > .x-btn-icon-el-default-large { + min-width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-large.x-btn-glyph { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-large { + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-large { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-large { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-large, +.x-btn-split-bottom > .x-btn-button-default-large { + padding-bottom: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-default-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-default-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; + padding-left: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-default-large.x-btn-split-bottom { + margin-bottom: -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-default-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-large { + background-image: none; + background-color: #5fa2dd; + -webkit-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + -moz-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #d3e0ec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-large { + border-color: #518bbd; + background-image: none; + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-large { + -webkit-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + -moz-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-large, +.x-btn.x-btn-pressed.x-btn-default-large { + border-color: #42719a; + background-image: none; + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-large { + -webkit-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + -moz-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-large { + background-image: none; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-large-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-large-tl, +.x-btn-over .x-btn-default-large-bl, +.x-btn-over .x-btn-default-large-tr, +.x-btn-over .x-btn-default-large-br, +.x-btn-over .x-btn-default-large-tc, +.x-btn-over .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-large-ml, +.x-btn-over .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-large-mc { + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mc { + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-large-tl, +.x-btn.x-btn-menu-active .x-btn-default-large-bl, +.x-btn.x-btn-menu-active .x-btn-default-large-tr, +.x-btn.x-btn-menu-active .x-btn-default-large-br, +.x-btn.x-btn-menu-active .x-btn-default-large-tc, +.x-btn.x-btn-menu-active .x-btn-default-large-bc, +.x-btn.x-btn-pressed .x-btn-default-large-tl, +.x-btn.x-btn-pressed .x-btn-default-large-bl, +.x-btn.x-btn-pressed .x-btn-default-large-tr, +.x-btn.x-btn-pressed .x-btn-default-large-br, +.x-btn.x-btn-pressed .x-btn-default-large-tc, +.x-btn.x-btn-pressed .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-large-ml, +.x-btn.x-btn-menu-active .x-btn-default-large-mr, +.x-btn.x-btn-pressed .x-btn-default-large-ml, +.x-btn.x-btn-pressed .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-large-mc, +.x-btn.x-btn-pressed .x-btn-default-large-mc { + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mc { + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-large-tl, +.x-btn.x-btn-disabled .x-btn-default-large-bl, +.x-btn.x-btn-disabled .x-btn-default-large-tr, +.x-btn.x-btn-disabled .x-btn-default-large-br, +.x-btn.x-btn-disabled .x-btn-default-large-tc, +.x-btn.x-btn-disabled .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-large-ml, +.x-btn.x-btn-disabled .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-large-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-large { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first .x-btn-default-large-mc { + padding-right: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle .x-btn-default-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last .x-btn-default-large-mc { + padding-left: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first .x-btn-default-large-mc { + padding-bottom: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle .x-btn-default-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last .x-btn-default-large-mc { + padding-top: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-large:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-large:after { + border-width: 1px; + border-color: #d3e0ec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-large:after { + border-width: 1px; + border-color: #d1dee9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-large:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-large:after { + border-width: 1px; + border-color: #ced8e1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-large-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-large-cell > .x-grid-cell-inner >.x-btn-default-large { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-toolbar-small-mc { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-toolbar-small-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-toolbar-small-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-toolbar-small-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-toolbar-small-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-toolbar-small-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-toolbar-small-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-toolbar-small-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-toolbar-small-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-toolbar-small-tr, +.x-btn-default-toolbar-small-br, +.x-btn-default-toolbar-small-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-toolbar-small-tl, +.x-btn-default-toolbar-small-bl, +.x-btn-default-toolbar-small-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-toolbar-small-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-toolbar-small-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-toolbar-small-tl, +.x-btn-default-toolbar-small-bl, +.x-btn-default-toolbar-small-tr, +.x-btn-default-toolbar-small-br, +.x-btn-default-toolbar-small-tc, +.x-btn-default-toolbar-small-bc, +.x-btn-default-toolbar-small-ml, +.x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-toolbar-small-ml, +.x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-toolbar-small { + border-color: #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-toolbar-small { + min-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-toolbar-small { + min-height: auto; + height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-toolbar-small { + font: 400 12px/16px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-small { + max-width: calc(100% - 16px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-small { + max-width: calc(100% - 15px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-toolbar-small { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small { + min-width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-toolbar-small.x-btn-glyph { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small { + margin-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + margin-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-small, +.x-btn-split-bottom > .x-btn-button-default-toolbar-small { + padding-bottom: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-default-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-default-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-small { + background-image: none; + background-color: #f6f6f6; + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-toolbar-small { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-small { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-toolbar-small, +.x-btn.x-btn-pressed.x-btn-default-toolbar-small { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-toolbar-small { + background-image: none; + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mc { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-toolbar-small-tl, +.x-btn-over .x-btn-default-toolbar-small-bl, +.x-btn-over .x-btn-default-toolbar-small-tr, +.x-btn-over .x-btn-default-toolbar-small-br, +.x-btn-over .x-btn-default-toolbar-small-tc, +.x-btn-over .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-toolbar-small-ml, +.x-btn-over .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-toolbar-small-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mc { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-toolbar-small { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first .x-btn-default-toolbar-small-mc { + padding-right: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle .x-btn-default-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last .x-btn-default-toolbar-small-mc { + padding-left: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first .x-btn-default-toolbar-small-mc { + padding-bottom: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle .x-btn-default-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last .x-btn-default-toolbar-small-mc { + padding-top: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-small:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-toolbar-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-toolbar-small-cell > .x-grid-cell-inner >.x-btn-default-toolbar-small { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-toolbar-medium { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 8px 8px 8px; + border-width: 1px; + border-style: solid; + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-toolbar-medium-mc { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-toolbar-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-toolbar-medium-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-8-8-8-8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-toolbar-medium-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-toolbar-medium-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-toolbar-medium-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-toolbar-medium-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-toolbar-medium-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-toolbar-medium-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-toolbar-medium-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-toolbar-medium-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-toolbar-medium-tr, +.x-btn-default-toolbar-medium-br, +.x-btn-default-toolbar-medium-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-toolbar-medium-tl, +.x-btn-default-toolbar-medium-bl, +.x-btn-default-toolbar-medium-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-toolbar-medium-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-toolbar-medium-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-toolbar-medium-tl, +.x-btn-default-toolbar-medium-bl, +.x-btn-default-toolbar-medium-tr, +.x-btn-default-toolbar-medium-br, +.x-btn-default-toolbar-medium-tc, +.x-btn-default-toolbar-medium-bc, +.x-btn-default-toolbar-medium-ml, +.x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-toolbar-medium-ml, +.x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-toolbar-medium-mc { + padding: 8px 8px 8px 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-toolbar-medium { + border-color: #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-toolbar-medium { + min-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-toolbar-medium { + min-height: auto; + height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-toolbar-medium { + font: 400 14px/18px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 8px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-medium { + max-width: calc(100% - 20px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-medium { + max-width: calc(100% - 19px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-toolbar-medium { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-toolbar-medium { + font-size: 20px; + height: 20px; + color: #919191; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium { + min-width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-toolbar-medium.x-btn-glyph { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium { + margin-right: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + margin-left: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-medium, +.x-btn-split-bottom > .x-btn-button-default-toolbar-medium { + padding-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-toolbar-medium.x-btn-arrow-right:after { + width: 20px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-toolbar-medium.x-btn-arrow-bottom:after { + height: 14px; + content: "\f0d7"; + font: 20px/14px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-default-toolbar-medium.x-btn-split-right > .x-btn-button { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-default-toolbar-medium.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-toolbar-medium.x-btn-split-right:after { + width: 26px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; + padding-left: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom { + margin-bottom: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom:after { + height: 24px; + content: "\f0d7"; + font: 20px/24px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-medium { + background-image: none; + background-color: #f6f6f6; + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-toolbar-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 34px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-toolbar-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-toolbar-medium { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-medium { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-toolbar-medium, +.x-btn.x-btn-pressed.x-btn-default-toolbar-medium { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-toolbar-medium { + background-image: none; + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mc { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-toolbar-medium-tl, +.x-btn-over .x-btn-default-toolbar-medium-bl, +.x-btn-over .x-btn-default-toolbar-medium-tr, +.x-btn-over .x-btn-default-toolbar-medium-br, +.x-btn-over .x-btn-default-toolbar-medium-tc, +.x-btn-over .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-toolbar-medium-ml, +.x-btn-over .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-toolbar-medium-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mc { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-toolbar-medium { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-toolbar-medium { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first .x-btn-default-toolbar-medium-mc { + padding-right: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle .x-btn-default-toolbar-medium-mc { + padding-right: 8px !important; + padding-left: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last .x-btn-default-toolbar-medium-mc { + padding-left: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first .x-btn-default-toolbar-medium-mc { + padding-bottom: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle .x-btn-default-toolbar-medium-mc { + padding-top: 8px !important; + padding-bottom: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last .x-btn-default-toolbar-medium-mc { + padding-top: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-medium:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-toolbar-medium-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-toolbar-medium-cell > .x-grid-cell-inner >.x-btn-default-toolbar-medium { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-default-toolbar-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-default-toolbar-large-mc { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-default-toolbar-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-default-toolbar-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-default-toolbar-large-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-default-toolbar-large-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-default-toolbar-large-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-default-toolbar-large-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-default-toolbar-large-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-default-toolbar-large-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-default-toolbar-large-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-default-toolbar-large-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-default-toolbar-large-tr, +.x-btn-default-toolbar-large-br, +.x-btn-default-toolbar-large-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-default-toolbar-large-tl, +.x-btn-default-toolbar-large-bl, +.x-btn-default-toolbar-large-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-default-toolbar-large-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-default-toolbar-large-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-default-toolbar-large-tl, +.x-btn-default-toolbar-large-bl, +.x-btn-default-toolbar-large-tr, +.x-btn-default-toolbar-large-br, +.x-btn-default-toolbar-large-tc, +.x-btn-default-toolbar-large-bc, +.x-btn-default-toolbar-large-ml, +.x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-default-toolbar-large-ml, +.x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-default-toolbar-large-mc { + padding: 9px 9px 9px 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-default-toolbar-large { + border-color: #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-default-toolbar-large { + min-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-default-toolbar-large { + min-height: auto; + height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-default-toolbar-large { + font: 400 16px/20px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 10px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-large { + max-width: calc(100% - 24px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-large { + max-width: calc(100% - 23px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-default-toolbar-large { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-default-toolbar-large { + font-size: 24px; + height: 24px; + color: #919191; + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large { + min-width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-default-toolbar-large.x-btn-glyph { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large { + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-large, +.x-btn-split-bottom > .x-btn-button-default-toolbar-large { + padding-bottom: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-default-toolbar-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-default-toolbar-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-default-toolbar-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-default-toolbar-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-default-toolbar-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; + padding-left: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom { + margin-bottom: -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-large { + background-image: none; + background-color: #f6f6f6; + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-default-toolbar-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-default-toolbar-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-default-toolbar-large { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-large { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-default-toolbar-large, +.x-btn.x-btn-pressed.x-btn-default-toolbar-large { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-default-toolbar-large { + background-image: none; + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mc { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-default-toolbar-large-tl, +.x-btn-over .x-btn-default-toolbar-large-bl, +.x-btn-over .x-btn-default-toolbar-large-tr, +.x-btn-over .x-btn-default-toolbar-large-br, +.x-btn-over .x-btn-default-toolbar-large-tc, +.x-btn-over .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-default-toolbar-large-ml, +.x-btn-over .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-default-toolbar-large-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mc { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-default-toolbar-large { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-default-toolbar-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first .x-btn-default-toolbar-large-mc { + padding-right: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle .x-btn-default-toolbar-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last .x-btn-default-toolbar-large-mc { + padding-left: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first .x-btn-default-toolbar-large-mc { + padding-bottom: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle .x-btn-default-toolbar-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last .x-btn-default-toolbar-large-mc { + padding-top: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-large:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-default-toolbar-large-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-default-toolbar-large-cell > .x-grid-cell-inner >.x-btn-default-toolbar-large { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:1 */ +.x-tool { + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:5 */ +.x-tool-tool-el { + overflow: hidden; + width: 16px; + height: 16px; + margin: 0; + color: #fff; + text-align: center; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:16 */ +.x-tool-over .x-tool-tool-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:21 */ +.x-tool-pressed .x-tool-tool-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:30 */ +.x-keyboard-mode .x-tool-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-tool-focus, +.x-edge .x-keyboard-mode .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:40 */ +.x-tool-img { + background-image: url(images/tools/tool-sprites.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:44 */ +.x-tool-placeholder { + visibility: hidden; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:48 */ +.x-tool-close { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-close:before { + content: "\f00d"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:57 */ +.x-tool-minimize { + font: 16px/1 ExtJS; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-minimize:before { + content: "\e608"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:66 */ +.x-tool-maximize { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-maximize:before { + content: "\f065"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:75 */ +.x-tool-restore { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-restore:before { + content: "\f066"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:84 */ +.x-tool-toggle { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-toggle:before { + content: "\f077"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:92 */ +.x-panel-collapsed .x-tool-toggle { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-panel-collapsed .x-tool-toggle:before { + content: "\f078"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:102 */ +.x-tool-gear { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-gear:before { + content: "\f013"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:111 */ +.x-tool-prev { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-prev:before { + content: "\f053"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:120 */ +.x-tool-next { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-next:before { + content: "\f054"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:129 */ +.x-tool-pin { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-pin:before { + content: "\f08d"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:138 */ +.x-tool-unpin { + font: 16px/1 ExtJS; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-unpin:before { + content: "\e611"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:147 */ +.x-tool-right { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-right:before { + content: "\f0da"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:156 */ +.x-tool-left { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-left:before { + content: "\f0d9"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:165 */ +.x-tool-down { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-down:before { + content: "\f0d7"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:174 */ +.x-tool-up { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-up:before { + content: "\f0d8"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:183 */ +.x-tool-refresh { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-refresh:before { + content: "\f021"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:192 */ +.x-tool-plus { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-plus:before { + content: "\f067"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:201 */ +.x-tool-minus { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-minus:before { + content: "\f068"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:210 */ +.x-tool-search { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-search:before { + content: "\f002"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:219 */ +.x-tool-save { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-save:before { + content: "\f00c"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:228 */ +.x-tool-help { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-help:before { + content: "\f128"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:237 */ +.x-tool-print { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-print:before { + content: "\f02f"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:246 */ +.x-tool-expand { + font: 16px/1 ExtJS; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-expand:before { + content: "\e600"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:255 */ +.x-tool-collapse { + font: 16px/1 ExtJS; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-collapse:before { + content: "\e606"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:264 */ +.x-tool-resize { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-resize:before { + content: "\f07e"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:273 */ +.x-tool-move { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-move:before { + content: "\f047"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:282 */ +.x-tool-expand-bottom { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-expand-bottom:before { + content: "\f0d7"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:291 */ +.x-tool-collapse-bottom { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-collapse-bottom:before { + content: "\f0d7"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:300 */ +.x-tool-expand-top { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-expand-top:before { + content: "\f0d8"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:309 */ +.x-tool-collapse-top { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-collapse-top:before { + content: "\f0d8"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:318 */ +.x-tool-expand-left { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-expand-left:before { + content: "\f0d9"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:327 */ +.x-tool-collapse-left { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-collapse-left:before { + content: "\f0d9"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:336 */ +.x-tool-expand-right { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-expand-right:before { + content: "\f0da"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Tool.scss:345 */ +.x-tool-collapse-right { + font: 16px/1 FontAwesome; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tool-collapse-right:before { + content: "\f0da"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Header.scss:1 */ +.x-header-draggable, +.x-header-ghost { + cursor: move; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Header.scss:6 */ +.x-header-text { + white-space: nowrap; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:22 */ +.x-collapse-el { + cursor: pointer; + color: #919191; + display: table; + table-layout: fixed; + background-color: #e0e0e0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:31 */ +.x-collapse-el:before { + display: table-cell; + vertical-align: middle; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:46 */ +.x-layout-split-left { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-layout-split-left:before { + content: "\f0d9"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:55 */ +.x-layout-split-right { + font: 16px/1 FontAwesome; + padding: 0 0 0 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-layout-split-right:before { + content: "\f0da"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:86 */ +.x-layout-split-top { + font: 16px/1 FontAwesome; + padding: 0 0 2px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-layout-split-top:before { + content: "\f0d8"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:95 */ +.x-layout-split-bottom { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-layout-split-bottom:before { + content: "\f0d7"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:105 */ +.x-splitter-collapsed .x-layout-split-left { + font: 16px/1 FontAwesome; + padding: 0 0 0 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-splitter-collapsed .x-layout-split-left:before { + content: "\f0da"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:114 */ +.x-splitter-collapsed .x-layout-split-right { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-splitter-collapsed .x-layout-split-right:before { + content: "\f0d9"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:145 */ +.x-splitter-collapsed .x-layout-split-top { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-splitter-collapsed .x-layout-split-top:before { + content: "\f0d7"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:154 */ +.x-splitter-collapsed .x-layout-split-bottom { + font: 16px/1 FontAwesome; + padding: 0 0 2px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-splitter-collapsed .x-layout-split-bottom:before { + content: "\f0d8"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:164 */ +.x-splitter-active { + background-color: #b4b4b4; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:168 */ +.x-splitter-active .x-collapse-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:173 */ +.x-layout-split-left, +.x-layout-split-right { + top: 50%; + margin-top: -24px; + width: 100%; + height: 48px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:184 */ +.x-layout-split-top, +.x-layout-split-bottom { + left: 50%; + width: 48px; + height: 100%; + margin-left: -24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Splitter.scss:199 */ +.x-layout-split-top:before, +.x-layout-split-bottom:before { + width: 100%; + line-height: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-keyboard-mode .x-splitter-focus:after { + position: absolute; + content: ' '; + top: 1px; + right: 1px; + bottom: 1px; + left: 1px; + border: 1px solid #4c82b1; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:598 */ +.x-toolbar-default { + padding: 6px 0 6px 8px; + border-style: solid; + border-color: #d0d0d0; + border-width: 1px; + background-image: none; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:614 */ +.x-toolbar-default .x-tool-img { + color: #919191; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:629 */ +.x-toolbar-default .x-toolbar-item { + margin: 0 8px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:639 */ +.x-toolbar-default .x-toolbar-separator-horizontal { + margin: 0 8px 0 0; + height: 14px; + border-style: solid; + border-width: 0 0 0 1px; + border-left-color: #d0d0d0; + border-right-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:648 */ +.x-toolbar-default .x-box-menu-after { + margin: 0 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:653 */ +.x-toolbar-default-vertical { + padding: 6px 8px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:662 */ +.x-toolbar-default-vertical .x-toolbar-item { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:671 */ +.x-toolbar-default-vertical .x-toolbar-separator-vertical { + margin: 0 5px 6px; + border-style: solid none; + border-width: 1px 0 0; + border-top-color: #d0d0d0; + border-bottom-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:679 */ +.x-toolbar-default-vertical .x-box-menu-after { + margin: 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:694 */ +.x-toolbar-text-default { + padding: 0 4px; + color: #4b4c4c; + font: 300 13px/16px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:700 */ +.x-toolbar-spacer-default { + width: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-toolbar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-toolbar-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-toolbar-default { + cursor: pointer; + color: #919191; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-toolbar-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-toolbar-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-toolbar-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:232 */ +.x-box-scroller-toolbar-default.x-box-scroller-left, +.x-box-scroller-toolbar-default.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:259 */ +.x-box-scroller-toolbar-default.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-toolbar-default.x-box-scroller-left:before { + content: "\f053"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:284 */ +.x-box-scroller-toolbar-default.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-toolbar-default.x-box-scroller-right:before { + content: "\f054"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:311 */ +.x-box-scroller-toolbar-default.x-box-scroller-top, +.x-box-scroller-toolbar-default.x-box-scroller-bottom { + height: 24px; + width: 24px; + left: 50%; + margin-left: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:338 */ +.x-box-scroller-toolbar-default.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-toolbar-default.x-box-scroller-top:before { + content: "\f077"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:363 */ +.x-box-scroller-toolbar-default.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-toolbar-default.x-box-scroller-bottom:before { + content: "\f078"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:742 */ +.x-ie8 .x-box-scroller-toolbar-default { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:748 */ +.x-toolbar-more-icon { + font: 16px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-toolbar-more-icon:before { + content: "\f0c9"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:598 */ +.x-toolbar-footer { + padding: 6px 0 6px 6px; + border-style: solid; + border-color: #d0d0d0; + border-width: 0; + background-image: none; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:614 */ +.x-toolbar-footer .x-tool-img { + color: #919191; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:629 */ +.x-toolbar-footer .x-toolbar-item { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:639 */ +.x-toolbar-footer .x-toolbar-separator-horizontal { + margin: 0 8px 0 0; + height: 14px; + border-style: solid; + border-width: 0 0 0 1px; + border-left-color: #d0d0d0; + border-right-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:648 */ +.x-toolbar-footer .x-box-menu-after { + margin: 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:653 */ +.x-toolbar-footer-vertical { + padding: 6px 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:662 */ +.x-toolbar-footer-vertical .x-toolbar-item { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:671 */ +.x-toolbar-footer-vertical .x-toolbar-separator-vertical { + margin: 0 5px 6px; + border-style: solid none; + border-width: 1px 0 0; + border-top-color: #d0d0d0; + border-bottom-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:679 */ +.x-toolbar-footer-vertical .x-box-menu-after { + margin: 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:694 */ +.x-toolbar-text-footer { + padding: 0 4px; + color: #4b4c4c; + font: 300 13px/16px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:700 */ +.x-toolbar-spacer-footer { + width: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-toolbar-footer-scroller .x-box-scroller-body-horizontal { + margin-left: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-toolbar-footer-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-toolbar-footer { + cursor: pointer; + color: #919191; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-toolbar-footer.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-toolbar-footer.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-toolbar-footer.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:232 */ +.x-box-scroller-toolbar-footer.x-box-scroller-left, +.x-box-scroller-toolbar-footer.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:259 */ +.x-box-scroller-toolbar-footer.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-toolbar-footer.x-box-scroller-left:before { + content: "\f053"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:284 */ +.x-box-scroller-toolbar-footer.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-toolbar-footer.x-box-scroller-right:before { + content: "\f054"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:742 */ +.x-ie8 .x-box-scroller-toolbar-footer { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Toolbar.scss:748 */ +.x-toolbar-more-icon { + font: 16px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-toolbar-more-icon:before { + content: "\f0c9"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:1 */ +.x-dd-drag-proxy { + color: #404040; + font: 300 13px/17px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + border: 1px solid #d0d0d0; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:8 */ +.x-dd-drag-ghost, +.x-dd-drop-icon { + padding: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:19 */ +.x-dd-drag-ghost { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:30 */ +.x-dd-drop-ok .x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #a4cf6d; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-dd-drop-ok .x-dd-drop-icon:before { + content: "\f058"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:38 */ +.x-dd-drop-ok-add .x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #a4cf6d; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-dd-drop-ok-add .x-dd-drop-icon:before { + content: "\f058"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dd/StatusProxy.scss:47 */ +.x-dd-drop-nodrop div.x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #d9705d; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-dd-drop-nodrop div.x-dd-drop-icon:before { + content: "\f057"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/panel/Panel.scss:1 */ +.x-panel-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:799 */ +.x-panel-default { + border-color: #5fa2dd; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:802 */ +.x-panel-default.x-masked { + border-color: #afd1ee; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:810 */ +.x-panel-header-default { + font-size: 16px; + border: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:836 */ +.x-panel-header-default .x-tool-tool-el { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:842 */ +.x-panel-header-default-horizontal { + padding: 11px 15px 12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:846 */ +.x-panel-header-default-horizontal .x-panel-header-default-tab-bar { + margin-top: -11px; + margin-bottom: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:854 */ +.x-panel-header-default-horizontal.x-header-noborder { + padding: 12px 16px 12px 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:858 */ +.x-panel-header-default-horizontal.x-header-noborder .x-panel-header-default-tab-bar { + margin-top: -12px; + margin-bottom: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:866 */ +.x-panel-header-default-vertical { + padding: 15px 11px 15px 12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:870 */ +.x-panel-header-default-vertical .x-panel-header-default-tab-bar { + margin-right: -11px; + margin-left: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:878 */ +.x-panel-header-default-vertical.x-header-noborder { + padding: 16px 12px 16px 12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:882 */ +.x-panel-header-default-vertical.x-header-noborder .x-panel-header-default-tab-bar { + margin-right: -12px; + margin-left: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:916 */ +.x-panel-header-title-default { + color: #f0f0f0; + font-size: 16px; + font-weight: 400; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:929 */ +.x-keyboard-mode .x-panel-header-title-default.x-title-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:950 */ +.x-panel-header-title-default > .x-title-text-default { + text-transform: none; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:997 */ +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1002 */ +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1014 */ +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1019 */ +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1031 */ +.x-panel-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default { + width: 16px; + height: 16px; + font-size: 16px; + color: #f0f0f0; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1051 */ +.x-ie8 .x-panel-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1062 */ +.x-panel-body-default { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 13px; + font-weight: 300; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1226 */ +.x-panel-header-default { + background-image: none; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1230 */ +.x-panel-header-default-vertical { + background-image: none; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1288 */ +.x-panel .x-panel-header-default-collapsed-border-top { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1292 */ +.x-panel .x-panel-header-default-collapsed-border-right { + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1296 */ +.x-panel .x-panel-header-default-collapsed-border-bottom { + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1300 */ +.x-panel .x-panel-header-default-collapsed-border-left { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1336 */ +.x-panel-header-default-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1346 */ +.x-panel-header-default-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1358 */ +.x-panel-header-default-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1368 */ +.x-panel-header-default-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1381 */ +.x-keyboard-mode .x-panel-header-default .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1429 */ +.x-panel-default-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-panel-default-outer-border-l { + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-panel-default-outer-border-b { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-panel-default-outer-border-bl { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-panel-default-outer-border-r { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-panel-default-outer-border-rl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-panel-default-outer-border-rb { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-panel-default-outer-border-rbl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-panel-default-outer-border-t { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-panel-default-outer-border-tl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-panel-default-outer-border-tb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-panel-default-outer-border-tbl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-panel-default-outer-border-tr { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-panel-default-outer-border-trl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-panel-default-outer-border-trb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-panel-default-outer-border-trbl { + border-color: #5fa2dd !important; + border-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:799 */ +.x-panel-default-framed { + border-color: #5fa2dd; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:802 */ +.x-panel-default-framed.x-masked { + border-color: #afd1ee; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:810 */ +.x-panel-header-default-framed { + font-size: 16px; + border: 2px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:836 */ +.x-panel-header-default-framed .x-tool-tool-el { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:842 */ +.x-panel-header-default-framed-horizontal { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:846 */ +.x-panel-header-default-framed-horizontal .x-panel-header-default-framed-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:854 */ +.x-panel-header-default-framed-horizontal.x-header-noborder { + padding: 12px 16px 10px 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:858 */ +.x-panel-header-default-framed-horizontal.x-header-noborder .x-panel-header-default-framed-tab-bar { + margin-top: -12px; + margin-bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:866 */ +.x-panel-header-default-framed-vertical { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:870 */ +.x-panel-header-default-framed-vertical .x-panel-header-default-framed-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:878 */ +.x-panel-header-default-framed-vertical.x-header-noborder { + padding: 16px 12px 16px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:882 */ +.x-panel-header-default-framed-vertical.x-header-noborder .x-panel-header-default-framed-tab-bar { + margin-right: -12px; + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:916 */ +.x-panel-header-title-default-framed { + color: #f0f0f0; + font-size: 16px; + font-weight: 400; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:929 */ +.x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:950 */ +.x-panel-header-title-default-framed > .x-title-text-default-framed { + text-transform: none; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:997 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1002 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1014 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1019 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1031 */ +.x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed > .x-title-icon-default-framed { + width: 16px; + height: 16px; + font-size: 16px; + color: #f0f0f0; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1051 */ +.x-ie8 .x-panel-header-title-default-framed > .x-title-icon-wrap-default-framed > .x-title-icon-default-framed.x-title-glyph { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1062 */ +.x-panel-body-default-framed { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 13px; + font-weight: 300; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-default-framed { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 0 0 0 0; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-default-framed-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-default-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-default-framed-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-0px-0px-0px-0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-default-framed-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-default-framed-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-default-framed-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-default-framed-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-default-framed-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-default-framed-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-default-framed-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-default-framed-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-default-framed-tr, +.x-panel-default-framed-br, +.x-panel-default-framed-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-default-framed-tl, +.x-panel-default-framed-bl, +.x-panel-default-framed-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-default-framed-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-default-framed-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-default-framed-tl, +.x-panel-default-framed-bl, +.x-panel-default-framed-tr, +.x-panel-default-framed-br, +.x-panel-default-framed-tc, +.x-panel-default-framed-bc, +.x-panel-default-framed-ml, +.x-panel-default-framed-mr { + background-image: url(images/panel/panel-default-framed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-default-framed-ml, +.x-panel-default-framed-mr { + background-image: url(images/panel/panel-default-framed-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-default-framed-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 0 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-top-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-top-frameInfo { + font-family: dh-2-2-0-2-2-2-0-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-top-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-top-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-top-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-top-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-top-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-top-tr, +.x-panel-header-default-framed-top-br, +.x-panel-header-default-framed-top-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-top-tl, +.x-panel-header-default-framed-top-bl, +.x-panel-header-default-framed-top-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-top-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-top-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-top-tl, +.x-panel-header-default-framed-top-bl, +.x-panel-header-default-framed-top-tr, +.x-panel-header-default-framed-top-br, +.x-panel-header-default-framed-top-tc, +.x-panel-header-default-framed-top-bc, +.x-panel-header-default-framed-top-ml, +.x-panel-header-default-framed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-top-ml, +.x-panel-header-default-framed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-top-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 0; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-right-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-right-frameInfo { + font-family: dh-2-2-2-0-2-2-2-0-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-right-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-right-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-right-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-right-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-right-ml { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-right-mr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-right-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-right-tr, +.x-panel-header-default-framed-right-br, +.x-panel-header-default-framed-right-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-right-tl, +.x-panel-header-default-framed-right-bl, +.x-panel-header-default-framed-right-ml { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-right-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-right-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-right-tl, +.x-panel-header-default-framed-right-bl, +.x-panel-header-default-framed-right-tr, +.x-panel-header-default-framed-right-br, +.x-panel-header-default-framed-right-tc, +.x-panel-header-default-framed-right-bc, +.x-panel-header-default-framed-right-ml, +.x-panel-header-default-framed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-right-ml, +.x-panel-header-default-framed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-right-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 0 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-bottom-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-bottom-frameInfo { + font-family: dh-0-2-2-2-0-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-bottom-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-bottom-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-bottom-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-bottom-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-bottom-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-bottom-tr, +.x-panel-header-default-framed-bottom-br, +.x-panel-header-default-framed-bottom-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-bottom-tl, +.x-panel-header-default-framed-bottom-bl, +.x-panel-header-default-framed-bottom-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-bottom-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-bottom-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-bottom-tl, +.x-panel-header-default-framed-bottom-bl, +.x-panel-header-default-framed-bottom-tr, +.x-panel-header-default-framed-bottom-br, +.x-panel-header-default-framed-bottom-tc, +.x-panel-header-default-framed-bottom-bc, +.x-panel-header-default-framed-bottom-ml, +.x-panel-header-default-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-bottom-ml, +.x-panel-header-default-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-bottom-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 0 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-left-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-left-frameInfo { + font-family: dh-2-0-2-2-2-0-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-left-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-left-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-left-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-left-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-left-ml { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-left-mr { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-left-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-left-tr, +.x-panel-header-default-framed-left-br, +.x-panel-header-default-framed-left-mr { + padding-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-left-tl, +.x-panel-header-default-framed-left-bl, +.x-panel-header-default-framed-left-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-left-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-left-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-left-tl, +.x-panel-header-default-framed-left-bl, +.x-panel-header-default-framed-left-tr, +.x-panel-header-default-framed-left-br, +.x-panel-header-default-framed-left-tc, +.x-panel-header-default-framed-left-bc, +.x-panel-header-default-framed-left-ml, +.x-panel-header-default-framed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-left-ml, +.x-panel-header-default-framed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-left-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-collapsed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-collapsed-top-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-collapsed-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-collapsed-top-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-collapsed-top-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-collapsed-top-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-collapsed-top-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-collapsed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-collapsed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-collapsed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-collapsed-top-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-collapsed-top-tr, +.x-panel-header-default-framed-collapsed-top-br, +.x-panel-header-default-framed-collapsed-top-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-collapsed-top-tl, +.x-panel-header-default-framed-collapsed-top-bl, +.x-panel-header-default-framed-collapsed-top-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-collapsed-top-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-collapsed-top-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-collapsed-top-tl, +.x-panel-header-default-framed-collapsed-top-bl, +.x-panel-header-default-framed-collapsed-top-tr, +.x-panel-header-default-framed-collapsed-top-br, +.x-panel-header-default-framed-collapsed-top-tc, +.x-panel-header-default-framed-collapsed-top-bc, +.x-panel-header-default-framed-collapsed-top-ml, +.x-panel-header-default-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-collapsed-top-ml, +.x-panel-header-default-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-collapsed-top-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-collapsed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-collapsed-right-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-collapsed-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-collapsed-right-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-collapsed-right-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-collapsed-right-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-collapsed-right-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-collapsed-right-ml { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-collapsed-right-mr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-collapsed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-collapsed-right-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-collapsed-right-tr, +.x-panel-header-default-framed-collapsed-right-br, +.x-panel-header-default-framed-collapsed-right-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-collapsed-right-tl, +.x-panel-header-default-framed-collapsed-right-bl, +.x-panel-header-default-framed-collapsed-right-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-collapsed-right-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-collapsed-right-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-collapsed-right-tl, +.x-panel-header-default-framed-collapsed-right-bl, +.x-panel-header-default-framed-collapsed-right-tr, +.x-panel-header-default-framed-collapsed-right-br, +.x-panel-header-default-framed-collapsed-right-tc, +.x-panel-header-default-framed-collapsed-right-bc, +.x-panel-header-default-framed-collapsed-right-ml, +.x-panel-header-default-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-collapsed-right-ml, +.x-panel-header-default-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-collapsed-right-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-collapsed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-collapsed-bottom-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-collapsed-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-collapsed-bottom-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-collapsed-bottom-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-collapsed-bottom-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-collapsed-bottom-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-collapsed-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-collapsed-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-collapsed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-collapsed-bottom-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-collapsed-bottom-tr, +.x-panel-header-default-framed-collapsed-bottom-br, +.x-panel-header-default-framed-collapsed-bottom-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-collapsed-bottom-tl, +.x-panel-header-default-framed-collapsed-bottom-bl, +.x-panel-header-default-framed-collapsed-bottom-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-collapsed-bottom-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-collapsed-bottom-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-collapsed-bottom-tl, +.x-panel-header-default-framed-collapsed-bottom-bl, +.x-panel-header-default-framed-collapsed-bottom-tr, +.x-panel-header-default-framed-collapsed-bottom-br, +.x-panel-header-default-framed-collapsed-bottom-tc, +.x-panel-header-default-framed-collapsed-bottom-bc, +.x-panel-header-default-framed-collapsed-bottom-ml, +.x-panel-header-default-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-collapsed-bottom-ml, +.x-panel-header-default-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-collapsed-bottom-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-default-framed-collapsed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-default-framed-collapsed-left-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-default-framed-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-default-framed-collapsed-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-default-framed-collapsed-left-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-default-framed-collapsed-left-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-default-framed-collapsed-left-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-default-framed-collapsed-left-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-default-framed-collapsed-left-ml { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-default-framed-collapsed-left-mr { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-default-framed-collapsed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-default-framed-collapsed-left-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-default-framed-collapsed-left-tr, +.x-panel-header-default-framed-collapsed-left-br, +.x-panel-header-default-framed-collapsed-left-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-default-framed-collapsed-left-tl, +.x-panel-header-default-framed-collapsed-left-bl, +.x-panel-header-default-framed-collapsed-left-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-default-framed-collapsed-left-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-default-framed-collapsed-left-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-default-framed-collapsed-left-tl, +.x-panel-header-default-framed-collapsed-left-bl, +.x-panel-header-default-framed-collapsed-left-tr, +.x-panel-header-default-framed-collapsed-left-br, +.x-panel-header-default-framed-collapsed-left-tc, +.x-panel-header-default-framed-collapsed-left-bc, +.x-panel-header-default-framed-collapsed-left-ml, +.x-panel-header-default-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-default-framed-collapsed-left-ml, +.x-panel-header-default-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-default-framed-collapsed-left-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1188 */ +.x-panel .x-panel-header-default-framed-top { + border-bottom-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1192 */ +.x-panel .x-panel-header-default-framed-right { + border-left-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1196 */ +.x-panel .x-panel-header-default-framed-bottom { + border-top-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1200 */ +.x-panel .x-panel-header-default-framed-left { + border-right-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1206 */ +.x-nbr .x-panel-header-default-framed-collapsed-top { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1210 */ +.x-nbr .x-panel-header-default-framed-collapsed-right { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1214 */ +.x-nbr .x-panel-header-default-framed-collapsed-bottom { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1218 */ +.x-nbr .x-panel-header-default-framed-collapsed-left { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1336 */ +.x-panel-header-default-framed-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1346 */ +.x-panel-header-default-framed-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1358 */ +.x-panel-header-default-framed-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1368 */ +.x-panel-header-default-framed-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1381 */ +.x-keyboard-mode .x-panel-header-default-framed .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1429 */ +.x-panel-default-framed-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-panel-default-framed-outer-border-l { + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-panel-default-framed-outer-border-b { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-panel-default-framed-outer-border-bl { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-panel-default-framed-outer-border-r { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-panel-default-framed-outer-border-rl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-panel-default-framed-outer-border-rb { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-panel-default-framed-outer-border-rbl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-panel-default-framed-outer-border-t { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-panel-default-framed-outer-border-tl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-panel-default-framed-outer-border-tb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-panel-default-framed-outer-border-tbl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-panel-default-framed-outer-border-tr { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-panel-default-framed-outer-border-trl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-panel-default-framed-outer-border-trb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-panel-default-framed-outer-border-trbl { + border-color: #5fa2dd !important; + border-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:243 */ +.x-btn-group-default { + border-color: #d0d0d0; + -webkit-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + -moz-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:252 */ +.x-btn-group-header-default { + padding: 8px 8px 7px; + line-height: 16px; + background: #fff; + -moz-border-radius-topleft: 0px; + -webkit-border-top-left-radius: 0px; + border-top-left-radius: 0px; + -moz-border-radius-topright: 0px; + -webkit-border-top-right-radius: 0px; + border-top-right-radius: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:263 */ +.x-btn-group-header-default .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:274 */ +.x-btn-group-header-title-default { + font: 300 14px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 16px; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:280 */ +.x-btn-group-body-default { + padding: 0 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:282 */ +.x-btn-group-body-default .x-table-layout { + border-spacing: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-group-default-framed { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-group-default-framed-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-group-default-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-group-default-framed-frameInfo { + font-family: dh-2-2-2-2-1-1-1-1-1-1-1-1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-group-default-framed-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-group-default-framed-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-group-default-framed-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-group-default-framed-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-group-default-framed-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-group-default-framed-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-group-default-framed-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-group-default-framed-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-group-default-framed-tr, +.x-btn-group-default-framed-br, +.x-btn-group-default-framed-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-group-default-framed-tl, +.x-btn-group-default-framed-bl, +.x-btn-group-default-framed-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-group-default-framed-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-group-default-framed-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-group-default-framed-tl, +.x-btn-group-default-framed-bl, +.x-btn-group-default-framed-tr, +.x-btn-group-default-framed-br, +.x-btn-group-default-framed-tc, +.x-btn-group-default-framed-bc, +.x-btn-group-default-framed-ml, +.x-btn-group-default-framed-mr { + background-image: url(images/btn-group/btn-group-default-framed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-group-default-framed-ml, +.x-btn-group-default-framed-mr { + background-image: url(images/btn-group/btn-group-default-framed-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-group-default-framed-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-group-default-framed-notitle { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-group-default-framed-notitle-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-group-default-framed-notitle { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-group-default-framed-notitle-frameInfo { + font-family: dh-2-2-2-2-1-1-1-1-1-1-1-1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-group-default-framed-notitle-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-group-default-framed-notitle-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-group-default-framed-notitle-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-group-default-framed-notitle-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-group-default-framed-notitle-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-group-default-framed-notitle-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-group-default-framed-notitle-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-group-default-framed-notitle-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-group-default-framed-notitle-tr, +.x-btn-group-default-framed-notitle-br, +.x-btn-group-default-framed-notitle-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-group-default-framed-notitle-tl, +.x-btn-group-default-framed-notitle-bl, +.x-btn-group-default-framed-notitle-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-group-default-framed-notitle-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-group-default-framed-notitle-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-group-default-framed-notitle-tl, +.x-btn-group-default-framed-notitle-bl, +.x-btn-group-default-framed-notitle-tr, +.x-btn-group-default-framed-notitle-br, +.x-btn-group-default-framed-notitle-tc, +.x-btn-group-default-framed-notitle-bc, +.x-btn-group-default-framed-notitle-ml, +.x-btn-group-default-framed-notitle-mr { + background-image: url(images/btn-group/btn-group-default-framed-notitle-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-group-default-framed-notitle-ml, +.x-btn-group-default-framed-notitle-mr { + background-image: url(images/btn-group/btn-group-default-framed-notitle-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-group-default-framed-notitle-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:243 */ +.x-btn-group-default-framed { + border-color: #d0d0d0; + -webkit-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + -moz-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:252 */ +.x-btn-group-header-default-framed { + padding: 8px 8px 7px; + line-height: 16px; + background: #fff; + -moz-border-radius-topleft: 2px; + -webkit-border-top-left-radius: 2px; + border-top-left-radius: 2px; + -moz-border-radius-topright: 2px; + -webkit-border-top-right-radius: 2px; + border-top-right-radius: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:263 */ +.x-btn-group-header-default-framed .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:274 */ +.x-btn-group-header-title-default-framed { + font: 300 14px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 16px; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:280 */ +.x-btn-group-body-default-framed { + padding: 0 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/container/ButtonGroup.scss:282 */ +.x-btn-group-body-default-framed .x-table-layout { + border-spacing: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:1 */ +.x-dashboard-column { + padding: 0 0 7px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:5 */ +.x-dashboard-panel { + margin-top: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:9 */ +.x-dashboard-column-first { + padding-left: 7px; + clear: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:14 */ +.x-dashboard-column-last { + padding-right: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:18 */ +.x-dashboard .x-panel-dd-spacer { + border: 2px dashed #99bbe8; + background: #f6f6f6; + border-radius: 4px; + -moz-border-radius: 4px; + margin-top: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/dashboard/Dashboard.scss:28 */ +.x-dashboard-dd-over { + overflow: hidden !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Window.scss:1 */ +.x-window-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:545 */ +.x-window-default { + border-color: #5fa2dd; + -webkit-border-radius: 0 0 0 0; + -moz-border-radius: 0 0 0 0; + -ms-border-radius: 0 0 0 0; + -o-border-radius: 0 0 0 0; + border-radius: 0 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-default { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 0 0 0 0; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-default-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-default { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-default-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-0px-0px-0px-0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-default-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-default-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-default-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-default-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-default-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-default-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-default-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-default-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-default-tr, +.x-window-default-br, +.x-window-default-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-default-tl, +.x-window-default-bl, +.x-window-default-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-default-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-default-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-default-tl, +.x-window-default-bl, +.x-window-default-tr, +.x-window-default-br, +.x-window-default-tc, +.x-window-default-bc, +.x-window-default-ml, +.x-window-default-mr { + background-image: url(images/window/window-default-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-default-ml, +.x-window-default-mr { + background-image: url(images/window/window-default-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-default-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:567 */ +.x-window-body-default { + border-color: #5fa2dd; + border-width: 1px; + border-style: solid; + background: #fff; + color: #000; + font-size: 13px; + font-weight: 300; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:581 */ +.x-window-header-default { + font-size: 16px; + border-color: #5fa2dd; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:586 */ +.x-window-header-default .x-tool-img { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:599 */ +.x-window-header-default-horizontal .x-window-header-default-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:606 */ +.x-window-header-default-vertical .x-window-header-default-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:622 */ +.x-window-header-title-default { + color: #f0f0f0; + font-size: 16px; + font-weight: 400; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:631 */ +.x-window-header-title-default > .x-title-text-default { + padding: 0; + text-transform: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:678 */ +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:683 */ +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:695 */ +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:700 */ +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:712 */ +.x-window-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default { + width: 16px; + height: 16px; + font-size: 16px; + color: #f0f0f0; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:732 */ +.x-ie8 .x-window-header-title-default > .x-title-icon-wrap-default > .x-title-icon-default.x-title-glyph { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-top-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-top-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-top-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-top-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-top-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-top-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-top-tr, +.x-window-header-default-top-br, +.x-window-header-default-top-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-top-tl, +.x-window-header-default-top-bl, +.x-window-header-default-top-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-top-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-top-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-top-tl, +.x-window-header-default-top-bl, +.x-window-header-default-top-tr, +.x-window-header-default-top-br, +.x-window-header-default-top-tc, +.x-window-header-default-top-bc, +.x-window-header-default-top-ml, +.x-window-header-default-top-mr { + background-image: url(images/window-header/window-header-default-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-top-ml, +.x-window-header-default-top-mr { + background-image: url(images/window-header/window-header-default-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-top-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-right-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-right-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-right-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-right-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-right-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-right-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-right-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-right-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-right-tr, +.x-window-header-default-right-br, +.x-window-header-default-right-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-right-tl, +.x-window-header-default-right-bl, +.x-window-header-default-right-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-right-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-right-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-right-tl, +.x-window-header-default-right-bl, +.x-window-header-default-right-tr, +.x-window-header-default-right-br, +.x-window-header-default-right-tc, +.x-window-header-default-right-bc, +.x-window-header-default-right-ml, +.x-window-header-default-right-mr { + background-image: url(images/window-header/window-header-default-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-right-ml, +.x-window-header-default-right-mr { + background-image: url(images/window-header/window-header-default-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-right-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-bottom-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-bottom-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-bottom-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-bottom-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-bottom-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-bottom-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-bottom-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-bottom-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-bottom-tr, +.x-window-header-default-bottom-br, +.x-window-header-default-bottom-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-bottom-tl, +.x-window-header-default-bottom-bl, +.x-window-header-default-bottom-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-bottom-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-bottom-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-bottom-tl, +.x-window-header-default-bottom-bl, +.x-window-header-default-bottom-tr, +.x-window-header-default-bottom-br, +.x-window-header-default-bottom-tc, +.x-window-header-default-bottom-bc, +.x-window-header-default-bottom-ml, +.x-window-header-default-bottom-mr { + background-image: url(images/window-header/window-header-default-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-bottom-ml, +.x-window-header-default-bottom-mr { + background-image: url(images/window-header/window-header-default-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-bottom-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-left-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-left-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-left-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-left-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-left-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-left-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-left-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-left-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-left-tr, +.x-window-header-default-left-br, +.x-window-header-default-left-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-left-tl, +.x-window-header-default-left-bl, +.x-window-header-default-left-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-left-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-left-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-left-tl, +.x-window-header-default-left-bl, +.x-window-header-default-left-tr, +.x-window-header-default-left-br, +.x-window-header-default-left-tc, +.x-window-header-default-left-bc, +.x-window-header-default-left-ml, +.x-window-header-default-left-mr { + background-image: url(images/window-header/window-header-default-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-left-ml, +.x-window-header-default-left-mr { + background-image: url(images/window-header/window-header-default-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-left-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-collapsed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-collapsed-top-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-collapsed-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-collapsed-top-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-collapsed-top-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-collapsed-top-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-collapsed-top-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-collapsed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-collapsed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-collapsed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-collapsed-top-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-collapsed-top-tr, +.x-window-header-default-collapsed-top-br, +.x-window-header-default-collapsed-top-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-collapsed-top-tl, +.x-window-header-default-collapsed-top-bl, +.x-window-header-default-collapsed-top-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-collapsed-top-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-collapsed-top-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-collapsed-top-tl, +.x-window-header-default-collapsed-top-bl, +.x-window-header-default-collapsed-top-tr, +.x-window-header-default-collapsed-top-br, +.x-window-header-default-collapsed-top-tc, +.x-window-header-default-collapsed-top-bc, +.x-window-header-default-collapsed-top-ml, +.x-window-header-default-collapsed-top-mr { + background-image: url(images/window-header/window-header-default-collapsed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-collapsed-top-ml, +.x-window-header-default-collapsed-top-mr { + background-image: url(images/window-header/window-header-default-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-collapsed-top-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-collapsed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-collapsed-right-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-collapsed-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-collapsed-right-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-collapsed-right-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-collapsed-right-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-collapsed-right-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-collapsed-right-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-collapsed-right-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-collapsed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-collapsed-right-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-collapsed-right-tr, +.x-window-header-default-collapsed-right-br, +.x-window-header-default-collapsed-right-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-collapsed-right-tl, +.x-window-header-default-collapsed-right-bl, +.x-window-header-default-collapsed-right-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-collapsed-right-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-collapsed-right-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-collapsed-right-tl, +.x-window-header-default-collapsed-right-bl, +.x-window-header-default-collapsed-right-tr, +.x-window-header-default-collapsed-right-br, +.x-window-header-default-collapsed-right-tc, +.x-window-header-default-collapsed-right-bc, +.x-window-header-default-collapsed-right-ml, +.x-window-header-default-collapsed-right-mr { + background-image: url(images/window-header/window-header-default-collapsed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-collapsed-right-ml, +.x-window-header-default-collapsed-right-mr { + background-image: url(images/window-header/window-header-default-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-collapsed-right-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-collapsed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-collapsed-bottom-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-collapsed-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-collapsed-bottom-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-collapsed-bottom-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-collapsed-bottom-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-collapsed-bottom-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-collapsed-bottom-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-collapsed-bottom-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-collapsed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-collapsed-bottom-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-collapsed-bottom-tr, +.x-window-header-default-collapsed-bottom-br, +.x-window-header-default-collapsed-bottom-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-collapsed-bottom-tl, +.x-window-header-default-collapsed-bottom-bl, +.x-window-header-default-collapsed-bottom-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-collapsed-bottom-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-collapsed-bottom-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-collapsed-bottom-tl, +.x-window-header-default-collapsed-bottom-bl, +.x-window-header-default-collapsed-bottom-tr, +.x-window-header-default-collapsed-bottom-br, +.x-window-header-default-collapsed-bottom-tc, +.x-window-header-default-collapsed-bottom-bc, +.x-window-header-default-collapsed-bottom-ml, +.x-window-header-default-collapsed-bottom-mr { + background-image: url(images/window-header/window-header-default-collapsed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-collapsed-bottom-ml, +.x-window-header-default-collapsed-bottom-mr { + background-image: url(images/window-header/window-header-default-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-collapsed-bottom-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-window-header-default-collapsed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-window-header-default-collapsed-left-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-window-header-default-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-window-header-default-collapsed-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-window-header-default-collapsed-left-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-window-header-default-collapsed-left-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-window-header-default-collapsed-left-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-window-header-default-collapsed-left-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-window-header-default-collapsed-left-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-window-header-default-collapsed-left-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-window-header-default-collapsed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-window-header-default-collapsed-left-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-window-header-default-collapsed-left-tr, +.x-window-header-default-collapsed-left-br, +.x-window-header-default-collapsed-left-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-window-header-default-collapsed-left-tl, +.x-window-header-default-collapsed-left-bl, +.x-window-header-default-collapsed-left-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-window-header-default-collapsed-left-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-window-header-default-collapsed-left-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-window-header-default-collapsed-left-tl, +.x-window-header-default-collapsed-left-bl, +.x-window-header-default-collapsed-left-tr, +.x-window-header-default-collapsed-left-br, +.x-window-header-default-collapsed-left-tc, +.x-window-header-default-collapsed-left-bc, +.x-window-header-default-collapsed-left-ml, +.x-window-header-default-collapsed-left-mr { + background-image: url(images/window-header/window-header-default-collapsed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-window-header-default-collapsed-left-ml, +.x-window-header-default-collapsed-left-mr { + background-image: url(images/window-header/window-header-default-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-window-header-default-collapsed-left-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:857 */ +.x-window-header-default .x-window-header-icon { + width: 16px; + height: 16px; + color: #f0f0f0; + font-size: 16px; + line-height: 16px; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:866 */ +.x-window-header-default .x-window-header-glyph { + color: #f0f0f0; + font-size: 16px; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:883 */ +.x-ie8 .x-window-header-default .x-window-header-glyph { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:892 */ +.x-window-header-default-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:902 */ +.x-window-header-default-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:914 */ +.x-window-header-default-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:924 */ +.x-window-header-default-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:937 */ +.x-keyboard-mode .x-window-header-default .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus, +.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:951 */ +.x-window-header-default { + border-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/window/Window.scss:961 */ +.x-nbr .x-window-default-collapsed .x-window-header { + border-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-window-default-outer-border-l { + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-window-default-outer-border-b { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-window-default-outer-border-bl { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-window-default-outer-border-r { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-window-default-outer-border-rl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-window-default-outer-border-rb { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-window-default-outer-border-rbl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-window-default-outer-border-t { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-window-default-outer-border-tl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-window-default-outer-border-tb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-window-default-outer-border-tbl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-window-default-outer-border-tr { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-window-default-outer-border-trl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-window-default-outer-border-trb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-window-default-outer-border-trbl { + border-color: #5fa2dd !important; + border-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Window.scss:11 */ +.x-window-body-plain { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:97 */ +.x-form-item-label-default { + color: #404040; + font: 300 13px/17px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + min-height: 32px; + padding-top: 8px; + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:113 */ +.x-ie8 .x-form-item-label-default { + min-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:119 */ +.x-form-item-label-default.x-form-item-label-top { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:121 */ +.x-form-item-label-default.x-form-item-label-top > .x-form-item-label-inner { + padding-top: 8px; + padding-bottom: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:127 */ +.x-form-item-label-default.x-form-item-label-top-side-error:after { + width: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:132 */ +.x-form-item-body-default { + min-height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:136 */ +.x-form-invalid-icon-default { + width: 16px; + height: 16px; + margin: 0 5px; + background: url(images/form/exclamation.png) no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:143 */ +.x-form-invalid-under-default { + padding: 2px 2px 2px 20px; + color: #cf4c35; + font: 300 13px/16px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + background: no-repeat 0 2px; + background-image: url(images/form/exclamation.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:151 */ +.x-form-error-wrap-default.x-form-error-wrap-side { + width: 26px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/Labelable.scss:156 */ +.x-form-item-default.x-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/Labelable.scss:33 */ +.x-autocontainer-form-item, +.x-anchor-form-item, +.x-vbox-form-item, +.x-table-form-item { + margin-bottom: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:201 */ +.x-form-text-field-body-default { + min-width: 170px; + max-width: 170px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:221 */ +.x-form-trigger-wrap-default { + border-width: 1px; + border-style: solid; + border-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:229 */ +.x-form-trigger-wrap-default.x-form-trigger-wrap-focus { + border-color: #77b0e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:233 */ +.x-form-trigger-wrap-default.x-form-trigger-wrap-invalid { + border-color: #cf4c35; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:258 */ +.x-form-text-default { + color: #404040; + padding: 5px 10px 4px; + background-color: #fff; + font: 300 13px/21px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + min-height: 30px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:272 */ +.x-ie8 .x-form-text-default { + min-height: 21px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:278 */ +.x-form-text-default.x-form-textarea { + line-height: 20px; + min-height: 80px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:283 */ +.x-ie8 .x-form-text-default.x-form-textarea { + min-height: 71px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:290 */ +.x-form-text-default.x-form-text-file { + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:294 */ +.x-form-text-default.x-webkit-border-box-bug { + height: calc(100% + 9px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:300 */ +.x-placeholder-label-default { + padding: 5px 10px 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:304 */ +.x-form-empty-field-default + .x-placeholder-label-default { + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:309 */ +.x-form-text-default:-ms-input-placeholder { + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:313 */ +.x-form-invalid-field-default { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:324 */ +.x-form-trigger-default { + width: 32px; + font: 16px/30px FontAwesome; + background: #fff; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-trigger-default:before { + content: "\f0d7"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:347 */ +.x-form-trigger-default.x-form-trigger-over { + background-position: -32px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:353 */ +.x-form-trigger-default.x-form-trigger-over.x-form-trigger-focus { + background-position: -128px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:358 */ +.x-form-trigger-default.x-form-trigger-focus { + background-position: -96px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:367 */ +.x-form-trigger.x-form-trigger-default.x-form-trigger-click { + background-position: -64px center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Text.scss:376 */ +.x-textfield-default-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/Text.scss:54 */ +.x-form-clear-trigger { + font-size: 16px; + font-family: FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-clear-trigger:before { + content: "\f00d"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/Text.scss:67 */ +.x-form-search-trigger { + font-size: 16px; + font-family: FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-search-trigger:before { + content: "\f002"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:1 */ +.x-message-box .x-window-body { + background-color: #fff; + border-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:10 */ +.x-message-box-info, +.x-message-box-warning, +.x-message-box-question, +.x-message-box-error { + background-position: left top; + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:29 */ +.x-message-box-icon { + height: 44px; + width: 44px; + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:35 */ +.x-message-box-info { + font: 44px/1 FontAwesome; + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-message-box-info:before { + content: "\f05a"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:44 */ +.x-message-box-warning { + font: 44px/1 FontAwesome; + color: #f8d400; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-message-box-warning:before { + content: "\f071"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:53 */ +.x-message-box-question { + font: 44px/1 FontAwesome; + color: grey; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-message-box-question:before { + content: "\f059"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/MessageBox.scss:62 */ +.x-message-box-error { + font: 44px/1 FontAwesome; + color: #ee611f; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-message-box-error:before { + content: "\f057"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:89 */ +.x-form-cb-wrap-default { + height: 32px; + min-width: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:98 */ +.x-form-cb-default { + margin-top: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:103 */ +.x-form-checkbox-default, +.x-form-radio-default { + width: 18px; + height: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:109 */ +.x-form-radio-default { + font: 18px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-radio-default:before { + content: "\f10c"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:114 */ +.x-form-cb-checked .x-form-radio-default { + font: 18px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-cb-checked .x-form-radio-default:before { + content: "\f192"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:126 */ +.x-form-checkbox-default { + font: 18px/1 ExtJS; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-checkbox-default:before { + content: "\e614"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:131 */ +.x-form-cb-checked .x-form-checkbox-default { + font: 18px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-cb-checked .x-form-checkbox-default:before { + content: "\e613"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:145 */ +.x-keyboard-mode .x-form-checkbox-focus.x-form-radio-default { + color: #77b0e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:154 */ +.x-keyboard-mode .x-form-checkbox-focus.x-form-checkbox-default { + color: #77b0e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:165 */ +.x-keyboard-mode .x-form-cb-checked .x-form-checkbox-focus.x-form-radio-default { + color: #77b0e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:174 */ +.x-keyboard-mode .x-form-cb-checked .x-form-checkbox-focus.x-form-checkbox-default { + color: #77b0e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:185 */ +.x-form-cb-label-default { + margin-top: 8px; + font: 300 13px/17px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:190 */ +.x-form-cb-label-default.x-form-cb-label-before { + padding-right: 22px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:201 */ +.x-form-cb-label-default.x-form-cb-label-after { + padding-left: 22px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Checkbox.scss:215 */ +.x-checkbox-default-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/CheckboxGroup.scss:96 */ +.x-form-item-body-default.x-form-checkboxgroup-body { + padding: 0 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/CheckboxGroup.scss:99 */ +.x-form-invalid .x-form-item-body-default.x-form-checkboxgroup-body { + border-width: 1px; + border-style: solid; + border-color: #cf4c35; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:282 */ +.x-fieldset-default { + border: 1px solid #d0d0d0; + padding: 5px 15px 10px 15px; + margin: 0 0 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:295 */ +.x-ie8 .x-fieldset-default { + padding-top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:298 */ +.x-ie8 .x-fieldset-body-default { + padding-top: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:304 */ +.x-fieldset-header-default { + padding: 10px 5px; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:308 */ +.x-fieldset-header-default > .x-fieldset-header-text { + font: 400 16px/20px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #919191; + padding: 1px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:315 */ +.x-fieldset-header-checkbox-default { + margin: 2px 4px 0 0; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:325 */ +.x-fieldset-header-tool-default { + margin: 2px 4px 0 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:334 */ +.x-fieldset-header-tool-default > .x-tool-img { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; + height: 15px; + width: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:341 */ +.x-fieldset-header-tool-default.x-tool-over > .x-tool-img { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=90)"; + opacity: 0.9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:347 */ +.x-fieldset-header-tool-default.x-tool-pressed > .x-tool-img { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:353 */ +.x-fieldset-header-tool-default > .x-tool-toggle { + font: 14px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-fieldset-header-tool-default > .x-tool-toggle:before { + content: "\f146"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:373 */ +.x-keyboard-mode .x-fieldset-header-tool-default.x-focus { + outline: 1px solid #77b0e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:380 */ +.x-fieldset-default.x-fieldset-collapsed { + border-width: 1px 1px 0 1px; + border-left-color: transparent; + border-right-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/FieldSet.scss:389 */ +.x-fieldset-default.x-fieldset-collapsed .x-tool-toggle { + font: 14px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-fieldset-default.x-fieldset-collapsed .x-tool-toggle:before { + content: "\f0fe"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:71 */ +.x-form-trigger-spinner-default { + width: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:79 */ +.x-form-trigger-spinner-default:before { + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:85 */ +.x-form-spinner-default { + background-color: #fff; + width: 32px; + height: 15px; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:131 */ +.x-form-spinner-up-default { + font: 16px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-spinner-up-default:before { + content: "\e61c"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:137 */ +.x-form-spinner-down-default { + font: 16px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-spinner-down-default:before { + content: "\e61b"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:143 */ +.x-form-spinner-up-default { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:146 */ +.x-form-spinner-up-default.x-form-spinner-over { + background-position: -32px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:148 */ +.x-form-spinner-up-default.x-form-spinner-over.x-form-spinner-focus { + background-position: -128px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:153 */ +.x-form-spinner-up-default.x-form-spinner-focus { + background-position: -96px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:158 */ +.x-form-spinner-up-default.x-form-spinner.x-form-spinner-click { + background-position: -64px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:163 */ +.x-form-spinner-down-default { + background-position: 0 -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:166 */ +.x-form-spinner-down-default.x-form-spinner-over { + background-position: -32px -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:168 */ +.x-form-spinner-down-default.x-form-spinner-over.x-form-spinner-focus { + background-position: -128px -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:173 */ +.x-form-spinner-down-default.x-form-spinner-focus { + background-position: -96px -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/trigger/Spinner.scss:178 */ +.x-form-spinner-down-default.x-form-spinner.x-form-spinner-click { + background-position: -64px -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:1 */ +.x-tbar-page-number { + width: 30px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:10 */ +.x-btn-icon-el.x-tbar-page-first { + font: 16px/16px ExtJS; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-btn-icon-el.x-tbar-page-first:before { + content: "\e617"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:19 */ +.x-btn-icon-el.x-tbar-page-prev { + font: 16px/16px ExtJS; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-btn-icon-el.x-tbar-page-prev:before { + content: "\e615"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:28 */ +.x-btn-icon-el.x-tbar-page-next { + font: 16px/16px ExtJS; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-btn-icon-el.x-tbar-page-next:before { + content: "\e616"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:37 */ +.x-btn-icon-el.x-tbar-page-last { + font: 16px/16px ExtJS; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-btn-icon-el.x-tbar-page-last:before { + content: "\e618"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/toolbar/Paging.scss:46 */ +.x-btn-icon-el.x-tbar-loading { + font: 16px/16px FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-btn-icon-el.x-tbar-loading:before { + content: "\f021"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:1 */ +.x-boundlist { + border-width: 1px; + border-style: solid; + border-color: #d0d0d0; + background: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:8 */ +.x-boundlist-item { + padding: 0 10px; + font: normal 13px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 30px; + cursor: pointer; + cursor: hand; + position: relative; + /*allow hover in IE on empty items*/ + border-width: 1px; + border-style: dotted; + border-color: #fff; + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:25 */ +.x-boundlist-selected { + color: #fff; + background: #5fa2dd; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:33 */ +.x-boundlist-item-over { + color: #fff; + background: #7fb5e4; + border-color: #7fb5e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:42 */ +.x-boundlist-floating { + border-top-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/BoundList.scss:46 */ +.x-boundlist-above { + border-top-width: 1px; + border-bottom-width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:9 */ +.x-datepicker { + border-width: 1px; + border-style: solid; + border-color: #d0d0d0; + background-color: #fff; + width: 310px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:19 */ +.x-datepicker-header { + padding: 0; + text-align: center; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:29 */ +.x-datepicker-arrow { + width: 32px; + height: 44px; + top: 0px; + cursor: pointer; + -webkit-touch-callout: none; + color: #919191; + background-color: #ececec; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:51 */ +div.x-datepicker-arrow:hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:56 */ +.x-datepicker-next { + right: 0; + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-datepicker-next:before { + content: "\f101"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:65 */ +.x-datepicker-prev { + left: 0; + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-datepicker-prev:before { + content: "\f100"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:74 */ +.x-datepicker-month { + background: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:77 */ +.x-datepicker-month .x-btn, +.x-datepicker-month .x-btn .x-btn-tc, +.x-datepicker-month .x-btn .x-btn-tl, +.x-datepicker-month .x-btn .x-btn-tr, +.x-datepicker-month .x-btn .x-btn-mc, +.x-datepicker-month .x-btn .x-btn-ml, +.x-datepicker-month .x-btn .x-btn-mr, +.x-datepicker-month .x-btn .x-btn-bc, +.x-datepicker-month .x-btn .x-btn-bl, +.x-datepicker-month .x-btn .x-btn-br { + background: transparent; + border-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:93 */ +.x-datepicker-month .x-btn-inner { + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:98 */ +.x-datepicker-month .x-btn-split-right:after, +.x-datepicker-month .x-btn-over .x-btn-split-right:after { + content: "\f107"; + font: 16px/1 FontAwesome; + color: #606060; + background: none; + padding: 0; + text-align: right; + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:111 */ +.x-datepicker-month .x-btn { + padding: 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:115 */ +.x-datepicker-month .x-btn-over { + border-color: transparent; + background: #dfdfdf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:120 */ +.x-datepicker-month .x-btn.x-btn-pressed { + border-color: transparent; + background: #d3d3d3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:125 */ +.x-datepicker-month .x-btn-inner { + font-size: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:130 */ +.x-datepicker-column-header { + width: 44px; + color: #404040; + font: 400 13px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + text-align: right; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:149 */ +.x-datepicker-column-header-inner { + line-height: 36px; + padding: 0 15px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:154 */ +.x-datepicker-cell { + text-align: right; + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:163 */ +.x-datepicker-date { + padding: 0 15px 0 0; + font: 300 13px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #404040; + cursor: pointer; + line-height: 36px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:173 */ +div.x-datepicker-date:hover { + color: #404040; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:178 */ +.x-datepicker-selected { + border-style: solid; + border-color: #7fb5e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:181 */ +.x-datepicker-selected div.x-datepicker-date { + background-color: #5fa2dd; + color: #fff; + font-weight: 300; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:188 */ +.x-datepicker-today { + border-color: darkred; + border-style: solid; + background-color: #bfdaf1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:199 */ +.x-datepicker-prevday .x-datepicker-date, +.x-datepicker-nextday .x-datepicker-date { + color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:206 */ +.x-datepicker-disabled .x-datepicker-date { + background-color: #eee; + cursor: default; + color: silver; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:214 */ +.x-datepicker-disabled div.x-datepicker-date:hover { + background-color: #eee; + color: silver; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:219 */ +.x-datepicker-footer, +.x-monthpicker-buttons { + padding: 6px 0; + background-color: #fff; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:236 */ +.x-datepicker-footer .x-btn, +.x-monthpicker-buttons .x-btn { + margin: 0 3px 0 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:242 */ +.x-monthpicker { + width: 310px; + border-width: 1px; + border-style: solid; + border-color: #d0d0d0; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:252 */ +.x-monthpicker-months { + border-width: 0 1px 0 0; + border-color: #d0d0d0; + border-style: solid; + width: 154px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:261 */ +.x-monthpicker-months .x-monthpicker-item { + width: 76px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:266 */ +.x-monthpicker-years { + width: 154px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:269 */ +.x-monthpicker-years .x-monthpicker-item { + width: 77px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:274 */ +.x-monthpicker-item { + margin: 5px 0 5px; + font: 300 13px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:280 */ +.x-monthpicker-item-inner { + margin: 0 5px 0 5px; + color: #404040; + border: 0; + line-height: 37px; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:295 */ +a.x-monthpicker-item-inner:hover { + color: #404040; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:301 */ +.x-monthpicker-item a.x-monthpicker-selected { + background-color: #5fa2dd; + color: #fff; + border-style: solid; + border-color: #7fb5e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:308 */ +.x-monthpicker-yearnav { + height: 47px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:312 */ +.x-monthpicker-yearnav-button-ct { + width: 77px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:316 */ +.x-monthpicker-yearnav-button { + height: 16px; + width: 16px; + cursor: pointer; + margin-top: 15px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; + -webkit-touch-callout: none; + color: #919191; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:337 */ +a.x-monthpicker-yearnav-button:hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:342 */ +.x-monthpicker-yearnav-next { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-monthpicker-yearnav-next:before { + content: "\f101"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:356 */ +.x-monthpicker-yearnav-prev { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-monthpicker-yearnav-prev:before { + content: "\f100"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:371 */ +.x-monthpicker-small .x-monthpicker-item { + margin: 2px 0 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:375 */ +.x-monthpicker-small .x-monthpicker-item-inner { + margin: 0 5px 0 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:379 */ +.x-monthpicker-small .x-monthpicker-yearnav { + height: 41px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Date.scss:383 */ +.x-monthpicker-small .x-monthpicker-yearnav-button { + margin-top: 12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/Date.scss:2 */ +.x-form-field-date .x-form-date-trigger { + font-size: 16px; + font-family: FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-field-date .x-form-date-trigger:before { + content: "\f073"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Display.scss:52 */ +.x-form-display-field-default { + min-height: 32px; + font: 300 13px/17px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #404040; + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Display.scss:60 */ +.x-keyboard-mode .x-form-display-field-default.x-field-form-focus { + outline: 1px solid #77b0e2; + outline-offset: -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus, +.x-ie10p .x-keyboard-mode .x-form-display-field-default.x-field-form-focus, +.x-edge .x-keyboard-mode .x-form-display-field-default.x-field-form-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after, +.x-ie10p .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after, +.x-edge .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after { + position: absolute; + content: ' '; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + border: 1px solid #77b0e2; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Display.scss:71 */ +.x-ie8 .x-form-display-field-default.x-field-form-focus { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tip-default { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #747474; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tip-default-mc { + background-color: #747474; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tip-default { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tip-default-frameInfo { + font-family: th-2-2-2-2-1-1-1-1-1-1-1-1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tip-default-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tip-default-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tip-default-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tip-default-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tip-default-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tip-default-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tip-default-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tip-default-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tip-default-tr, +.x-tip-default-br, +.x-tip-default-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tip-default-tl, +.x-tip-default-bl, +.x-tip-default-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tip-default-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tip-default-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-tip-default-tl, +.x-tip-default-bl, +.x-tip-default-tr, +.x-tip-default-br, +.x-tip-default-tc, +.x-tip-default-bc, +.x-tip-default-ml, +.x-tip-default-mr { + background-image: url(images/tip/tip-default-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-tip-default-ml, +.x-tip-default-mr { + background-image: url(images/tip/tip-default-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tip-default-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:318 */ +.x-tip-default { + background-color: #747474; + border-color: #747474; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:328 */ +.x-tip-default .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #747474; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:343 */ +.x-tip-header-default .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:353 */ +.x-tip-header-default .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:364 */ +.x-tip-header-default { + padding: 3px 3px 0 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:368 */ +.x-tip-header-title-default { + color: #f0f0f0; + font-size: 13px; + font-weight: bold; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:374 */ +.x-tip-body-default { + padding: 6px 8px; + color: #f0f0f0; + font-size: 13px; + font-weight: 300; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:379 */ +.x-tip-body-default a { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:390 */ +.x-tip-default .x-tip-anchor { + border: 10px solid transparent; + _border-color: pink; + _filter: chroma(color=pink); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:467 */ +.x-tip-default .x-tip-anchor-top { + border-top-width: 0; + border-bottom: 10px solid #747474; + top: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:473 */ +.x-tip-default .x-tip-anchor-bottom { + border-bottom-width: 0; + border-top: 10px solid #747474; + bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:479 */ +.x-tip-default .x-tip-anchor-left { + border-left-width: 0; + border-right: 10px solid #747474; + left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:485 */ +.x-tip-default .x-tip-anchor-right { + border-right-width: 0; + border-left: 10px solid #747474; + right: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tip-form-invalid { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #747474; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tip-form-invalid-mc { + background-color: #747474; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tip-form-invalid { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tip-form-invalid-frameInfo { + font-family: th-2-2-2-2-1-1-1-1-1-1-1-1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tip-form-invalid-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tip-form-invalid-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tip-form-invalid-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tip-form-invalid-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tip-form-invalid-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tip-form-invalid-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tip-form-invalid-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tip-form-invalid-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tip-form-invalid-tr, +.x-tip-form-invalid-br, +.x-tip-form-invalid-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tip-form-invalid-tl, +.x-tip-form-invalid-bl, +.x-tip-form-invalid-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tip-form-invalid-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tip-form-invalid-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-tip-form-invalid-tl, +.x-tip-form-invalid-bl, +.x-tip-form-invalid-tr, +.x-tip-form-invalid-br, +.x-tip-form-invalid-tc, +.x-tip-form-invalid-bc, +.x-tip-form-invalid-ml, +.x-tip-form-invalid-mr { + background-image: url(images/tip/tip-form-invalid-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-tip-form-invalid-ml, +.x-tip-form-invalid-mr { + background-image: url(images/tip/tip-form-invalid-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tip-form-invalid-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:318 */ +.x-tip-form-invalid { + background-color: #747474; + border-color: #747474; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:328 */ +.x-tip-form-invalid .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #747474; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:343 */ +.x-tip-header-form-invalid .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:353 */ +.x-tip-header-form-invalid .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:364 */ +.x-tip-header-form-invalid { + padding: 3px 3px 0 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:368 */ +.x-tip-header-title-form-invalid { + color: #f0f0f0; + font-size: 13px; + font-weight: bold; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:374 */ +.x-tip-body-form-invalid { + padding: 3px 3px 3px 22px; + color: #f0f0f0; + font-size: 13px; + font-weight: 300; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:379 */ +.x-tip-body-form-invalid a { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:390 */ +.x-tip-form-invalid .x-tip-anchor { + border: 10px solid transparent; + _border-color: pink; + _filter: chroma(color=pink); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:467 */ +.x-tip-form-invalid .x-tip-anchor-top { + border-top-width: 0; + border-bottom: 10px solid #747474; + top: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:473 */ +.x-tip-form-invalid .x-tip-anchor-bottom { + border-bottom-width: 0; + border-top: 10px solid #747474; + bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:479 */ +.x-tip-form-invalid .x-tip-anchor-left { + border-left-width: 0; + border-right: 10px solid #747474; + left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tip/Tip.scss:485 */ +.x-tip-form-invalid .x-tip-anchor-right { + border-right-width: 0; + border-left: 10px solid #747474; + right: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tip/Tip.scss:25 */ +.x-tip-body-form-invalid { + background: 1px 1px no-repeat; + background-image: url(images/form/exclamation.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tip/Tip.scss:28 */ +.x-tip-body-form-invalid li { + margin-bottom: 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tip/Tip.scss:30 */ +.x-tip-body-form-invalid li.last { + margin-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:1 */ +.x-color-picker { + width: 192px; + height: 120px; + background-color: #fff; + border-color: #fff; + border-width: 0; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:10 */ +.x-color-picker-item { + width: 24px; + height: 24px; + border-width: 1px; + border-color: #fff; + border-style: solid; + background-color: #fff; + cursor: pointer; + padding: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:22 */ +a.x-color-picker-item:hover { + border-color: #8bb8f3; + background-color: #d9d9d9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:27 */ +.x-color-picker-selected { + border-color: #8bb8f3; + background-color: #d9d9d9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/picker/Color.scss:32 */ +.x-color-picker-item-inner { + line-height: 16px; + border-color: #d0d0d0; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:1 */ +.x-html-editor-tb .x-btn-icon-el { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:7 */ +.x-html-editor-tb .x-edit-bold, +.x-menu-item div.x-edit-bold { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-bold:before, +.x-menu-item div.x-edit-bold:before { + content: "\f032"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:18 */ +.x-html-editor-tb .x-edit-italic, +.x-menu-item div.x-edit-italic { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-italic:before, +.x-menu-item div.x-edit-italic:before { + content: "\f033"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:29 */ +.x-html-editor-tb .x-edit-underline, +.x-menu-item div.x-edit-underline { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-underline:before, +.x-menu-item div.x-edit-underline:before { + content: "\f0cd"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:40 */ +.x-html-editor-tb .x-edit-forecolor, +.x-menu-item div.x-edit-forecolor { + font: 16px/1 ExtJS; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-forecolor:before, +.x-menu-item div.x-edit-forecolor:before { + content: "\e60e"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:51 */ +.x-html-editor-tb .x-edit-backcolor, +.x-menu-item div.x-edit-backcolor { + font: 16px/1 ExtJS; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-backcolor:before, +.x-menu-item div.x-edit-backcolor:before { + content: "\e60d"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:62 */ +.x-html-editor-tb .x-edit-justifyleft, +.x-menu-item div.x-edit-justifyleft { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-justifyleft:before, +.x-menu-item div.x-edit-justifyleft:before { + content: "\f036"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:73 */ +.x-html-editor-tb .x-edit-justifycenter, +.x-menu-item div.x-edit-justifycenter { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-justifycenter:before, +.x-menu-item div.x-edit-justifycenter:before { + content: "\f037"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:84 */ +.x-html-editor-tb .x-edit-justifyright, +.x-menu-item div.x-edit-justifyright { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-justifyright:before, +.x-menu-item div.x-edit-justifyright:before { + content: "\f038"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:95 */ +.x-html-editor-tb .x-edit-insertorderedlist, +.x-menu-item div.x-edit-insertorderedlist { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-insertorderedlist:before, +.x-menu-item div.x-edit-insertorderedlist:before { + content: "\f0cb"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:106 */ +.x-html-editor-tb .x-edit-insertunorderedlist, +.x-menu-item div.x-edit-insertunorderedlist { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-insertunorderedlist:before, +.x-menu-item div.x-edit-insertunorderedlist:before { + content: "\f0ca"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:117 */ +.x-html-editor-tb .x-edit-increasefontsize, +.x-menu-item div.x-edit-increasefontsize { + font: 16px/1 ExtJS; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-increasefontsize:before, +.x-menu-item div.x-edit-increasefontsize:before { + content: "\e610"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:128 */ +.x-html-editor-tb .x-edit-decreasefontsize, +.x-menu-item div.x-edit-decreasefontsize { + font: 16px/1 ExtJS; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-decreasefontsize:before, +.x-menu-item div.x-edit-decreasefontsize:before { + content: "\e60f"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:139 */ +.x-html-editor-tb .x-edit-sourceedit, +.x-menu-item div.x-edit-sourceedit { + font: 16px/1 ExtJS; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-sourceedit:before, +.x-menu-item div.x-edit-sourceedit:before { + content: "\e604"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:150 */ +.x-html-editor-tb .x-edit-createlink, +.x-menu-item div.x-edit-createlink { + font: 16px/1 FontAwesome; + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-html-editor-tb .x-edit-createlink:before, +.x-menu-item div.x-edit-createlink:before { + content: "\f0c1"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:161 */ +.x-html-editor-tip .x-tip-bd .x-tip-bd-inner { + padding: 5px; + padding-bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:166 */ +.x-html-editor-tb .x-font-select { + font-size: 13px; + font-family: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:171 */ +.x-html-editor-wrap textarea { + font: 300 13px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + background-color: #fff; + resize: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/form/field/HtmlEditor.scss:177 */ +.x-htmleditor-iframe { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:320 */ +.x-form-text-default.x-tagfield { + padding: 3px 0 0 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:324 */ +.x-form-text-default .x-tagfield-input { + margin: 0 4px 3px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:328 */ +.x-form-text-default .x-tagfield-input-field { + height: 24px; + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:333 */ +.x-form-text-default .x-tagfield-item { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + background-color: #ececec; + border: 1px solid #ececec; + padding: 0 21px 0 5px; + margin: 0 4px 3px 0; + color: #404040; + line-height: 22px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:344 */ +.x-form-text-default .x-tagfield-item:hover { + background-color: #e5e5e5; + border-color: #e5e5e5; + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:352 */ +.x-form-text-default .x-tagfield-item.x-tagfield-item-selected { + background-color: #7fb5e4; + border-color: #7fb5e4; + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:367 */ +.x-form-text-default .x-tagfield-item-close { + width: 12px; + height: 12px; + top: 5px; + right: 3px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=85)"; + opacity: 0.85; + font: 12px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-form-text-default .x-tagfield-item-close:before { + content: "\f00d"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:384 */ +.x-form-text-default .x-tagfield-item-close:hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=93)"; + opacity: 0.93; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:395 */ +.x-form-text-default .x-tagfield-item-close:active { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:412 */ +.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/form/field/Tag.scss:416 */ +.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close:hover { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:5 */ +.x-grid-view, +.x-tree-view { + z-index: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:11 */ +.x-theme-row-height-el { + height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:15 */ +.x-grid-body { + background: #fff; + border-width: 2px 1px 1px; + border-style: solid; + border-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:22 */ +.x-grid-empty { + padding: 10px; + color: grey; + background-color: #fff; + font: 300 13px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:30 */ +.x-grid-item { + color: #404040; + font: 300 13px/19px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:36 */ +.x-grid-item-alt { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:40 */ +.x-grid-item-over { + color: #404040; + background-color: #eaeff4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:47 */ +.x-grid-item-focused { + outline: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:51 */ +.x-grid-item-focused .x-grid-cell-inner { + z-index: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:57 */ +.x-keyboard-mode .x-grid-item-focused { + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:60 */ +.x-keyboard-mode .x-grid-item-focused .x-grid-cell-inner:before { + content: ""; + position: absolute; + z-index: -1; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + pointer-events: none; + border: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:83 */ +.x-grid-item-selected { + color: #404040; + background-color: #ffefbb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:89 */ +.x-grid-with-row-lines .x-grid-item { + border-style: solid; + border-width: 1px 0 0; + border-color: #e9e9e9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:95 */ +.x-grid-with-row-lines .x-grid-item:first-child { + border-top-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:101 */ +.x-grid-with-row-lines .x-grid-item.x-grid-item-over { + border-style: solid; + border-color: #dee3e8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:106 */ +.x-grid-with-row-lines .x-grid-item-over + .x-grid-item { + border-top-style: solid; + border-top-color: #dee3e8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:111 */ +.x-grid-with-row-lines .x-grid-item.x-grid-item-selected { + border-style: solid; + border-color: #f2e3b2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:116 */ +.x-grid-with-row-lines .x-grid-item-selected + .x-grid-item { + border-top-style: solid; + border-top-color: #f2e3b2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:121 */ +.x-grid-with-row-lines .x-grid-item:last-child { + border-bottom-width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:131 */ +.x-ie8 .x-grid-with-row-lines .x-grid-item { + border-width: 1px 0; + margin-top: -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:136 */ +.x-ie8 .x-grid-with-row-lines .x-grid-item:first-child { + margin-top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:142 */ +.x-grid-cell-inner { + position: relative; + text-overflow: ellipsis; + padding: 7px 10px 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:158 */ +.x-grid-cell-special { + border-color: #e9e9e9; + border-style: solid; + border-right-width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:210 */ +.x-grid-dirty-cell > .x-grid-cell-inner:after { + content: "\e602"; + font: 14px/1 ExtJS; + color: #cf4c35; + position: absolute; + top: 0; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:238 */ +.x-grid-row .x-grid-cell-selected { + color: #404040; + background-color: #ffefbb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:245 */ +.x-grid-with-col-lines .x-grid-cell { + border-style: solid; + border-color: #e9e9e9; + border-width: 0 1px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:251 */ +.x-grid-with-col-lines .x-grid-item-over .x-grid-cell { + border-color: #dee3e8; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:256 */ +.x-grid-with-col-lines .x-grid-item-selected .x-grid-cell { + border-color: #f2e3b2; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/Table.scss:269 */ +.x-grid-resize-marker { + width: 1px; + background-color: #0f0f0f; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/DropZone.scss:1 */ +.x-grid-drop-indicator { + position: absolute; + height: 1px; + line-height: 0px; + background-color: #77bc71; + overflow: visible; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/DropZone.scss:9 */ +.x-grid-drop-indicator .x-grid-drop-indicator-left { + position: absolute; + top: -8px; + left: -12px; + background-image: url(images/grid/dd-insert-arrow-right.png); + height: 16px; + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/DropZone.scss:18 */ +.x-grid-drop-indicator .x-grid-drop-indicator-right { + position: absolute; + top: -8px; + right: -11px; + background-image: url(images/grid/dd-insert-arrow-left.png); + height: 16px; + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/DropZone.scss:1 */ +.x-col-move-top, +.x-col-move-bottom { + width: 9px; + height: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/DropZone.scss:7 */ +.x-col-move-top { + background-image: url(images/grid/col-move-top.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/DropZone.scss:11 */ +.x-col-move-bottom { + background-image: url(images/grid/col-move-bottom.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:1 */ +.x-grid-header-ct { + border: 1px solid #d0d0d0; + border-bottom-color: #fff; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:14 */ +.x-accordion-item .x-grid-header-ct { + border-width: 0 0 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:21 */ +.x-grid-header-ct-hidden { + border-top: 0 !important; + border-bottom: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:31 */ +.x-grid-body { + border-top-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:35 */ +.x-hmenu-sort-asc { + font: 16px/24px ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-hmenu-sort-asc:before { + content: "\e61a"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:46 */ +.x-hmenu-sort-desc { + font: 16px/24px ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-hmenu-sort-desc:before { + content: "\e619"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/header/Container.scss:57 */ +.x-cols-icon { + font: 16px/24px ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-cols-icon:before { + content: "\e601"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:1 */ +.x-column-header { + border-right: 1px solid #d0d0d0; + color: #404040; + font: 400 13px/19px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + outline: 0; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:27 */ +.x-group-sub-header { + background: transparent; + border-top: 1px solid #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:32 */ +.x-group-sub-header .x-column-header-inner { + padding: 6px 10px 6px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:37 */ +.x-column-header-inner { + padding: 7px 10px 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:41 */ +.x-column-header-inner-empty { + text-overflow: clip; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:50 */ +.x-keyboard-mode .x-column-header.x-column-header-focus { + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:51 */ +.x-keyboard-mode .x-column-header.x-column-header-focus .x-column-header-inner:after { + content: ""; + position: absolute; + z-index: 5; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + border: 1px solid #7fb5e4; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:65 */ +.x-keyboard-mode .x-column-header.x-column-header-focus.x-group-sub-header .x-column-header-inner:before { + bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:79 */ +.x-column-header-over { + background-image: none; + background-color: #eaeff4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:83 */ +.x-column-header-sort-ASC, +.x-column-header-sort-DESC { + background-image: none; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:111 */ +.x-column-header-open { + background-color: #eaeff4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:114 */ +.x-column-header-open .x-column-header-trigger { + background-color: #dee3e8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:119 */ +.x-column-header-over .x-column-header-trigger, +.x-column-header-open .x-column-header-trigger { + width: 24px; + cursor: pointer; + font: 16px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-column-header-over .x-column-header-trigger:before, +.x-column-header-open .x-column-header-trigger:before { + content: "\f0d7"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:127 */ +.x-column-header-over .x-column-header-trigger:before, +.x-column-header-open .x-column-header-trigger:before { + top: 50%; + margin-top: -8px; + text-align: center; + position: relative; + display: block; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:151 */ +.x-column-header-align-right .x-column-header-text { + margin-right: 18px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:165 */ +.x-column-header-sort-ASC .x-column-header-text-inner, +.x-column-header-sort-DESC .x-column-header-text-inner { + background-position: right center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:167 */ +.x-column-header-sort-ASC .x-column-header-text-inner:after, +.x-column-header-sort-DESC .x-column-header-text-inner:after { + display: inline-block; + text-align: center; + margin-left: 5px; + width: 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:139 */ +.x-column-header-sort-ASC .x-column-header-text-inner:after { + content: "\f176"; + font: 14px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:139 */ +.x-column-header-sort-DESC .x-column-header-text-inner:after { + content: "\f175"; + font: 14px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:224 */ +.x-no-header-borders .x-column-header { + border: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Column.scss:227 */ +.x-no-header-borders .x-column-header .x-column-header-inner { + padding-top: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Action.scss:1 */ +.x-grid-cell-inner-action-col { + padding: 7px 4px 7px 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Action.scss:14 */ +.x-action-col-cell .x-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Action.scss:18 */ +.x-action-col-icon { + color: #919191; + font-size: 18px; + height: 18px; + width: 18px; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:2 */ +.x-column-header-checkbox .x-column-header-inner, +.x-grid-checkcolumn-cell-inner { + padding: 7px 4px 7px 4px; + text-overflow: clip; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:20 */ +.x-column-header-checkbox { + border-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:22 */ +.x-column-header-checkbox .x-column-header-text { + overflow: visible; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:139 */ +.x-column-header-checkbox .x-column-header-checkbox:after, +.x-grid-checkcolumn:after { + content: "\e614"; + font: 18px/1 ExtJS; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:42 */ +.x-item-disabled .x-column-header-checkbox .x-column-header-checkbox, +.x-item-disabled .x-grid-checkcolumn { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:139 */ +.x-grid-hd-checker-on .x-column-header-checkbox:after, +.x-grid-checkcolumn-checked:after { + content: "\e613"; + font: 18px/1 ExtJS; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:139 */ +.x-grid-item-selected .x-selmodel-column .x-grid-checkcolumn:after { + content: "\e613"; + font: 18px/1 ExtJS; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Check.scss:79 */ +.x-gecko .x-selmodel-checkbox .x-grid-checkcolumn { + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/RowNumberer.scss:1 */ +.x-grid-cell-row-numberer { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/RowNumberer.scss:10 */ +.x-grid-cell-inner-row-numberer { + padding: 7px 5px 6px 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-grid-cell-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-grid-cell-small-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-grid-cell-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-grid-cell-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-grid-cell-small-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-grid-cell-small-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-grid-cell-small-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-grid-cell-small-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-grid-cell-small-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-grid-cell-small-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-grid-cell-small-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-grid-cell-small-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-grid-cell-small-tr, +.x-btn-grid-cell-small-br, +.x-btn-grid-cell-small-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-grid-cell-small-tl, +.x-btn-grid-cell-small-bl, +.x-btn-grid-cell-small-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-grid-cell-small-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-grid-cell-small-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-btn-grid-cell-small-tl, +.x-btn-grid-cell-small-bl, +.x-btn-grid-cell-small-tr, +.x-btn-grid-cell-small-br, +.x-btn-grid-cell-small-tc, +.x-btn-grid-cell-small-bc, +.x-btn-grid-cell-small-ml, +.x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-btn-grid-cell-small-ml, +.x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-grid-cell-small-mc { + padding: 7px 7px 7px 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-grid-cell-small { + border-color: #5897ce; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-grid-cell-small { + min-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-grid-cell-small { + min-height: auto; + height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-grid-cell-small { + font: 400 12px/16px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-grid-cell-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-grid-cell-small { + max-width: calc(100% - 16px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-grid-cell-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-grid-cell-small { + max-width: calc(100% - 15px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-grid-cell-small { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-grid-cell-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-grid-cell-small, +.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-grid-cell-small, +.x-btn-icon-bottom > .x-btn-icon-el-grid-cell-small { + min-width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-grid-cell-small.x-btn-glyph { + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-grid-cell-small { + margin-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + margin-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-grid-cell-small { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-grid-cell-small { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-grid-cell-small { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-grid-cell-small, +.x-btn-split-bottom > .x-btn-button-grid-cell-small { + padding-bottom: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-grid-cell-small.x-btn-arrow-right:after { + width: 8px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-grid-cell-small.x-btn-arrow-bottom:after { + height: 8px; + content: "\f0d7"; + font: 16px/8px FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-grid-cell-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-grid-cell-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-grid-cell-small.x-btn-split-right:after { + width: 14px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-grid-cell-small.x-btn-split-bottom { + margin-bottom: -7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-grid-cell-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-grid-cell-small.x-btn-split-bottom:after { + height: 14px; + content: "\f0d7"; + font: 16px/14px FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-grid-cell-small { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-grid-cell-small { + background-image: none; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-grid-cell-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 21px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-grid-cell-small { + border-color: #518bbd; + background-image: none; + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-grid-cell-small, +.x-btn.x-btn-pressed.x-btn-grid-cell-small { + border-color: #42719a; + background-image: none; + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-grid-cell-small { + background-image: none; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-grid-cell-small-tl, +.x-btn-over .x-btn-grid-cell-small-bl, +.x-btn-over .x-btn-grid-cell-small-tr, +.x-btn-over .x-btn-grid-cell-small-br, +.x-btn-over .x-btn-grid-cell-small-tc, +.x-btn-over .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-grid-cell-small-ml, +.x-btn-over .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-grid-cell-small-mc { + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-mc { + background-color: #5795cb; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tl, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-bl, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tr, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-br, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tc, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-bc, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-tl, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-bl, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-tr, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-br, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-tc, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-ml, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-mr, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-ml, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-mc, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-mc { + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-mc { + background-color: #477aa6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-grid-cell-small-tl, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-bl, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-tr, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-br, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-tc, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-grid-cell-small-ml, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-grid-cell-small-mc { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-grid-cell-small { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-grid-cell-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first .x-btn-grid-cell-small-mc { + padding-right: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-middle .x-btn-grid-cell-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-last .x-btn-grid-cell-small-mc { + padding-left: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first .x-btn-grid-cell-small-mc { + padding-bottom: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-middle .x-btn-grid-cell-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-last .x-btn-grid-cell-small-mc { + padding-top: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-grid-cell-small:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-grid-cell-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-grid-cell-small-cell > .x-grid-cell-inner >.x-btn-grid-cell-small { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/column/Widget.scss:110 */ +.x-grid-widgetcolumn-cell-inner { + text-overflow: clip; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:1 */ +.x-grid-group-hd { + border-width: 0 0 1px 0; + border-style: solid; + border-color: #d0d0d0; + padding: 8px 10px; + background: #fff; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:10 */ +.x-grid-group-hd-not-collapsible { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:14 */ +.x-grid-group-hd-collapsible .x-grid-group-title { + padding: 0 0 0 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-grid-group-hd-collapsible .x-grid-group-title:before { + content: "\f146"; + font-size: 14px; + font-family: FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:36 */ +.x-grid-group-title { + color: #606060; + font: 400 13px/15px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-grid-group-hd-collapsed .x-grid-group-title:before { + content: "\f0fe"; + font-size: 14px; + font-family: FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Grouping.scss:54 */ +.x-group-by-icon { + font: 16px/24px ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-group-by-icon:before { + content: "\e607"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/RowBody.scss:1 */ +.x-grid-rowbody { + font: 300 13px/19px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + padding: 5px 10px 5px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:1 */ +.x-docked-summary { + border-width: 1px; + border-color: #d0d0d0; + border-style: solid; + background: #fff!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:6 */ +.x-docked-summary .x-grid-table { + border: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:14 */ +.x-grid-row-summary .x-grid-cell, +.x-grid-row-summary .x-grid-rowwrap, +.x-grid-row-summary .x-grid-cell-rowbody { + border-color: #e9e9e9; + background-color: #fff !important; + border-top: 1px solid #e9e9e9; + font: 300 13px/19px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:26 */ +.x-docked-summary .x-grid-item, +.x-docked-summary .x-grid-row-summary .x-grid-cell { + border-bottom: 0 none; + border-top: 0 none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:34 */ +.x-docked-summary > :first-child { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/feature/Summary.scss:40 */ +.x-grid-row-summary .x-grid-cell-inner-row-expander { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:818 */ +.x-menu-default { + border-style: solid; + border-width: 1px; + border-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:824 */ +.x-menu-body-default { + background: #fff; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:829 */ +.x-menu-icon-separator-default { + left: 32px; + border-left: solid 1px #d0d0d0; + background-color: #fff; + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:843 */ +.x-menu-item-default { + border-width: 0; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:849 */ +.x-menu-item-default.x-menu-item-focus, +.x-menu-item-default.x-menu-item-active { + background-image: none; + background-color: #7fb5e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:862 */ +.x-nlg .x-menu-item-default.x-menu-item-focus, +.x-nlg .x-menu-item-default.x-menu-item-active { + background: #7fb5e4 repeat-x left top; + background-image: url(images/menu/menu-item-default-active-bg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:869 */ +.x-menu-item-default.x-menu-item-disabled { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:872 */ +.x-menu-item-default.x-menu-item-disabled a { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:877 */ +.x-menu-item-default.x-menu-item-separator { + height: 1px; + border-top: solid 1px #d0d0d0; + background-color: #fff; + margin: 2px 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:885 */ +.x-menu-item-default.x-menu-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:890 */ +.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-icon-ui { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:894 */ +.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-text-default { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:904 */ +.x-menu-item-default .x-form-item-label { + font-size: 13px; + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:911 */ +.x-menu-item-text-default, +.x-menu-item-cmp-default { + margin: 0 8px 0 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:916 */ +.x-menu-item-text-default { + font: 300 13px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 31px; + padding-top: 1px; + color: #000; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:928 */ +.x-menu-item-focus .x-menu-item-text-default, +.x-menu-item-active .x-menu-item-text-default { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:934 */ +.x-menu-item-text-default.x-menu-item-indent { + margin-left: 41px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:938 */ +.x-menu-item-text-default.x-menu-item-indent-no-separator { + margin-left: 36px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:942 */ +.x-menu-item-text-default.x-menu-item-indent-right-icon { + margin-right: 40px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:946 */ +.x-menu-item-text-default.x-menu-item-indent-right-arrow { + margin-right: 29px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:950 */ +.x-menu-item-disabled .x-menu-item-text-default { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:982 */ +.x-menu-item-indent-default { + margin-left: 41px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:992 */ +.x-menu-item-icon-default { + width: 24px; + height: 24px; + top: 4px; + left: 4px; + line-height: 24px; + font-size: 16px; + color: #919191; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1001 */ +.x-menu-item-focus .x-menu-item-icon-default, +.x-menu-item-active .x-menu-item-icon-default { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1008 */ +.x-ie8 .x-menu-item-focus .x-menu-item-icon-default, +.x-ie8 .x-menu-item-active .x-menu-item-icon-default { + color: #fff !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1041 */ +.x-ie8 .x-menu-item-icon-default.x-menu-item-glyph { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1049 */ +.x-menu-item-icon-default.x-menu-item-icon-right { + width: 24px; + height: 24px; + top: 4px; + right: 4px; + left: auto; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1070 */ +.x-menu-item-icon-default.x-menu-item-checkbox { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1080 */ +.x-menu-item-focus .x-menu-item-icon-default.x-menu-item-checkbox, +.x-menu-item-active .x-menu-item-icon-default.x-menu-item-checkbox { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1087 */ +.x-menu-item-checked .x-menu-item-icon-default.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-menu-item-checked .x-menu-item-icon-default.x-menu-item-checkbox:before { + content: "\f046"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1095 */ +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-item-checkbox:before { + content: "\f096"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1110 */ +.x-menu-item-focus .x-menu-item-icon-default.x-menu-group-icon, +.x-menu-item-active .x-menu-item-icon-default.x-menu-group-icon { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1117 */ +.x-menu-item-checked .x-menu-item-icon-default.x-menu-group-icon { + font: 18px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-menu-item-checked .x-menu-item-icon-default.x-menu-group-icon:before { + content: "\f00c"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1125 */ +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-group-icon { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1130 */ +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-group-icon:before { + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1140 */ +.x-menu-item-arrow-default { + width: 16px; + height: 16px; + top: 8px; + right: 0; + margin: 0 4px 0; + font: 16px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-menu-item-arrow-default:before { + content: "\f0da"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1152 */ +.x-menu-item-focus .x-menu-item-arrow-default, +.x-menu-item-active .x-menu-item-arrow-default { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1161 */ +.x-menu-item-focus .x-menu-item-arrow-default, +.x-menu-item-active .x-menu-item-arrow-default { + top: 8px; + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-menu-default-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-menu-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-menu-default { + cursor: pointer; + color: #919191; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-menu-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-menu-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-menu-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:311 */ +.x-box-scroller-menu-default.x-box-scroller-top, +.x-box-scroller-menu-default.x-box-scroller-bottom { + height: 16px; + width: 16px; + left: 50%; + margin-left: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:338 */ +.x-box-scroller-menu-default.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-menu-default.x-box-scroller-top:before { + content: "\f077"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:363 */ +.x-box-scroller-menu-default.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-menu-default.x-box-scroller-bottom:before { + content: "\f078"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1217 */ +.x-ie8 .x-box-scroller-menu-default { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:818 */ +.x-menu-default-menubar { + border-style: solid; + border-width: 1px; + border-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:824 */ +.x-menu-body-default-menubar { + background: #fff; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:829 */ +.x-menu-icon-separator-default-menubar { + left: 32px; + border-left: solid 1px #d0d0d0; + background-color: #fff; + width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:843 */ +.x-menu-item-default-menubar { + border-width: 0; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:849 */ +.x-menu-item-default-menubar.x-menu-item-focus, +.x-menu-item-default-menubar.x-menu-item-active { + background-image: none; + background-color: #7fb5e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:862 */ +.x-nlg .x-menu-item-default-menubar.x-menu-item-focus, +.x-nlg .x-menu-item-default-menubar.x-menu-item-active { + background: #7fb5e4 repeat-x left top; + background-image: url(images/menu/menu-item-default-menubar-active-bg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:869 */ +.x-menu-item-default-menubar.x-menu-item-disabled { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:872 */ +.x-menu-item-default-menubar.x-menu-item-disabled a { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:877 */ +.x-menu-item-default-menubar.x-menu-item-separator { + height: 1px; + border-top: solid 1px #d0d0d0; + background-color: #fff; + margin: 2px 0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:885 */ +.x-menu-item-default-menubar.x-menu-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:890 */ +.x-ie9m .x-menu-item-default-menubar.x-menu-item-disabled .x-menu-item-icon-ui { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:894 */ +.x-ie9m .x-menu-item-default-menubar.x-menu-item-disabled .x-menu-item-text-default-menubar { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:904 */ +.x-menu-item-default-menubar .x-form-item-label { + font-size: 13px; + color: #000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:911 */ +.x-menu-item-text-default-menubar, +.x-menu-item-cmp-default-menubar { + margin: 0 8px 0 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:916 */ +.x-menu-item-text-default-menubar { + font: 300 13px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 31px; + padding-top: 1px; + color: #000; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:928 */ +.x-menu-item-focus .x-menu-item-text-default-menubar, +.x-menu-item-active .x-menu-item-text-default-menubar { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:934 */ +.x-menu-item-text-default-menubar.x-menu-item-indent { + margin-left: 41px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:938 */ +.x-menu-item-text-default-menubar.x-menu-item-indent-no-separator { + margin-left: 36px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:942 */ +.x-menu-item-text-default-menubar.x-menu-item-indent-right-icon { + margin-right: 40px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:946 */ +.x-menu-item-text-default-menubar.x-menu-item-indent-right-arrow { + margin-right: 27px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:950 */ +.x-menu-item-disabled .x-menu-item-text-default-menubar { + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:982 */ +.x-menu-item-indent-default-menubar { + margin-left: 41px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:992 */ +.x-menu-item-icon-default-menubar { + width: 24px; + height: 24px; + top: 4px; + left: 4px; + line-height: 24px; + font-size: 16px; + color: #919191; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1001 */ +.x-menu-item-focus .x-menu-item-icon-default-menubar, +.x-menu-item-active .x-menu-item-icon-default-menubar { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1008 */ +.x-ie8 .x-menu-item-focus .x-menu-item-icon-default-menubar, +.x-ie8 .x-menu-item-active .x-menu-item-icon-default-menubar { + color: #fff !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1041 */ +.x-ie8 .x-menu-item-icon-default-menubar.x-menu-item-glyph { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1049 */ +.x-menu-item-icon-default-menubar.x-menu-item-icon-right { + width: 24px; + height: 24px; + top: 4px; + right: 4px; + left: auto; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1070 */ +.x-menu-item-icon-default-menubar.x-menu-item-checkbox { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1080 */ +.x-menu-item-focus .x-menu-item-icon-default-menubar.x-menu-item-checkbox, +.x-menu-item-active .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1087 */ +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-item-checkbox:before { + content: "\f046"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1095 */ +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-item-checkbox:before { + content: "\f096"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1110 */ +.x-menu-item-focus .x-menu-item-icon-default-menubar.x-menu-group-icon, +.x-menu-item-active .x-menu-item-icon-default-menubar.x-menu-group-icon { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1117 */ +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-group-icon { + font: 18px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-group-icon:before { + content: "\f00c"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1125 */ +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-group-icon { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1130 */ +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-group-icon:before { + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1140 */ +.x-menu-item-arrow-default-menubar { + width: 9px; + height: 6px; + top: 9px; + right: 5px; + margin: 0 4px 0; + font: 16px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-menu-item-arrow-default-menubar:before { + content: "\f0d7"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1152 */ +.x-menu-item-focus .x-menu-item-arrow-default-menubar, +.x-menu-item-active .x-menu-item-arrow-default-menubar { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1161 */ +.x-menu-item-focus .x-menu-item-arrow-default-menubar, +.x-menu-item-active .x-menu-item-arrow-default-menubar { + top: 9px; + right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-menu-default-menubar-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-menu-default-menubar-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-menu-default-menubar { + cursor: pointer; + color: #919191; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:311 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-top, +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom { + height: 16px; + width: 16px; + left: 50%; + margin-left: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:338 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-top:before { + content: "\f077"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:363 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom:before { + content: "\f078"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/menu/Menu.scss:1217 */ +.x-ie8 .x-box-scroller-menu-default-menubar { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:1 */ +.x-grid-filters-filtered-column { + font-style: italic; + font-weight: 600; + text-decoration: underline; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:7 */ +.x-grid-filters-icon { + background-repeat: no-repeat; + background-position: center center; + color: #919191; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:16 */ +.x-grid-filters-find .x-form-item-label-inner { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-grid-filters-find .x-form-item-label-inner:before { + content: "\f002"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:26 */ +.x-grid-filters-gt .x-form-item-label-inner { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-grid-filters-gt .x-form-item-label-inner:before { + content: "\f054"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:36 */ +.x-grid-filters-lt .x-form-item-label-inner { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-grid-filters-lt .x-form-item-label-inner:before { + content: "\f053"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/filters/Filters.scss:46 */ +.x-grid-filters-eq .x-form-item-label-inner { + font: 16px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-grid-filters-eq .x-form-item-label-inner:before { + content: "\e605"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:1 */ +.x-grid-locked .x-grid-inner-locked { + border-width: 0 2px 0 0; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:12 */ +.x-grid-locked-split .x-grid-inner-normal { + border-width: 0 0 0 2px; + border-style: solid; + border-left-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:24 */ +.x-grid-locking-body { + border-width: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:31 */ +.x-grid-locking-body > .x-splitter { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:35 */ +.x-grid-locking-body > .x-splitter-active { + background-color: #b4b4b4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:40 */ +.x-grid-inner-locked { + border-right-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:45 */ +.x-grid-inner-locked .x-column-header-last, +.x-grid-inner-locked .x-grid-cell-last { + border-right-width: 0!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:75 */ +.x-hmenu-lock { + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-hmenu-lock:before { + content: "\f023"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:86 */ +.x-hmenu-unlock { + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-hmenu-unlock:before { + content: "\f09c"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:101 */ +.x-grid-scrollbar-clipper > .x-grid-view, +.x-grid-scrollbar-clipper > .x-tree-view { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:108 */ +.x-grid-scrollbar-clipper-locked, +.x-grid-scrollbar-locked { + border-width: 0 2px 0 0; + border-style: solid; + border-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/locking/Lockable.scss:123 */ +.x-grid-scroll-container { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/Editing.scss:18 */ +.x-grid-editor .x-form-display-field { + text-overflow: ellipsis; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/Editing.scss:24 */ +.x-grid-editor .x-form-action-col-field { + padding: 7px 4px 7px 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/Editing.scss:30 */ +.x-grid-editor .x-form-text { + padding-left: 9px; + padding-right: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/CellEditing.scss:3 */ +.x-tree-cell-editor .x-form-text { + padding-left: 5px; + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:2 */ +.x-grid-row-editor .x-field { + margin: 0 3px 0 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:7 */ +.x-grid-row-editor .x-form-display-field { + padding: 7px 8px 6px 8px; + line-height: 19px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:18 */ +.x-ie9m .x-grid-row-editor .x-form-display-field { + min-height: 19px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:26 */ +.x-grid-row-editor .x-form-action-col-field { + padding: 7px 1px 7px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:37 */ +.x-grid-row-editor .x-form-text { + padding: 5px 6px 4px 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:41 */ +.x-gecko .x-grid-row-editor .x-form-text { + padding-left: 6px; + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:50 */ +.x-grid-row-editor .x-panel-body { + border-top: 1px solid #d0d0d0 !important; + border-bottom: 1px solid #d0d0d0 !important; + padding: 5px 0 5px 0; + background-color: #e5edf4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:60 */ +.x-grid-with-col-lines .x-grid-row-editor .x-form-cb { + margin-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-grid-row-editor-buttons-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 5px; + -webkit-border-bottom-right-radius: 5px; + border-bottom-right-radius: 5px; + -moz-border-radius-bottomleft: 5px; + -webkit-border-bottom-left-radius: 5px; + border-bottom-left-radius: 5px; + padding: 5px 5px 5px 5px; + border-width: 0 1px 1px 1px; + border-style: solid; + background-color: #e5edf4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-grid-row-editor-buttons-default-bottom-mc { + background-color: #e5edf4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-grid-row-editor-buttons-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-grid-row-editor-buttons-default-bottom-frameInfo { + font-family: th-0-5-5-5-0-1-1-1-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-grid-row-editor-buttons-default-bottom-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-grid-row-editor-buttons-default-bottom-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-grid-row-editor-buttons-default-bottom-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-grid-row-editor-buttons-default-bottom-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-grid-row-editor-buttons-default-bottom-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-grid-row-editor-buttons-default-bottom-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-grid-row-editor-buttons-default-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-grid-row-editor-buttons-default-bottom-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-grid-row-editor-buttons-default-bottom-tr, +.x-grid-row-editor-buttons-default-bottom-br, +.x-grid-row-editor-buttons-default-bottom-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-grid-row-editor-buttons-default-bottom-tl, +.x-grid-row-editor-buttons-default-bottom-bl, +.x-grid-row-editor-buttons-default-bottom-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-grid-row-editor-buttons-default-bottom-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-grid-row-editor-buttons-default-bottom-bc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-grid-row-editor-buttons-default-bottom-tl, +.x-grid-row-editor-buttons-default-bottom-bl, +.x-grid-row-editor-buttons-default-bottom-tr, +.x-grid-row-editor-buttons-default-bottom-br, +.x-grid-row-editor-buttons-default-bottom-tc, +.x-grid-row-editor-buttons-default-bottom-bc, +.x-grid-row-editor-buttons-default-bottom-ml, +.x-grid-row-editor-buttons-default-bottom-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-grid-row-editor-buttons-default-bottom-ml, +.x-grid-row-editor-buttons-default-bottom-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-grid-row-editor-buttons-default-bottom-mc { + padding: 5px 1px 1px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-grid-row-editor-buttons-default-top { + -moz-border-radius-topleft: 5px; + -webkit-border-top-left-radius: 5px; + border-top-left-radius: 5px; + -moz-border-radius-topright: 5px; + -webkit-border-top-right-radius: 5px; + border-top-right-radius: 5px; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 5px 5px 5px 5px; + border-width: 1px 1px 0 1px; + border-style: solid; + background-color: #e5edf4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-grid-row-editor-buttons-default-top-mc { + background-color: #e5edf4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-grid-row-editor-buttons-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-grid-row-editor-buttons-default-top-frameInfo { + font-family: th-5-5-0-5-1-1-0-1-5-5-5-5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-grid-row-editor-buttons-default-top-tl { + background-position: 0 -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-grid-row-editor-buttons-default-top-tr { + background-position: right -15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-grid-row-editor-buttons-default-top-bl { + background-position: 0 -20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-grid-row-editor-buttons-default-top-br { + background-position: right -25px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-grid-row-editor-buttons-default-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-grid-row-editor-buttons-default-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-grid-row-editor-buttons-default-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-grid-row-editor-buttons-default-top-bc { + background-position: 0 -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-grid-row-editor-buttons-default-top-tr, +.x-grid-row-editor-buttons-default-top-br, +.x-grid-row-editor-buttons-default-top-mr { + padding-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-grid-row-editor-buttons-default-top-tl, +.x-grid-row-editor-buttons-default-top-bl, +.x-grid-row-editor-buttons-default-top-ml { + padding-left: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-grid-row-editor-buttons-default-top-tc { + height: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-grid-row-editor-buttons-default-top-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-grid-row-editor-buttons-default-top-tl, +.x-grid-row-editor-buttons-default-top-bl, +.x-grid-row-editor-buttons-default-top-tr, +.x-grid-row-editor-buttons-default-top-br, +.x-grid-row-editor-buttons-default-top-tc, +.x-grid-row-editor-buttons-default-top-bc, +.x-grid-row-editor-buttons-default-top-ml, +.x-grid-row-editor-buttons-default-top-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-grid-row-editor-buttons-default-top-ml, +.x-grid-row-editor-buttons-default-top-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-grid-row-editor-buttons-default-top-mc { + padding: 1px 1px 5px 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:108 */ +.x-grid-row-editor-buttons { + border-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:112 */ +.x-row-editor-update-button { + margin-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:115 */ +.x-row-editor-cancel-button { + margin-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:131 */ +.x-grid-row-editor-errors .x-tip-body { + padding: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowEditing.scss:136 */ +.x-grid-row-editor-errors-item { + list-style: disc; + margin-left: 15px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowExpander.scss:1 */ +.x-grid-cell-inner-row-expander { + padding: 8px 8px 8px 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowExpander.scss:16 */ +.x-grid-row-expander { + width: 16px; + height: 16px; + cursor: pointer; + color: #919191; + font: 14px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-grid-row-expander:before { + content: "\f146"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/plugin/RowExpander.scss:31 */ +.x-grid-row-collapsed .x-grid-row-expander { + font: 14px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-grid-row-collapsed .x-grid-row-expander:before { + content: "\f0fe"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:1 */ +.x-ssm-row-numberer-hd { + cursor: se-resize!important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:6 */ +.x-ssm-row-numberer-cell { + cursor: e-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:11 */ +.x-ssm-column-select .x-column-header { + cursor: s-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:16 */ +.x-ssm-extender-drag-handle { + height: 7px; + width: 7px; + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/grid/selection/SpreadsheetModel.scss:22 */ +.x-ssm-extender-mask { + border: 1px dotted #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:1 */ +.x-accordion-layout-ct { + background-color: #fff; + padding: 5px 5px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:6 */ +.x-accordion-hd .x-panel-header-title { + color: #404040; + font-weight: 300; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + text-transform: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:13 */ +.x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus, +.x-edge .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus:after, +.x-edge .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:34 */ +.x-accordion-item { + margin: 0 0 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:37 */ +.x-accordion-item .x-accordion-hd { + background: #ececec; + border-width: 0; + border-color: #5fa2dd; + padding: 12px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:45 */ +.x-accordion-item .x-accordion-hd-over { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:48 */ +.x-accordion-item .x-accordion-hd-over .x-tool-tool-el { + background-color: #f6f6f6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:54 */ +.x-accordion-item .x-accordion-hd-sibling-expanded { + border-top-color: #5fa2dd; + border-top-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:59 */ +.x-accordion-item .x-accordion-hd-last-collapsed { + border-bottom-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:63 */ +.x-accordion-item .x-accordion-body { + border-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:72 */ +.x-accordion-hd .x-tool-tool-el { + background-color: #ececec; + color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:77 */ +.x-accordion-hd .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:87 */ +.x-accordion-hd .x-tool-collapse-top, +.x-accordion-hd .x-tool-collapse-bottom { + font: 16px/1 FontAwesome; + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-accordion-hd .x-tool-collapse-top:before, +.x-accordion-hd .x-tool-collapse-bottom:before { + content: "\f068"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:106 */ +.x-accordion-hd .x-tool-expand-top, +.x-accordion-hd .x-tool-expand-bottom { + font: 16px/1 FontAwesome; + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-accordion-hd .x-tool-expand-top:before, +.x-accordion-hd .x-tool-expand-bottom:before { + content: "\f067"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Accordion.scss:126 */ +.x-keyboard-mode .x-accordion-hd .x-tool-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus, +.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Border.scss:5 */ +body.x-border-layout-ct, +div.x-border-layout-ct { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/layout/container/Form.scss:1 */ +.x-form-layout-wrap { + border-spacing: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:1 */ +.x-resizable-handle { + position: absolute; + z-index: 100; + font-size: 1px; + line-height: 10px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; + background-color: #ececec; + color: #919191; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:20 */ +.x-collapsed .x-resizable-handle { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:24 */ +.x-resizable-handle-southeast { + cursor: se-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:27 */ +.x-resizable-handle-southeast:before { + position: absolute; + bottom: 0; + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:34 */ +.x-resizable-handle-northwest { + cursor: nw-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:37 */ +.x-resizable-handle-northwest:before { + position: absolute; + top: 0; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:44 */ +.x-resizable-handle-northeast { + cursor: ne-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:47 */ +.x-resizable-handle-northeast:before { + position: absolute; + top: 0; + right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:54 */ +.x-resizable-handle-southwest { + cursor: sw-resize; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:57 */ +.x-resizable-handle-southwest:before { + position: absolute; + bottom: 0; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:68 */ +.x-resizable-handle-east:before, +.x-resizable-handle-west:before { + display: block; + position: absolute; + top: 50%; + margin-top: -0.5em; + width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:78 */ +.x-resizable-handle-east { + cursor: e-resize; + width: 10px; + right: 0; + top: 0; + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:86 */ +.x-resizable-handle-south { + cursor: s-resize; + height: 10px; + left: 0; + right: 0; + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:94 */ +.x-resizable-handle-west { + cursor: w-resize; + width: 10px; + left: 0; + top: 0; + bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:102 */ +.x-resizable-handle-north { + cursor: n-resize; + height: 10px; + left: 0; + right: 0; + top: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:110 */ +.x-resizable-handle-southeast { + width: 10px; + height: 10px; + right: 0; + bottom: 0; + z-index: 101; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:118 */ +.x-resizable-handle-northwest { + width: 10px; + height: 10px; + left: 0; + top: 0; + z-index: 101; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:126 */ +.x-resizable-handle-northeast { + width: 10px; + height: 10px; + right: 0; + top: 0; + z-index: 101; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:134 */ +.x-resizable-handle-southwest { + width: 10px; + height: 10px; + left: 0; + bottom: 0; + z-index: 101; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:145 */ +.x-tablet .x-resizable-handle-north, +.x-tablet .x-resizable-handle-south { + height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:149 */ +.x-tablet .x-resizable-handle-east, +.x-tablet .x-resizable-handle-west { + width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:153 */ +.x-tablet .x-resizable-handle-northwest, +.x-tablet .x-resizable-handle-northeast, +.x-tablet .x-resizable-handle-southwest, +.x-tablet .x-resizable-handle-southeast { + width: 20px; + height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:163 */ +.x-window .x-window-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:167 */ +.x-window-collapsed .x-window-handle { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:172 */ +.x-resizable-proxy { + border: 1px dashed #3b5a82; + position: absolute; + overflow: hidden; + z-index: 50000; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:180 */ +.x-resizable-handle-over, +.x-resizable-pinned .x-resizable-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:186 */ +.x-resizable-handle-east-over, +.x-resizable-handle-west-over, +.x-resizable-pinned > .x-resizable-handle-east, +.x-resizable-pinned > .x-resizable-handle-west { + font: 16px/1 FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-resizable-handle-east-over:before, +.x-resizable-handle-west-over:before, +.x-resizable-pinned > .x-resizable-handle-east:before, +.x-resizable-pinned > .x-resizable-handle-west:before { + content: "\f142"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:198 */ +.x-resizable-handle-south-over, +.x-resizable-handle-north-over, +.x-resizable-pinned > .x-resizable-handle-south, +.x-resizable-pinned > .x-resizable-handle-north { + font: 16px/10px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-resizable-handle-south-over:before, +.x-resizable-handle-north-over:before, +.x-resizable-pinned > .x-resizable-handle-south:before, +.x-resizable-pinned > .x-resizable-handle-north:before { + content: "\f141"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:210 */ +.x-resizable-handle-southeast-over, +.x-resizable-pinned > .x-resizable-handle-southeast { + font: 16px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-resizable-handle-southeast-over:before, +.x-resizable-pinned > .x-resizable-handle-southeast:before { + content: "\e60c"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:220 */ +.x-resizable-handle-northwest-over, +.x-resizable-pinned > .x-resizable-handle-northwest { + font: 16px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-resizable-handle-northwest-over:before, +.x-resizable-pinned > .x-resizable-handle-northwest:before { + content: "\e609"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:230 */ +.x-resizable-handle-northeast-over, +.x-resizable-pinned > .x-resizable-handle-northeast { + font: 16px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-resizable-handle-northeast-over:before, +.x-resizable-pinned > .x-resizable-handle-northeast:before { + content: "\e60a"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/resizer/Resizer.scss:240 */ +.x-resizable-handle-southwest-over, +.x-resizable-pinned > .x-resizable-handle-southwest { + font: 16px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-resizable-handle-southwest-over:before, +.x-resizable-pinned > .x-resizable-handle-southwest:before { + content: "\e60b"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:2 */ +.x-slider:before { + border: 1px solid #d0d0d0; + content: ''; + position: absolute; + border-radius: 2px; + background-color: #eee; + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:20 */ +.x-slider-thumb { + background-color: #f6f6f6; + border: 1px solid #d0d0d0; + border-radius: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:28 */ +.x-slider-thumb:before { + color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:33 */ +.x-slider-thumb-over { + background-color: #fcfcfc; + border-color: #c8cdd2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:36 */ +.x-slider-thumb-over:before { + color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:42 */ +.x-keyboard-mode .x-slider-focus .x-slider-thumb { + background-color: #f6f6f6; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:45 */ +.x-keyboard-mode .x-slider-focus .x-slider-thumb:before { + color: #a6c7e5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:52 */ +.x-keyboard-mode .x-slider-focus .x-slider-thumb-over { + background-color: #fcfcfc; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:57 */ +.x-slider-thumb-drag { + background-color: #f1f1f1; + border-color: #c0c8cf; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:60 */ +.x-slider-thumb-drag:before { + color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:66 */ +.x-keyboard-mode .x-slider-focus .x-slider-thumb-drag { + background-color: #f1f1f1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:79 */ +.x-slider-horz { + padding-left: 10px; + background: no-repeat 0 -20px; + margin: 6px 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:86 */ +.x-slider-horz .x-slider-end { + padding-right: 10px; + background: no-repeat right -40px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:91 */ +.x-slider-horz .x-slider-inner { + height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:96 */ +.x-slider-horz:before { + height: 10px; + width: 100%; + top: 50%; + left: 0; + margin-top: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:106 */ +.x-slider-horz .x-slider-thumb { + width: 20px; + height: 20px; + margin-left: -10px; + font: 12px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-slider-horz .x-slider-thumb:before { + content: "\e612"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:170 */ +.x-slider-ct-vert { + /* Vertical styles */ + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:174 */ +.x-slider-vert { + padding-top: 10px; + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:181 */ +.x-slider-vert > .x-slider-end { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:183 */ +.x-slider-vert > .x-slider-end > .x-slider-inner { + height: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:189 */ +.x-slider-vert:before { + width: 10px; + height: 100%; + left: 10px; + top: 0; + margin-left: -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:199 */ +.x-slider-vert .x-slider-end { + padding-bottom: 10px; + background: no-repeat -20px bottom; + width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:205 */ +.x-slider-vert .x-slider-inner { + width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:209 */ +.x-slider-vert .x-slider-thumb { + width: 20px; + height: 20px; + margin-bottom: -10px; + font: 12px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-slider-vert .x-slider-thumb:before { + content: "\e605"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/slider/Multi.scss:262 */ +.x-slider-default-cell > .x-grid-cell-inner, +.x-sliderwidget-default-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tab-default-top { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0; + border-style: solid; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tab-default-top-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tab-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tab-default-top-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tab-default-top-tl { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tab-default-top-tr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tab-default-top-bl { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tab-default-top-br { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tab-default-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tab-default-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tab-default-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tab-default-top-bc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tab-default-top-tr, +.x-tab-default-top-br, +.x-tab-default-top-mr { + padding-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tab-default-top-tl, +.x-tab-default-top-bl, +.x-tab-default-top-ml { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tab-default-top-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tab-default-top-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tab-default-top-mc { + padding: 8px 10px 8px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tab-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0 0 0 0; + border-style: solid; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tab-default-bottom-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tab-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tab-default-bottom-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tab-default-bottom-tl { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tab-default-bottom-tr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tab-default-bottom-bl { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tab-default-bottom-br { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tab-default-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tab-default-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tab-default-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tab-default-bottom-bc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tab-default-bottom-tr, +.x-tab-default-bottom-br, +.x-tab-default-bottom-mr { + padding-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tab-default-bottom-tl, +.x-tab-default-bottom-bl, +.x-tab-default-bottom-ml { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tab-default-bottom-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tab-default-bottom-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tab-default-bottom-mc { + padding: 8px 10px 8px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tab-default-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0 0 0 0; + border-style: solid; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tab-default-left-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tab-default-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tab-default-left-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tab-default-left-tl { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tab-default-left-tr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tab-default-left-bl { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tab-default-left-br { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tab-default-left-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tab-default-left-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tab-default-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tab-default-left-bc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tab-default-left-tr, +.x-tab-default-left-br, +.x-tab-default-left-mr { + padding-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tab-default-left-tl, +.x-tab-default-left-bl, +.x-tab-default-left-ml { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tab-default-left-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tab-default-left-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tab-default-left-mc { + padding: 8px 10px 8px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-tab-default-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0 0 0 0; + border-style: solid; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-tab-default-right-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-tab-default-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-tab-default-right-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-tab-default-right-tl { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-tab-default-right-tr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-tab-default-right-bl { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-tab-default-right-br { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-tab-default-right-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-tab-default-right-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-tab-default-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-tab-default-right-bc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-tab-default-right-tr, +.x-tab-default-right-br, +.x-tab-default-right-mr { + padding-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-tab-default-right-tl, +.x-tab-default-right-bl, +.x-tab-default-right-ml { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-tab-default-right-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-tab-default-right-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-tab-default-right-mc { + padding: 8px 10px 8px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2672 */ +.x-tab-default { + border-color: transparent; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2731 */ +.x-tab-default-top { + margin: 0 4px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2740 */ +.x-tab-default-top.x-tab-rotate-left { + margin: 0 0 0 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2763 */ +.x-keyboard-mode .x-tab-default-top.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2794 */ +.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2825 */ +.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2852 */ +.x-tab-default-right { + margin: 0 0 4px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2861 */ +.x-tab-default-right.x-tab-rotate-right { + margin: 4px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2884 */ +.x-keyboard-mode .x-tab-default-right.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2915 */ +.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2946 */ +.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2973 */ +.x-tab-default-bottom { + margin: 0 4px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:2982 */ +.x-tab-default-bottom.x-tab-rotate-left { + margin: 0 0 0 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3005 */ +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3036 */ +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3067 */ +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3094 */ +.x-tab-default-left { + margin: 0 0 4px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3103 */ +.x-tab-default-left.x-tab-rotate-right { + margin: 4px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3126 */ +.x-keyboard-mode .x-tab-default-left.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3157 */ +.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3188 */ +.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3215 */ +.x-tab-button-default { + height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3220 */ +.x-tab-inner-default { + font: 400 13px/20px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #f0f0f0; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3228 */ +.x-tab-bar-plain .x-tab-inner-default { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3236 */ +.x-tab-icon-right > .x-tab-inner-default, +.x-tab-icon-left > .x-tab-inner-default { + max-width: calc(100% - 20px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3244 */ +.x-tab-icon-el-default { + min-height: 20px; + background-position: center center; + font-size: 20px; + line-height: 20px; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3245 */ +.x-tab-icon-left > .x-tab-icon-el-default, +.x-tab-icon-right > .x-tab-icon-el-default { + width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3250 */ +.x-tab-icon-top > .x-tab-icon-el-default, +.x-tab-icon-bottom > .x-tab-icon-el-default { + min-width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3261 */ +.x-tab-bar-plain .x-tab-icon-el-default { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3266 */ +.x-tab-icon-el-default.x-tab-glyph { + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3286 */ +.x-tab-text.x-tab-icon-left > .x-tab-icon-el-default { + margin-right: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3297 */ +.x-tab-text.x-tab-icon-right > .x-tab-icon-el-default { + margin-left: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3308 */ +.x-tab-text.x-tab-icon-top > .x-tab-icon-el-default { + margin-bottom: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3312 */ +.x-tab-text.x-tab-icon-bottom > .x-tab-icon-el-default { + margin-top: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3318 */ +.x-keyboard-mode .x-tab-focus.x-tab-default { + border-color: transparent; + background-color: transparent; + outline: 1px solid #5fa2dd; + outline-offset: -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-tab-focus.x-tab-default, +.x-ie10p .x-keyboard-mode .x-tab-focus.x-tab-default, +.x-edge .x-keyboard-mode .x-tab-focus.x-tab-default { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-tab-focus.x-tab-default:after, +.x-ie10p .x-keyboard-mode .x-tab-focus.x-tab-default:after, +.x-edge .x-keyboard-mode .x-tab-focus.x-tab-default:after { + position: absolute; + content: ' '; + top: 2px; + right: 2px; + bottom: 2px; + left: 2px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3398 */ +.x-keyboard-mode .x-tab-bar-plain .x-tab-focus.x-tab-default .x-tab-inner-default { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3404 */ +.x-keyboard-mode .x-tab-bar-plain .x-tab-focus.x-tab-default .x-tab-icon-el { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3454 */ +.x-tab-over.x-tab-default { + border-color: #000; + background-image: none; + background-color: rgba(0, 0, 0, 0.08); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/background-opacity.scss:19 */ +.x-ie8 .x-tab-over.x-tab-default { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#14000000, endColorstr=#14000000)"; + zoom: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3483 */ +.x-ie8 .x-tab-over.x-tab-default.x-tab-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3489 */ +.x-ie8 .x-tab-over.x-tab-default.x-tab-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3515 */ +.x-tab-bar-plain .x-tab-over.x-tab-default .x-tab-inner-default { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3546 */ +.x-tab-bar-plain .x-tab-over.x-tab-default .x-tab-icon-el { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3567 */ +.x-keyboard-mode .x-tab-focus.x-tab-over.x-tab-default { + border-color: #000; + background-image: none; + background-color: rgba(0, 0, 0, 0.08); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/background-opacity.scss:19 */ +.x-ie8 .x-keyboard-mode .x-tab-focus.x-tab-over.x-tab-default { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#14000000, endColorstr=#14000000)"; + zoom: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3612 */ +.x-keyboard-mode .x-tab-bar-plain .x-tab-focus.x-tab-over.x-tab-default .x-tab-inner-default { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3618 */ +.x-keyboard-mode .x-tab-bar-plain .x-tab-focus.x-tab-over.x-tab-default .x-tab-icon-el { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3642 */ +.x-keyboard-mode.x-ie8 .x-tab-focus.x-tab-over.x-tab-default.x-tab-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3646 */ +.x-keyboard-mode.x-ie8 .x-tab-focus.x-tab-over.x-tab-default.x-tab-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3685 */ +.x-tab.x-tab-active.x-tab-default { + border-color: #fff; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3741 */ +.x-tab.x-tab-active.x-tab-default .x-tab-inner-default { + color: #4c82b1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3746 */ +.x-tab-bar-plain .x-tab.x-tab-active.x-tab-default .x-tab-inner-default { + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3761 */ +.x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #4c82b1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3769 */ +.x-ie8 .x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #82a7c8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3775 */ +.x-tab-bar-plain .x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3797 */ +.x-keyboard-mode .x-tab-focus.x-tab-active.x-tab-default { + border-color: #fff; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3842 */ +.x-keyboard-mode .x-tab-bar-plain .x-tab-focus.x-tab-active.x-tab-default .x-tab-inner-default { + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3848 */ +.x-keyboard-mode .x-tab-bar-plain .x-tab-focus.x-tab-active.x-tab-default .x-tab-icon-el { + color: #404040; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3916 */ +.x-tab.x-tab-disabled.x-tab-default { + border-color: transparent; + background-color: transparent; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3976 */ +.x-tab.x-tab-disabled.x-tab-default .x-tab-inner-default { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:3981 */ +.x-tab-bar-plain .x-tab.x-tab-disabled.x-tab-default .x-tab-inner-default { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4000 */ +.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el-default { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4005 */ +.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el { + color: #f0f0f0; + opacity: 0.3; + filter: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4026 */ +.x-tab-bar-plain .x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4046 */ +.x-nbr .x-tab-default { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-over .x-tab-default-top-tl, +.x-tab-over .x-tab-default-top-bl, +.x-tab-over .x-tab-default-top-tr, +.x-tab-over .x-tab-default-top-br, +.x-tab-over .x-tab-default-top-tc, +.x-tab-over .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-over .x-tab-default-top-ml, +.x-tab-over .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-over .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus .x-tab-default-top-tl, +.x-tab-focus .x-tab-default-top-bl, +.x-tab-focus .x-tab-default-top-tr, +.x-tab-focus .x-tab-default-top-br, +.x-tab-focus .x-tab-default-top-tc, +.x-tab-focus .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus .x-tab-default-top-ml, +.x-tab-focus .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-over .x-tab-default-top-tl, +.x-tab-focus.x-tab-over .x-tab-default-top-bl, +.x-tab-focus.x-tab-over .x-tab-default-top-tr, +.x-tab-focus.x-tab-over .x-tab-default-top-br, +.x-tab-focus.x-tab-over .x-tab-default-top-tc, +.x-tab-focus.x-tab-over .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-over .x-tab-default-top-ml, +.x-tab-focus.x-tab-over .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-over .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-active .x-tab-default-top-tl, +.x-tab.x-tab-active .x-tab-default-top-bl, +.x-tab.x-tab-active .x-tab-default-top-tr, +.x-tab.x-tab-active .x-tab-default-top-br, +.x-tab.x-tab-active .x-tab-default-top-tc, +.x-tab.x-tab-active .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-active .x-tab-default-top-ml, +.x-tab.x-tab-active .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-active .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-active .x-tab-default-top-tl, +.x-tab-focus.x-tab-active .x-tab-default-top-bl, +.x-tab-focus.x-tab-active .x-tab-default-top-tr, +.x-tab-focus.x-tab-active .x-tab-default-top-br, +.x-tab-focus.x-tab-active .x-tab-default-top-tc, +.x-tab-focus.x-tab-active .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-active .x-tab-default-top-ml, +.x-tab-focus.x-tab-active .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-active .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-disabled .x-tab-default-top-tl, +.x-tab.x-tab-disabled .x-tab-default-top-bl, +.x-tab.x-tab-disabled .x-tab-default-top-tr, +.x-tab.x-tab-disabled .x-tab-default-top-br, +.x-tab.x-tab-disabled .x-tab-default-top-tc, +.x-tab.x-tab-disabled .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-disabled .x-tab-default-top-ml, +.x-tab.x-tab-disabled .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-disabled .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-over .x-tab-default-right-tl, +.x-tab-over .x-tab-default-right-bl, +.x-tab-over .x-tab-default-right-tr, +.x-tab-over .x-tab-default-right-br, +.x-tab-over .x-tab-default-right-tc, +.x-tab-over .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-over .x-tab-default-right-ml, +.x-tab-over .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-over .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus .x-tab-default-right-tl, +.x-tab-focus .x-tab-default-right-bl, +.x-tab-focus .x-tab-default-right-tr, +.x-tab-focus .x-tab-default-right-br, +.x-tab-focus .x-tab-default-right-tc, +.x-tab-focus .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus .x-tab-default-right-ml, +.x-tab-focus .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-over .x-tab-default-right-tl, +.x-tab-focus.x-tab-over .x-tab-default-right-bl, +.x-tab-focus.x-tab-over .x-tab-default-right-tr, +.x-tab-focus.x-tab-over .x-tab-default-right-br, +.x-tab-focus.x-tab-over .x-tab-default-right-tc, +.x-tab-focus.x-tab-over .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-over .x-tab-default-right-ml, +.x-tab-focus.x-tab-over .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-over .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-active .x-tab-default-right-tl, +.x-tab.x-tab-active .x-tab-default-right-bl, +.x-tab.x-tab-active .x-tab-default-right-tr, +.x-tab.x-tab-active .x-tab-default-right-br, +.x-tab.x-tab-active .x-tab-default-right-tc, +.x-tab.x-tab-active .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-active .x-tab-default-right-ml, +.x-tab.x-tab-active .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-active .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-active .x-tab-default-right-tl, +.x-tab-focus.x-tab-active .x-tab-default-right-bl, +.x-tab-focus.x-tab-active .x-tab-default-right-tr, +.x-tab-focus.x-tab-active .x-tab-default-right-br, +.x-tab-focus.x-tab-active .x-tab-default-right-tc, +.x-tab-focus.x-tab-active .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-active .x-tab-default-right-ml, +.x-tab-focus.x-tab-active .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-active .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-disabled .x-tab-default-right-tl, +.x-tab.x-tab-disabled .x-tab-default-right-bl, +.x-tab.x-tab-disabled .x-tab-default-right-tr, +.x-tab.x-tab-disabled .x-tab-default-right-br, +.x-tab.x-tab-disabled .x-tab-default-right-tc, +.x-tab.x-tab-disabled .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-disabled .x-tab-default-right-ml, +.x-tab.x-tab-disabled .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-disabled .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-over .x-tab-default-bottom-tl, +.x-tab-over .x-tab-default-bottom-bl, +.x-tab-over .x-tab-default-bottom-tr, +.x-tab-over .x-tab-default-bottom-br, +.x-tab-over .x-tab-default-bottom-tc, +.x-tab-over .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-over .x-tab-default-bottom-ml, +.x-tab-over .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-over .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus .x-tab-default-bottom-tl, +.x-tab-focus .x-tab-default-bottom-bl, +.x-tab-focus .x-tab-default-bottom-tr, +.x-tab-focus .x-tab-default-bottom-br, +.x-tab-focus .x-tab-default-bottom-tc, +.x-tab-focus .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus .x-tab-default-bottom-ml, +.x-tab-focus .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-over .x-tab-default-bottom-tl, +.x-tab-focus.x-tab-over .x-tab-default-bottom-bl, +.x-tab-focus.x-tab-over .x-tab-default-bottom-tr, +.x-tab-focus.x-tab-over .x-tab-default-bottom-br, +.x-tab-focus.x-tab-over .x-tab-default-bottom-tc, +.x-tab-focus.x-tab-over .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-over .x-tab-default-bottom-ml, +.x-tab-focus.x-tab-over .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-over .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-over-fbg.gif); +} \ No newline at end of file diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all-debug_2.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all-debug_2.css new file mode 100644 index 0000000..b41f7a8 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all-debug_2.css @@ -0,0 +1,7347 @@ +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-active .x-tab-default-bottom-tl, +.x-tab.x-tab-active .x-tab-default-bottom-bl, +.x-tab.x-tab-active .x-tab-default-bottom-tr, +.x-tab.x-tab-active .x-tab-default-bottom-br, +.x-tab.x-tab-active .x-tab-default-bottom-tc, +.x-tab.x-tab-active .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-active .x-tab-default-bottom-ml, +.x-tab.x-tab-active .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-active .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-active .x-tab-default-bottom-tl, +.x-tab-focus.x-tab-active .x-tab-default-bottom-bl, +.x-tab-focus.x-tab-active .x-tab-default-bottom-tr, +.x-tab-focus.x-tab-active .x-tab-default-bottom-br, +.x-tab-focus.x-tab-active .x-tab-default-bottom-tc, +.x-tab-focus.x-tab-active .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-active .x-tab-default-bottom-ml, +.x-tab-focus.x-tab-active .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-active .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-disabled .x-tab-default-bottom-tl, +.x-tab.x-tab-disabled .x-tab-default-bottom-bl, +.x-tab.x-tab-disabled .x-tab-default-bottom-tr, +.x-tab.x-tab-disabled .x-tab-default-bottom-br, +.x-tab.x-tab-disabled .x-tab-default-bottom-tc, +.x-tab.x-tab-disabled .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-disabled .x-tab-default-bottom-ml, +.x-tab.x-tab-disabled .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-disabled .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-over .x-tab-default-left-tl, +.x-tab-over .x-tab-default-left-bl, +.x-tab-over .x-tab-default-left-tr, +.x-tab-over .x-tab-default-left-br, +.x-tab-over .x-tab-default-left-tc, +.x-tab-over .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-over .x-tab-default-left-ml, +.x-tab-over .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-over .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus .x-tab-default-left-tl, +.x-tab-focus .x-tab-default-left-bl, +.x-tab-focus .x-tab-default-left-tr, +.x-tab-focus .x-tab-default-left-br, +.x-tab-focus .x-tab-default-left-tc, +.x-tab-focus .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus .x-tab-default-left-ml, +.x-tab-focus .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-focus-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-over .x-tab-default-left-tl, +.x-tab-focus.x-tab-over .x-tab-default-left-bl, +.x-tab-focus.x-tab-over .x-tab-default-left-tr, +.x-tab-focus.x-tab-over .x-tab-default-left-br, +.x-tab-focus.x-tab-over .x-tab-default-left-tc, +.x-tab-focus.x-tab-over .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-over .x-tab-default-left-ml, +.x-tab-focus.x-tab-over .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-over .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-focus-over-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-active .x-tab-default-left-tl, +.x-tab.x-tab-active .x-tab-default-left-bl, +.x-tab.x-tab-active .x-tab-default-left-tr, +.x-tab.x-tab-active .x-tab-default-left-br, +.x-tab.x-tab-active .x-tab-default-left-tc, +.x-tab.x-tab-active .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-active .x-tab-default-left-ml, +.x-tab.x-tab-active .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-active .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab-focus.x-tab-active .x-tab-default-left-tl, +.x-tab-focus.x-tab-active .x-tab-default-left-bl, +.x-tab-focus.x-tab-active .x-tab-default-left-tr, +.x-tab-focus.x-tab-active .x-tab-default-left-br, +.x-tab-focus.x-tab-active .x-tab-default-left-tc, +.x-tab-focus.x-tab-active .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-focus-active-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab-focus.x-tab-active .x-tab-default-left-ml, +.x-tab-focus.x-tab-active .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-focus-active-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab-focus.x-tab-active .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-focus-active-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4065 */ +.x-tab.x-tab-disabled .x-tab-default-left-tl, +.x-tab.x-tab-disabled .x-tab-default-left-bl, +.x-tab.x-tab-disabled .x-tab-default-left-tr, +.x-tab.x-tab-disabled .x-tab-default-left-br, +.x-tab.x-tab-disabled .x-tab-default-left-tc, +.x-tab.x-tab-disabled .x-tab-default-left-bc { + background-image: url(images/tab/tab-default-left-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4074 */ +.x-tab.x-tab-disabled .x-tab-default-left-ml, +.x-tab.x-tab-disabled .x-tab-default-left-mr { + background-image: url(images/tab/tab-default-left-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4079 */ +.x-tab.x-tab-disabled .x-tab-default-left-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-left-disabled-fbg.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4089 */ +.x-tab-default-tl, +.x-tab-default-bl, +.x-tab-default-tr, +.x-tab-default-br { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#00FFFFFF,endColorstr=#00FFFFFF)"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4099 */ +.x-tab-default .x-tab-close-btn { + top: 0; + right: 0; + width: 16px; + height: 16px; + font: 12px/1 FontAwesome; + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tab-default .x-tab-close-btn:before { + content: "\f00d"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4109 */ +.x-tab-bar-plain .x-tab-default .x-tab-close-btn { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4121 */ +.x-tab-default .x-tab-close-btn-over { + background-position: -16px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4131 */ +.x-tab-default .x-tab-close-btn-pressed { + background-position: -32px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4139 */ +.x-keyboard-mode .x-tab-default.x-tab-focus .x-tab-close-btn { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4145 */ +.x-keyboard-mode .x-tab-bar-plain .x-tab-default.x-tab-focus .x-tab-close-btn { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4156 */ +.x-tab-default.x-tab-over .x-tab-close-btn { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4160 */ +.x-tab-bar-plain .x-tab-default.x-tab-over .x-tab-close-btn { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4171 */ +.x-keyboard-mode .x-tab-default.x-tab-focus.x-tab-over .x-tab-close-btn { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4177 */ +.x-keyboard-mode .x-tab-bar-plain .x-tab-default.x-tab-focus.x-tab-over .x-tab-close-btn { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4188 */ +.x-tab-default.x-tab-active .x-tab-close-btn { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4219 */ +.x-keyboard-mode .x-tab-default.x-tab-focus.x-tab-active .x-tab-close-btn { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4235 */ +.x-tab-default.x-tab-disabled .x-tab-close-btn { + color: #fff; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4240 */ +.x-tab-bar-plain .x-tab-default.x-tab-disabled .x-tab-close-btn { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Tab.scss:4262 */ +.x-tab-closable.x-tab-default .x-tab-button { + padding-right: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:389 */ +.x-tab-bar-default { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:428 */ +.x-tab-bar-default-top > .x-tab-bar-body-default { + padding: 8px 4px 0 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:432 */ +.x-tab-bar-default-bottom > .x-tab-bar-body-default { + padding: 0 4px 8px 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:436 */ +.x-tab-bar-default-left > .x-tab-bar-body-default { + padding: 4px 0 8px 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:446 */ +.x-tab-bar-default-right > .x-tab-bar-body-default { + padding: 8px 8px 4px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:459 */ +.x-tab-bar-plain.x-tab-bar-default-top > .x-tab-bar-body-default { + padding: 8px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:463 */ +.x-tab-bar-plain.x-tab-bar-default-bottom > .x-tab-bar-body-default { + padding: 0 0 8px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:467 */ +.x-tab-bar-plain.x-tab-bar-default-left > .x-tab-bar-body-default { + padding: 0 0 0 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:477 */ +.x-tab-bar-plain.x-tab-bar-default-right > .x-tab-bar-body-default { + padding: 0 8px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:490 */ +.x-tab-bar-plain.x-tab-bar-default-horizontal { + border-top-color: transparent; + border-bottom-color: transparent; + border-left-width: 0; + border-right-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:497 */ +.x-tab-bar-plain.x-tab-bar-default-vertical { + border-right-color: transparent; + border-left-color: transparent; + border-top-width: 0; + border-bottom-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:611 */ +.x-tab-bar-horizontal > .x-tab-bar-body-default { + min-height: 44px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:614 */ +.x-ie8m .x-tab-bar-horizontal > .x-tab-bar-body-default { + min-height: 36px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:621 */ +.x-tab-bar-vertical > .x-tab-bar-body-default { + min-width: 44px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:624 */ +.x-ie8m .x-tab-bar-vertical > .x-tab-bar-body-default { + min-width: 36px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-tab-bar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-tab-bar-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-tab-bar-default { + cursor: pointer; + color: #fff; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-tab-bar-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-tab-bar-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-tab-bar-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:232 */ +.x-box-scroller-tab-bar-default.x-box-scroller-left, +.x-box-scroller-tab-bar-default.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:259 */ +.x-box-scroller-tab-bar-default.x-box-scroller-left { + margin-left: 0; + margin-right: 0; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-tab-bar-default.x-box-scroller-left:before { + content: "\f053"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:284 */ +.x-box-scroller-tab-bar-default.x-box-scroller-right { + margin-left: 0; + margin-right: 0; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-tab-bar-default.x-box-scroller-right:before { + content: "\f054"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:311 */ +.x-box-scroller-tab-bar-default.x-box-scroller-top, +.x-box-scroller-tab-bar-default.x-box-scroller-bottom { + height: 24px; + width: 24px; + left: 50%; + margin-left: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:338 */ +.x-box-scroller-tab-bar-default.x-box-scroller-top { + margin-top: 0; + margin-right: 0; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-tab-bar-default.x-box-scroller-top:before { + content: "\f077"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:363 */ +.x-box-scroller-tab-bar-default.x-box-scroller-bottom { + margin-top: 0; + margin-right: 0; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-box-scroller-tab-bar-default.x-box-scroller-bottom:before { + content: "\f078"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:704 */ +.x-tab-bar-more-icon { + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tab-bar-more-icon:before { + content: "\f0c9"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:721 */ +.x-tab-bar-plain.x-tab-bar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:727 */ +.x-tab-bar-plain.x-tab-bar-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:732 */ +.x-tab-bar-plain .x-box-scroller-tab-bar-default { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:780 */ +.x-tab-bar-default-top .x-box-scroller-tab-bar-default { + margin-top: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:784 */ +.x-tab-bar-default-right .x-box-scroller-tab-bar-default { + margin-left: -16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:788 */ +.x-tab-bar-default-bottom .x-box-scroller-tab-bar-default { + margin-top: -16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:792 */ +.x-tab-bar-default-left .x-box-scroller-tab-bar-default { + margin-left: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:801 */ +.x-box-scroller-tab-bar-default { + background-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/tab/Bar.scss:807 */ +.x-box-scroller-tab-bar-default .x-ie8 .x-box-scroller-plain { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:406 */ +.x-breadcrumb-btn-default { + margin: 0 0 0 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:410 */ +.x-breadcrumb-icon-folder-default { + font: 16px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-breadcrumb-icon-folder-default:before { + content: "\f114"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:418 */ +.x-btn-menu-active .x-breadcrumb-icon-folder-default { + font: 16px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-btn-menu-active .x-breadcrumb-icon-folder-default:before { + content: "\f115"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:428 */ +.x-breadcrumb-icon-leaf-default { + font: 16px/1 FontAwesome; + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-breadcrumb-icon-leaf-default:before { + content: "\f016"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:438 */ +.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-arrow:after { + width: 20px; + background-image: url(images/breadcrumb/default-arrow.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:450 */ +.x-btn-menu-active.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-arrow:after { + background-image: url(images/breadcrumb/default-arrow-open.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:463 */ +.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after { + width: 20px; + content: "\f105"; + font: 16px/1 FontAwesome; + color: #919191; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/toolbar/Breadcrumb.scss:500 */ +.x-btn-menu-active.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after { + content: "\f107"; + font: 16px/1 FontAwesome; + color: #919191; + background: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:182 */ +.x-breadcrumb-default-scroller .x-box-scroller-body-horizontal { + margin-left: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:195 */ +.x-breadcrumb-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:200 */ +.x-box-scroller-breadcrumb-default { + cursor: pointer; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:210 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:216 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:222 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:232 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-left, +.x-box-scroller-breadcrumb-default.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:259 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + background-image: url(images/breadcrumb/default-scroll-left.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/layout/container/Box.scss:284 */ +.x-box-scroller-breadcrumb-default.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + background-image: url(images/breadcrumb/default-scroll-right.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:1 */ +.x-tree-expander { + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:8 */ +.x-tree-arrows .x-tree-expander { + font-size: 16px; + font-family: FontAwesome; + color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tree-arrows .x-tree-expander:before { + content: "\f0da"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:18 */ +.x-tree-arrows .x-grid-tree-node-expanded .x-tree-expander { + font-size: 16px; + font-family: FontAwesome; + color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tree-arrows .x-grid-tree-node-expanded .x-tree-expander:before { + content: "\f0d7"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:61 */ +.x-tree-elbow-plus, +.x-tree-elbow-end-plus { + font-size: 14px; + font-family: FontAwesome; + color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tree-elbow-plus:before, +.x-tree-elbow-end-plus:before { + content: "\f0fe"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:69 */ +.x-grid-tree-node-expanded .x-tree-elbow-plus, +.x-grid-tree-node-expanded .x-tree-elbow-end-plus { + font-size: 14px; + font-family: FontAwesome; + color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-grid-tree-node-expanded .x-tree-elbow-plus:before, +.x-grid-tree-node-expanded .x-tree-elbow-end-plus:before { + content: "\f146"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:157 */ +.x-tree-icon { + width: 16px; + height: 32px; + line-height: 32px; + color: #5fa2dd; + font-size: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:165 */ +.x-tree-elbow-img { + width: 18px; + height: 32px; + line-height: 32px; + margin-right: 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:179 */ +.x-tree-icon, +.x-tree-elbow-img, +.x-tree-checkbox { + margin-top: -7px; + margin-bottom: -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:189 */ +.x-tree-icon-leaf { + font-size: 16px; + font-family: FontAwesome; + color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tree-icon-leaf:before { + content: "\f016"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:204 */ +.x-tree-icon-parent { + font-size: 16px; + font-family: FontAwesome; + color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tree-icon-parent:before { + content: "\f114"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:220 */ +.x-tree-icon-parent-expanded { + font-size: 16px; + font-family: FontAwesome; + color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tree-icon-parent-expanded:before { + content: "\f115"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:236 */ +.x-tree-icon-custom { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:240 */ +.x-tree-icon-custom:before { + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:252 */ +.x-tree-checkbox { + margin-right: 6px; + top: 7px; + width: 18px; + height: 18px; + font: 18px/1 ExtJS; + color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tree-checkbox:before { + content: "\e614"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:272 */ +.x-tree-checkbox-checked { + font: 18px/1 ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tree-checkbox-checked:before { + content: "\e613"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:280 */ +.x-grid-tree-loading .x-tree-icon { + background-image: url(images/tree/loading.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:290 */ +.x-tree-node-text { + padding-left: 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/View.scss:302 */ +.x-grid-cell-inner-treecolumn { + padding: 7px 10px 6px 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/ViewDropZone.scss:2 */ +.x-tree-drop-ok-append .x-dd-drop-icon, +.x-tree-drop-ok-above .x-dd-drop-icon, +.x-tree-drop-ok-below .x-dd-drop-icon, +.x-tree-drop-ok-between .x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #a4cf6d; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/etc/mixins/font-icon.scss:132 */ +.x-tree-drop-ok-append .x-dd-drop-icon:before, +.x-tree-drop-ok-above .x-dd-drop-icon:before, +.x-tree-drop-ok-below .x-dd-drop-icon:before, +.x-tree-drop-ok-between .x-dd-drop-icon:before { + content: "\f055"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/tree/ViewDropZone.scss:26 */ +.x-tree-ddindicator { + height: 1px; + border-width: 1px 0px 0px; + border-style: dotted; + border-color: green; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/MultiSelector.scss:1 */ +.x-multiselector-remove { + font-size: 110%; + color: #d0d0d0; + cursor: pointer; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/MultiSelector.scss:6 */ +.x-multiselector-remove .x-grid-cell-inner { + padding: 7px 4px 6px 4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/MultiSelector.scss:11 */ +.x-grid-item-over .x-multiselector-remove { + color: red; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/view/MultiSelector.scss:16 */ +.x-multiselector-search-input .x-form-text::-ms-clear { + display: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:1 */ +.x-toast-icon-information { + background-image: url(images/window/toast/icon16_info.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:5 */ +.x-toast-icon-error { + background-image: url(images/window/toast/icon16_error.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:11 */ +.x-toast-window .x-window-body { + /* Using standard theme */ + padding: 15px 5px 15px 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:17 */ +.x-toast-light .x-window-header { + /* Custom styling */ + background-color: #7fb5e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:21 */ +.x-toast-light .x-tool-img { + background-color: #7fb5e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:25 */ +.x-toast-light { + background-image: url(images/window/toast/fader.png); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/src/window/Toast.scss:29 */ +.x-toast-light .x-window-body { + padding: 15px 5px 20px 5px; + background-color: transparent; + border: 0px solid white; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-plain-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-plain-toolbar-small-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-plain-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-plain-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-plain-toolbar-small-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-plain-toolbar-small-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-plain-toolbar-small-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-plain-toolbar-small-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-plain-toolbar-small-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-plain-toolbar-small-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-plain-toolbar-small-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-plain-toolbar-small-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-plain-toolbar-small-tr, +.x-btn-plain-toolbar-small-br, +.x-btn-plain-toolbar-small-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-plain-toolbar-small-tl, +.x-btn-plain-toolbar-small-bl, +.x-btn-plain-toolbar-small-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-plain-toolbar-small-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-plain-toolbar-small-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-plain-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-plain-toolbar-small { + border-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-plain-toolbar-small { + min-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-plain-toolbar-small { + min-height: auto; + height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-plain-toolbar-small { + font: 400 12px/16px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-small { + max-width: calc(100% - 16px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-small { + max-width: calc(100% - 15px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-plain-toolbar-small { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-plain-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small { + min-width: 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-plain-toolbar-small.x-btn-glyph { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small { + margin-right: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + margin-left: 3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-small, +.x-btn-split-bottom > .x-btn-button-plain-toolbar-small { + padding-bottom: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-plain-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-plain-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-plain-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-plain-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-plain-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small { + margin-right: 5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-small { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-plain-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-plain-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-plain-toolbar-small { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-small { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-plain-toolbar-small, +.x-btn.x-btn-pressed.x-btn-plain-toolbar-small { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-plain-toolbar-small { + background-image: none; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-plain-toolbar-small-tl, +.x-btn-over .x-btn-plain-toolbar-small-bl, +.x-btn-over .x-btn-plain-toolbar-small-tr, +.x-btn-over .x-btn-plain-toolbar-small-br, +.x-btn-over .x-btn-plain-toolbar-small-tc, +.x-btn-over .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-plain-toolbar-small-ml, +.x-btn-over .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-plain-toolbar-small-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bc { + background-image: url(images/btn/btn-plain-toolbar-small-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mr { + background-image: url(images/btn/btn-plain-toolbar-small-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-plain-toolbar-small { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-plain-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first .x-btn-plain-toolbar-small-mc { + padding-right: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle .x-btn-plain-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last .x-btn-plain-toolbar-small-mc { + padding-left: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first .x-btn-plain-toolbar-small-mc { + padding-bottom: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle .x-btn-plain-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last .x-btn-plain-toolbar-small-mc { + padding-top: 7px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-small:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-small:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-small:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-plain-toolbar-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-plain-toolbar-small-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-small { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-plain-toolbar-medium { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 8px 8px 8px; + border-width: 1px; + border-style: solid; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-plain-toolbar-medium-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-plain-toolbar-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-plain-toolbar-medium-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-8-8-8-8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-plain-toolbar-medium-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-plain-toolbar-medium-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-plain-toolbar-medium-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-plain-toolbar-medium-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-plain-toolbar-medium-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-plain-toolbar-medium-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-plain-toolbar-medium-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-plain-toolbar-medium-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-plain-toolbar-medium-tr, +.x-btn-plain-toolbar-medium-br, +.x-btn-plain-toolbar-medium-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-plain-toolbar-medium-tl, +.x-btn-plain-toolbar-medium-bl, +.x-btn-plain-toolbar-medium-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-plain-toolbar-medium-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-plain-toolbar-medium-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-plain-toolbar-medium-mc { + padding: 8px 8px 8px 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-plain-toolbar-medium { + border-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-plain-toolbar-medium { + min-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-plain-toolbar-medium { + min-height: auto; + height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-plain-toolbar-medium { + font: 400 14px/18px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 8px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium { + max-width: calc(100% - 20px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium { + max-width: calc(100% - 19px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-plain-toolbar-medium { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-plain-toolbar-medium { + font-size: 20px; + height: 20px; + color: #919191; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium, +.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium, +.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium { + min-width: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-plain-toolbar-medium.x-btn-glyph { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium { + margin-right: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + margin-left: 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-medium, +.x-btn-split-bottom > .x-btn-button-plain-toolbar-medium { + padding-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-right:after { + width: 20px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-bottom:after { + height: 14px; + content: "\f0d7"; + font: 20px/14px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-split-right > .x-btn-button { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-split-right:after { + width: 26px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; + padding-left: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom { + margin-bottom: -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom:after { + height: 24px; + content: "\f0d7"; + font: 20px/24px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium { + margin-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-medium { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-plain-toolbar-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 34px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-plain-toolbar-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-plain-toolbar-medium { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-plain-toolbar-medium, +.x-btn.x-btn-pressed.x-btn-plain-toolbar-medium { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-plain-toolbar-medium { + background-image: none; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-plain-toolbar-medium-tl, +.x-btn-over .x-btn-plain-toolbar-medium-bl, +.x-btn-over .x-btn-plain-toolbar-medium-tr, +.x-btn-over .x-btn-plain-toolbar-medium-br, +.x-btn-over .x-btn-plain-toolbar-medium-tc, +.x-btn-over .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-plain-toolbar-medium-ml, +.x-btn-over .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-plain-toolbar-medium-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tr, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-br, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tc, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-br, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-ml, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-ml, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tr, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-br, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tc, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bc { + background-image: url(images/btn/btn-plain-toolbar-medium-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-ml, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mr { + background-image: url(images/btn/btn-plain-toolbar-medium-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-plain-toolbar-medium { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-plain-toolbar-medium { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first .x-btn-plain-toolbar-medium-mc { + padding-right: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle .x-btn-plain-toolbar-medium-mc { + padding-right: 8px !important; + padding-left: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last .x-btn-plain-toolbar-medium-mc { + padding-left: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first .x-btn-plain-toolbar-medium-mc { + padding-bottom: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle .x-btn-plain-toolbar-medium-mc { + padding-top: 8px !important; + padding-bottom: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last .x-btn-plain-toolbar-medium-mc { + padding-top: 8px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-medium:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-medium:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-plain-toolbar-medium-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-plain-toolbar-medium-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-medium { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-btn-plain-toolbar-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-btn-plain-toolbar-large-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-btn-plain-toolbar-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-btn-plain-toolbar-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-btn-plain-toolbar-large-tl { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-btn-plain-toolbar-large-tr { + background-position: right -3px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-btn-plain-toolbar-large-bl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-btn-plain-toolbar-large-br { + background-position: right -5px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-btn-plain-toolbar-large-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-btn-plain-toolbar-large-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-btn-plain-toolbar-large-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-btn-plain-toolbar-large-bc { + background-position: 0 -1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-btn-plain-toolbar-large-tr, +.x-btn-plain-toolbar-large-br, +.x-btn-plain-toolbar-large-mr { + padding-right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-btn-plain-toolbar-large-tl, +.x-btn-plain-toolbar-large-bl, +.x-btn-plain-toolbar-large-ml { + padding-left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-btn-plain-toolbar-large-tc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-btn-plain-toolbar-large-bc { + height: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-btn-plain-toolbar-large-mc { + padding: 9px 9px 9px 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2463 */ +.x-btn-plain-toolbar-large { + border-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2470 */ +.x-btn-button-plain-toolbar-large { + min-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2475 */ +.x-ie9m .x-btn-button-plain-toolbar-large { + min-height: auto; + height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2482 */ +.x-btn-inner-plain-toolbar-large { + font: 400 16px/20px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + color: #606060; + padding: 0 10px; + max-width: 100%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2502 */ +.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-large { + max-width: calc(100% - 24px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2510 */ +.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-large { + max-width: calc(100% - 23px); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2516 */ +.x-ie10p .x-btn-inner-plain-toolbar-large { + max-width: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2521 */ +.x-btn-icon-el-plain-toolbar-large { + font-size: 24px; + height: 24px; + color: #919191; + line-height: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2527 */ +.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large, +.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2532 */ +.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large, +.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large { + min-width: 24px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2554 */ +.x-ie8 .x-btn-icon-el-plain-toolbar-large.x-btn-glyph { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2561 */ +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large { + margin-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2572 */ +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + margin-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2583 */ +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large { + margin-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2587 */ +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large { + margin-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2593 */ +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2596 */ +.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2603 */ +.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-large, +.x-btn-split-bottom > .x-btn-button-plain-toolbar-large { + padding-bottom: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2609 */ +.x-btn-wrap-plain-toolbar-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2636 */ +.x-btn-wrap-plain-toolbar-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2663 */ +.x-btn-wrap-plain-toolbar-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2671 */ +.x-btn-wrap-plain-toolbar-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2676 */ +.x-btn-wrap-plain-toolbar-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; + padding-left: 9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2702 */ +.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom { + margin-bottom: -9px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2704 */ +.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2715 */ +.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2748 */ +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large { + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2751 */ +.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large { + margin-right: 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2757 */ +.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-large { + background-image: none; + background-color: transparent; + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2793 */ +.x-btn-plain-toolbar-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2810 */ +.x-keyboard-mode .x-btn-plain-toolbar-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2817 */ +.x-btn-over.x-btn-plain-toolbar-large { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2845 */ +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-large { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2874 */ +.x-btn.x-btn-menu-active.x-btn-plain-toolbar-large, +.x-btn.x-btn-pressed.x-btn-plain-toolbar-large { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2904 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2933 */ +.x-btn.x-btn-disabled.x-btn-plain-toolbar-large { + background-image: none; + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2966 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-focus-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2974 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-focus-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2978 */ +.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2991 */ +.x-btn-over .x-btn-plain-toolbar-large-tl, +.x-btn-over .x-btn-plain-toolbar-large-bl, +.x-btn-over .x-btn-plain-toolbar-large-tr, +.x-btn-over .x-btn-plain-toolbar-large-br, +.x-btn-over .x-btn-plain-toolbar-large-tc, +.x-btn-over .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:2999 */ +.x-btn-over .x-btn-plain-toolbar-large-ml, +.x-btn-over .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3003 */ +.x-btn-over .x-btn-plain-toolbar-large-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3016 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-focus-over-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3024 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-focus-over-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3028 */ +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mc { + background-color: #ececec; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3043 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bl, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tr, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-br, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tc, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bl, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-br, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3051 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-ml, +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mr, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-ml, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3055 */ +.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mc, +.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3069 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3077 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3081 */ +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mc { + background-color: #e2e2e2; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3095 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bl, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tr, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-br, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tc, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bc { + background-image: url(images/btn/btn-plain-toolbar-large-disabled-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3103 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-ml, +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mr { + background-image: url(images/btn/btn-plain-toolbar-large-disabled-sides.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3107 */ +.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mc { + background-color: transparent; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3117 */ +.x-nbr .x-btn-plain-toolbar-large { + background-image: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3123 */ +.x-btn-disabled.x-btn-plain-toolbar-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3142 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3144 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first .x-btn-plain-toolbar-large-mc { + padding-right: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3148 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3150 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle .x-btn-plain-toolbar-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3156 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last .x-btn-plain-toolbar-large-mc { + padding-left: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3163 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3165 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first .x-btn-plain-toolbar-large-mc { + padding-bottom: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3169 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3171 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle .x-btn-plain-toolbar-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3177 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last .x-btn-plain-toolbar-large-mc { + padding-top: 9px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3183 */ +.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-large:after { + content: ' '; + border-style: solid; + border-width: 0; + position: absolute; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3201 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3207 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first:after { + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3210 */ +.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last:after { + right: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3216 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3222 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first:after { + top: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3225 */ +.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last:after { + bottom: 1px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3233 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-large:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3249 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-large:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3267 */ +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large:after, +.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large:after { + border-width: 1px; + border-color: #5fa2dd; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3294 */ +.x-button-plain-toolbar-large-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/button/Button.scss:3299 */ +.x-button-plain-toolbar-large-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-large { + vertical-align: top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/button/Button.scss:220 */ +.x-btn-plain-toolbar-small-disabled .x-btn-icon-el, +.x-btn-plain-toolbar-medium-disabled .x-btn-icon-el, +.x-btn-plain-toolbar-large-disabled .x-btn-icon-el { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/button/Button.scss:223 */ +.x-ie8 .x-btn-plain-toolbar-small-disabled .x-btn-icon-el, +.x-ie8 .x-btn-plain-toolbar-medium-disabled .x-btn-icon-el, +.x-ie8 .x-btn-plain-toolbar-large-disabled .x-btn-icon-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:799 */ +.x-panel-light { + border-color: #d0d0d0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:802 */ +.x-panel-light.x-masked { + border-color: #e8e8e8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:810 */ +.x-panel-header-light { + font-size: 16px; + border: 1px solid #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:819 */ +.x-panel-header-light .x-tool-tool-el { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:836 */ +.x-panel-header-light .x-tool-tool-el { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:842 */ +.x-panel-header-light-horizontal { + padding: 11px 15px 12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:846 */ +.x-panel-header-light-horizontal .x-panel-header-light-tab-bar { + margin-top: -11px; + margin-bottom: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:854 */ +.x-panel-header-light-horizontal.x-header-noborder { + padding: 12px 16px 12px 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:858 */ +.x-panel-header-light-horizontal.x-header-noborder .x-panel-header-light-tab-bar { + margin-top: -12px; + margin-bottom: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:866 */ +.x-panel-header-light-vertical { + padding: 15px 11px 15px 12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:870 */ +.x-panel-header-light-vertical .x-panel-header-light-tab-bar { + margin-right: -11px; + margin-left: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:878 */ +.x-panel-header-light-vertical.x-header-noborder { + padding: 16px 12px 16px 12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:882 */ +.x-panel-header-light-vertical.x-header-noborder .x-panel-header-light-tab-bar { + margin-right: -12px; + margin-left: -12px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:916 */ +.x-panel-header-title-light { + color: #606060; + font-size: 16px; + font-weight: 400; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:929 */ +.x-keyboard-mode .x-panel-header-title-light.x-title-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:950 */ +.x-panel-header-title-light > .x-title-text-light { + text-transform: none; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:997 */ +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1002 */ +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1014 */ +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1019 */ +.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1031 */ +.x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light { + width: 16px; + height: 16px; + font-size: 16px; + color: #606060; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1051 */ +.x-ie8 .x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light.x-title-glyph { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1062 */ +.x-panel-body-light { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 13px; + font-weight: 300; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1226 */ +.x-panel-header-light { + background-image: none; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1230 */ +.x-panel-header-light-vertical { + background-image: none; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1288 */ +.x-panel .x-panel-header-light-collapsed-border-top { + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1292 */ +.x-panel .x-panel-header-light-collapsed-border-right { + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1296 */ +.x-panel .x-panel-header-light-collapsed-border-bottom { + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1300 */ +.x-panel .x-panel-header-light-collapsed-border-left { + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1336 */ +.x-panel-header-light-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1346 */ +.x-panel-header-light-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1358 */ +.x-panel-header-light-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1368 */ +.x-panel-header-light-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1381 */ +.x-keyboard-mode .x-panel-header-light .x-tool-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1429 */ +.x-panel-light-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-panel-light-outer-border-l { + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-panel-light-outer-border-b { + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-panel-light-outer-border-bl { + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-panel-light-outer-border-r { + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-panel-light-outer-border-rl { + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-panel-light-outer-border-rb { + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-panel-light-outer-border-rbl { + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-panel-light-outer-border-t { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-panel-light-outer-border-tl { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-panel-light-outer-border-tb { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-panel-light-outer-border-tbl { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-panel-light-outer-border-tr { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-panel-light-outer-border-trl { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-panel-light-outer-border-trb { + border-top-color: #d0d0d0 !important; + border-top-width: 1px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 1px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-panel-light-outer-border-trbl { + border-color: #d0d0d0 !important; + border-width: 1px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:799 */ +.x-panel-light-framed { + border-color: #d0d0d0; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:802 */ +.x-panel-light-framed.x-masked { + border-color: #e8e8e8; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:810 */ +.x-panel-header-light-framed { + font-size: 16px; + border: 2px solid #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:819 */ +.x-panel-header-light-framed .x-tool-tool-el { + color: #919191; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:836 */ +.x-panel-header-light-framed .x-tool-tool-el { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:842 */ +.x-panel-header-light-framed-horizontal { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:846 */ +.x-panel-header-light-framed-horizontal .x-panel-header-light-framed-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:854 */ +.x-panel-header-light-framed-horizontal.x-header-noborder { + padding: 12px 16px 10px 16px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:858 */ +.x-panel-header-light-framed-horizontal.x-header-noborder .x-panel-header-light-framed-tab-bar { + margin-top: -12px; + margin-bottom: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:866 */ +.x-panel-header-light-framed-vertical { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:870 */ +.x-panel-header-light-framed-vertical .x-panel-header-light-framed-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:878 */ +.x-panel-header-light-framed-vertical.x-header-noborder { + padding: 16px 12px 16px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:882 */ +.x-panel-header-light-framed-vertical.x-header-noborder .x-panel-header-light-framed-tab-bar { + margin-right: -12px; + margin-left: -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:916 */ +.x-panel-header-title-light-framed { + color: #606060; + font-size: 16px; + font-weight: 400; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + line-height: 20px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:929 */ +.x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:950 */ +.x-panel-header-title-light-framed > .x-title-text-light-framed { + text-transform: none; + padding: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:997 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1002 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1014 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1019 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1031 */ +.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed { + width: 16px; + height: 16px; + font-size: 16px; + color: #606060; + background-position: center center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1051 */ +.x-ie8 .x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed.x-title-glyph { + color: #606060; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1062 */ +.x-panel-body-light-framed { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 13px; + font-weight: 300; + font-family: 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif; + border-width: 1px; + border-style: solid; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-light-framed { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 0 0 0 0; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-light-framed-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-light-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-light-framed-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-0px-0px-0px-0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-light-framed-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-light-framed-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-light-framed-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-light-framed-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-light-framed-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-light-framed-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-light-framed-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-light-framed-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-light-framed-tr, +.x-panel-light-framed-br, +.x-panel-light-framed-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-light-framed-tl, +.x-panel-light-framed-bl, +.x-panel-light-framed-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-light-framed-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-light-framed-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-light-framed-tl, +.x-panel-light-framed-bl, +.x-panel-light-framed-tr, +.x-panel-light-framed-br, +.x-panel-light-framed-tc, +.x-panel-light-framed-bc, +.x-panel-light-framed-ml, +.x-panel-light-framed-mr { + background-image: url(images/panel/panel-light-framed-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-light-framed-ml, +.x-panel-light-framed-mr { + background-image: url(images/panel/panel-light-framed-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-light-framed-mc { + padding: 0px 0px 0px 0px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 0 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-top-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-top-frameInfo { + font-family: dh-2-2-0-2-2-2-0-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-top-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-top-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-top-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-top-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-top-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-top-tr, +.x-panel-header-light-framed-top-br, +.x-panel-header-light-framed-top-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-top-tl, +.x-panel-header-light-framed-top-bl, +.x-panel-header-light-framed-top-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-top-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-top-bc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-top-tl, +.x-panel-header-light-framed-top-bl, +.x-panel-header-light-framed-top-tr, +.x-panel-header-light-framed-top-br, +.x-panel-header-light-framed-top-tc, +.x-panel-header-light-framed-top-bc, +.x-panel-header-light-framed-top-ml, +.x-panel-header-light-framed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-top-ml, +.x-panel-header-light-framed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-top-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 0; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-right-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-right-frameInfo { + font-family: dh-2-2-2-0-2-2-2-0-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-right-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-right-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-right-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-right-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-right-ml { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-right-mr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-right-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-right-tr, +.x-panel-header-light-framed-right-br, +.x-panel-header-light-framed-right-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-right-tl, +.x-panel-header-light-framed-right-bl, +.x-panel-header-light-framed-right-ml { + padding-left: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-right-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-right-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-right-tl, +.x-panel-header-light-framed-right-bl, +.x-panel-header-light-framed-right-tr, +.x-panel-header-light-framed-right-br, +.x-panel-header-light-framed-right-tc, +.x-panel-header-light-framed-right-bc, +.x-panel-header-light-framed-right-ml, +.x-panel-header-light-framed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-right-ml, +.x-panel-header-light-framed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-right-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 0 2px 2px 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-bottom-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-bottom-frameInfo { + font-family: dh-0-2-2-2-0-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-bottom-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-bottom-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-bottom-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-bottom-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-bottom-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-bottom-tr, +.x-panel-header-light-framed-bottom-br, +.x-panel-header-light-framed-bottom-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-bottom-tl, +.x-panel-header-light-framed-bottom-bl, +.x-panel-header-light-framed-bottom-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-bottom-tc { + height: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-bottom-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-bottom-tl, +.x-panel-header-light-framed-bottom-bl, +.x-panel-header-light-framed-bottom-tr, +.x-panel-header-light-framed-bottom-br, +.x-panel-header-light-framed-bottom-tc, +.x-panel-header-light-framed-bottom-bc, +.x-panel-header-light-framed-bottom-ml, +.x-panel-header-light-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-bottom-ml, +.x-panel-header-light-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-bottom-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 0 2px 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-left-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-left-frameInfo { + font-family: dh-2-0-2-2-2-0-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-left-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-left-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-left-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-left-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-left-ml { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-left-mr { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-left-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-left-tr, +.x-panel-header-light-framed-left-br, +.x-panel-header-light-framed-left-mr { + padding-right: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-left-tl, +.x-panel-header-light-framed-left-bl, +.x-panel-header-light-framed-left-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-left-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-left-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-left-tl, +.x-panel-header-light-framed-left-bl, +.x-panel-header-light-framed-left-tr, +.x-panel-header-light-framed-left-br, +.x-panel-header-light-framed-left-tc, +.x-panel-header-light-framed-left-bc, +.x-panel-header-light-framed-left-ml, +.x-panel-header-light-framed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-left-ml, +.x-panel-header-light-framed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-left-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-collapsed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-collapsed-top-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-collapsed-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-collapsed-top-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-collapsed-top-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-collapsed-top-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-collapsed-top-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-collapsed-top-ml { + background-position: 0 top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-collapsed-top-mr { + background-position: right top; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-collapsed-top-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-collapsed-top-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-collapsed-top-tr, +.x-panel-header-light-framed-collapsed-top-br, +.x-panel-header-light-framed-collapsed-top-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-collapsed-top-tl, +.x-panel-header-light-framed-collapsed-top-bl, +.x-panel-header-light-framed-collapsed-top-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-collapsed-top-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-collapsed-top-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-collapsed-top-tl, +.x-panel-header-light-framed-collapsed-top-bl, +.x-panel-header-light-framed-collapsed-top-tr, +.x-panel-header-light-framed-collapsed-top-br, +.x-panel-header-light-framed-collapsed-top-tc, +.x-panel-header-light-framed-collapsed-top-bc, +.x-panel-header-light-framed-collapsed-top-ml, +.x-panel-header-light-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-top-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-collapsed-top-ml, +.x-panel-header-light-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-collapsed-top-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-collapsed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-collapsed-right-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-collapsed-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-collapsed-right-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-collapsed-right-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-collapsed-right-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-collapsed-right-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-collapsed-right-ml { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-collapsed-right-mr { + background-position: right 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-collapsed-right-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-collapsed-right-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-collapsed-right-tr, +.x-panel-header-light-framed-collapsed-right-br, +.x-panel-header-light-framed-collapsed-right-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-collapsed-right-tl, +.x-panel-header-light-framed-collapsed-right-bl, +.x-panel-header-light-framed-collapsed-right-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-collapsed-right-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-collapsed-right-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-collapsed-right-tl, +.x-panel-header-light-framed-collapsed-right-bl, +.x-panel-header-light-framed-collapsed-right-tr, +.x-panel-header-light-framed-collapsed-right-br, +.x-panel-header-light-framed-collapsed-right-tc, +.x-panel-header-light-framed-collapsed-right-bc, +.x-panel-header-light-framed-collapsed-right-ml, +.x-panel-header-light-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-right-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-collapsed-right-ml, +.x-panel-header-light-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-collapsed-right-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-collapsed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-collapsed-bottom-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-collapsed-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-collapsed-bottom-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-collapsed-bottom-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-collapsed-bottom-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-collapsed-bottom-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-collapsed-bottom-ml { + background-position: 0 bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-collapsed-bottom-mr { + background-position: right bottom; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-collapsed-bottom-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-collapsed-bottom-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-collapsed-bottom-tr, +.x-panel-header-light-framed-collapsed-bottom-br, +.x-panel-header-light-framed-collapsed-bottom-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-collapsed-bottom-tl, +.x-panel-header-light-framed-collapsed-bottom-bl, +.x-panel-header-light-framed-collapsed-bottom-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-collapsed-bottom-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-collapsed-bottom-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-collapsed-bottom-tl, +.x-panel-header-light-framed-collapsed-bottom-bl, +.x-panel-header-light-framed-collapsed-bottom-tr, +.x-panel-header-light-framed-collapsed-bottom-br, +.x-panel-header-light-framed-collapsed-bottom-tc, +.x-panel-header-light-framed-collapsed-bottom-bc, +.x-panel-header-light-framed-collapsed-bottom-ml, +.x-panel-header-light-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-collapsed-bottom-ml, +.x-panel-header-light-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-collapsed-bottom-mc { + padding: 10px 14px 10px 14px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:187 */ +.x-panel-header-light-framed-collapsed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:237 */ +.x-panel-header-light-framed-collapsed-left-mc { + background-color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:264 */ +.x-nbr .x-panel-header-light-framed-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:281 */ +.x-panel-header-light-framed-collapsed-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:347 */ +.x-panel-header-light-framed-collapsed-left-tl { + background-position: 0 -4px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:351 */ +.x-panel-header-light-framed-collapsed-left-tr { + background-position: right -6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:355 */ +.x-panel-header-light-framed-collapsed-left-bl { + background-position: 0 -8px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:359 */ +.x-panel-header-light-framed-collapsed-left-br { + background-position: right -10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:363 */ +.x-panel-header-light-framed-collapsed-left-ml { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:371 */ +.x-panel-header-light-framed-collapsed-left-mr { + background-position: left 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:379 */ +.x-panel-header-light-framed-collapsed-left-tc { + background-position: 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:383 */ +.x-panel-header-light-framed-collapsed-left-bc { + background-position: 0 -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:388 */ +.x-panel-header-light-framed-collapsed-left-tr, +.x-panel-header-light-framed-collapsed-left-br, +.x-panel-header-light-framed-collapsed-left-mr { + padding-right: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:394 */ +.x-panel-header-light-framed-collapsed-left-tl, +.x-panel-header-light-framed-collapsed-left-bl, +.x-panel-header-light-framed-collapsed-left-ml { + padding-left: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:400 */ +.x-panel-header-light-framed-collapsed-left-tc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:403 */ +.x-panel-header-light-framed-collapsed-left-bc { + height: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:407 */ +.x-panel-header-light-framed-collapsed-left-tl, +.x-panel-header-light-framed-collapsed-left-bl, +.x-panel-header-light-framed-collapsed-left-tr, +.x-panel-header-light-framed-collapsed-left-br, +.x-panel-header-light-framed-collapsed-left-tc, +.x-panel-header-light-framed-collapsed-left-bc, +.x-panel-header-light-framed-collapsed-left-ml, +.x-panel-header-light-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-left-corners.gif); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:453 */ +.x-panel-header-light-framed-collapsed-left-ml, +.x-panel-header-light-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-light-framed-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/frame.scss:464 */ +.x-panel-header-light-framed-collapsed-left-mc { + padding: 14px 10px 14px 10px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1188 */ +.x-panel .x-panel-header-light-framed-top { + border-bottom-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1192 */ +.x-panel .x-panel-header-light-framed-right { + border-left-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1196 */ +.x-panel .x-panel-header-light-framed-bottom { + border-top-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1200 */ +.x-panel .x-panel-header-light-framed-left { + border-right-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1206 */ +.x-nbr .x-panel-header-light-framed-collapsed-top { + border-bottom-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1210 */ +.x-nbr .x-panel-header-light-framed-collapsed-right { + border-left-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1214 */ +.x-nbr .x-panel-header-light-framed-collapsed-bottom { + border-top-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1218 */ +.x-nbr .x-panel-header-light-framed-collapsed-left { + border-right-width: 0 !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1336 */ +.x-panel-header-light-framed-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1346 */ +.x-panel-header-light-framed-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1358 */ +.x-panel-header-light-framed-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1368 */ +.x-panel-header-light-framed-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1381 */ +.x-keyboard-mode .x-panel-header-light-framed .x-tool-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:63 */ +.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus { + outline: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/css-outline.scss:39 */ +.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after { + position: absolute; + content: ' '; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neutral/sass/var/panel/Panel.scss:1429 */ +.x-panel-light-framed-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:2 */ +.x-panel-light-framed-outer-border-l { + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:6 */ +.x-panel-light-framed-outer-border-b { + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:10 */ +.x-panel-light-framed-outer-border-bl { + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:16 */ +.x-panel-light-framed-outer-border-r { + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:20 */ +.x-panel-light-framed-outer-border-rl { + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:26 */ +.x-panel-light-framed-outer-border-rb { + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:32 */ +.x-panel-light-framed-outer-border-rbl { + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:40 */ +.x-panel-light-framed-outer-border-t { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:44 */ +.x-panel-light-framed-outer-border-tl { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:50 */ +.x-panel-light-framed-outer-border-tb { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:56 */ +.x-panel-light-framed-outer-border-tbl { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:64 */ +.x-panel-light-framed-outer-border-tr { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:70 */ +.x-panel-light-framed-outer-border-trl { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-left-color: #d0d0d0 !important; + border-left-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:78 */ +.x-panel-light-framed-outer-border-trb { + border-top-color: #d0d0d0 !important; + border-top-width: 2px !important; + border-right-color: #d0d0d0 !important; + border-right-width: 2px !important; + border-bottom-color: #d0d0d0 !important; + border-bottom-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-base/sass/etc/mixins/border-management.scss:86 */ +.x-panel-light-framed-outer-border-trbl { + border-color: #d0d0d0 !important; + border-width: 2px !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/form/field/File.scss:3 */ +.x-form-file-wrap .x-form-trigger-wrap { + border: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/form/field/File.scss:7 */ +.x-form-file-wrap .x-form-trigger-wrap .x-form-text { + border: 1px solid; + border-color: #d0d0d0; + height: 32px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/form/field/File.scss:12 */ +.x-form-file-wrap .x-form-trigger-wrap .x-form-text.x-form-invalid-field { + border-color: #cf4c35; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/form/field/HtmlEditor.scss:1 */ +.x-html-editor-container { + border: 1px solid; + border-color: #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/grid/header/Container.scss:1 */ +.x-grid-header-ct { + border: 1px solid #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/grid/column/Column.scss:6 */ +.x-column-header-trigger { + background-color: #eaeff4; + border-left: 1px solid #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/grid/column/Column.scss:18 */ +.x-column-header-last { + border-right-width: 0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/grid/column/Column.scss:20 */ +.x-column-header-last .x-column-header-over .x-column-header-trigger { + border-right: 1px solid #d0d0d0; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:1 */ +.x-resizable-handle { + background-repeat: no-repeat; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:6 */ +.x-resizable-handle-east-over, +.x-resizable-handle-west-over { + background-position: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:11 */ +.x-resizable-handle-south-over, +.x-resizable-handle-north-over { + background-position: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:16 */ +.x-resizable-handle-southeast-over { + background-position: -2px -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:20 */ +.x-resizable-handle-northwest-over { + background-position: 2px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:24 */ +.x-resizable-handle-northeast-over { + background-position: -2px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:28 */ +.x-resizable-handle-southwest-over { + background-position: 2px -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:33 */ +.x-resizable-pinned .x-resizable-handle-east, +.x-resizable-pinned .x-resizable-handle-west { + background-position: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:38 */ +.x-resizable-pinned .x-resizable-handle-south, +.x-resizable-pinned .x-resizable-handle-north { + background-position: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:43 */ +.x-resizable-pinned .x-resizable-handle-southeast { + background-position: -2px -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:47 */ +.x-resizable-pinned .x-resizable-handle-northwest { + background-position: 2px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:51 */ +.x-resizable-pinned .x-resizable-handle-northeast { + background-position: -2px 2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-neptune/sass/src/resizer/Resizer.scss:55 */ +.x-resizable-pinned .x-resizable-handle-southwest { + background-position: 2px -2px; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_path.scss:5 */ +@font-face { + /* FONT PATH + * -------------------------- */ + /* FONT PATH + * -------------------------- */ + font-family: 'FontAwesome'; + src: url('font-awesome/fonts/fontawesome-webfont.eot?v=4.7.0'); + src: url('font-awesome/fonts/fontawesome-webfont.eot?#iefix&v=4.7.0') format('embedded-opentype'), url('font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0') format('woff2'), url('font-awesome/fonts/fontawesome-webfont.woff?v=4.7.0') format('woff'), url('font-awesome/fonts/fontawesome-webfont.ttf?v=4.7.0') format('truetype'), url('font-awesome/fonts/fontawesome-webfont.svg?v=4.7.0#fontawesomeregular') format('svg'); + font-weight: normal; + font-style: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_core.scss:4 */ +.fa { + display: inline-block; + font: normal normal normal 14px/1 FontAwesome; + font-size: inherit; + text-rendering: auto; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_larger.scss:5 */ +.fa-lg { + /* makes the font 33% larger relative to the icon container */ + font-size: 1.33333em; + line-height: 0.75em; + vertical-align: -15%; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_larger.scss:10 */ +.fa-2x { + font-size: 2em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_larger.scss:11 */ +.fa-3x { + font-size: 3em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_larger.scss:12 */ +.fa-4x { + font-size: 4em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_larger.scss:13 */ +.fa-5x { + font-size: 5em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_fixed-width.scss:3 */ +.fa-fw { + width: 1.28571em; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_list.scss:4 */ +.fa-ul { + padding-left: 0; + margin-left: 2.14286em; + list-style-type: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_list.scss:8 */ +.fa-ul > li { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_list.scss:10 */ +.fa-li { + position: absolute; + left: -2.14286em; + width: 2.14286em; + top: 0.14286em; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_list.scss:16 */ +.fa-li.fa-lg { + left: -1.85714em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_bordered-pulled.scss:4 */ +.fa-border { + padding: 0.2em 0.25em 0.15em; + border: solid 0.08em #eee; + border-radius: 0.1em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_bordered-pulled.scss:10 */ +.fa-pull-left { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_bordered-pulled.scss:11 */ +.fa-pull-right { + float: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_bordered-pulled.scss:14 */ +.fa.fa-pull-left { + margin-right: 0.3em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_bordered-pulled.scss:15 */ +.fa.fa-pull-right { + margin-left: 0.3em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_bordered-pulled.scss:19 */ +.pull-right { + /* Deprecated as of 4.4.0 */ + float: right; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_bordered-pulled.scss:20 */ +.pull-left { + float: left; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_bordered-pulled.scss:23 */ +.fa.pull-left { + margin-right: 0.3em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_bordered-pulled.scss:24 */ +.fa.pull-right { + margin-left: 0.3em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_animated.scss:4 */ +.fa-spin { + -webkit-animation: fa-spin 2s infinite linear; + animation: fa-spin 2s infinite linear; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_animated.scss:9 */ +.fa-pulse { + -webkit-animation: fa-spin 1s infinite steps(8); + animation: fa-spin 1s infinite steps(8); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_animated.scss:14 */ +@-webkit-keyframes fa-spin { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_animated.scss:15 */ + 0% { + -webkit-transform: rotate(0deg); + transform: rotate(0deg); + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_animated.scss:19 */ + 100% { + -webkit-transform: rotate(359deg); + transform: rotate(359deg); + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_animated.scss:25 */ +@keyframes fa-spin { + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_animated.scss:26 */ + 0% { + -webkit-transform: rotate(0deg); + transform: rotate(0deg); + } + /* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_animated.scss:30 */ + 100% { + -webkit-transform: rotate(359deg); + transform: rotate(359deg); + } +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_rotated-flipped.scss:4 */ +.fa-rotate-90 { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; + -webkit-transform: rotate(90deg); + -ms-transform: rotate(90deg); + transform: rotate(90deg); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_rotated-flipped.scss:5 */ +.fa-rotate-180 { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=2)"; + -webkit-transform: rotate(180deg); + -ms-transform: rotate(180deg); + transform: rotate(180deg); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_rotated-flipped.scss:6 */ +.fa-rotate-270 { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; + -webkit-transform: rotate(270deg); + -ms-transform: rotate(270deg); + transform: rotate(270deg); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_rotated-flipped.scss:8 */ +.fa-flip-horizontal { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=0, mirror=1)"; + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_rotated-flipped.scss:9 */ +.fa-flip-vertical { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1)"; + -webkit-transform: scale(1, -1); + -ms-transform: scale(1, -1); + transform: scale(1, -1); +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_rotated-flipped.scss:14 */ +:root .fa-rotate-90, +:root .fa-rotate-180, +:root .fa-rotate-270, +:root .fa-flip-horizontal, +:root .fa-flip-vertical { + filter: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_stacked.scss:4 */ +.fa-stack { + position: relative; + display: inline-block; + width: 2em; + height: 2em; + line-height: 2em; + vertical-align: middle; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_stacked.scss:12 */ +.fa-stack-1x, +.fa-stack-2x { + position: absolute; + left: 0; + width: 100%; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_stacked.scss:18 */ +.fa-stack-1x { + line-height: inherit; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_stacked.scss:19 */ +.fa-stack-2x { + font-size: 2em; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_stacked.scss:20 */ +.fa-inverse { + color: #fff; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:14 */ +.fa-glass:before { + content: "\f000" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:15 */ +.fa-music:before { + content: "\f001" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:16 */ +.fa-search:before { + content: "\f002" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:17 */ +.fa-envelope-o:before { + content: "\f003" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:18 */ +.fa-heart:before { + content: "\f004" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:19 */ +.fa-star:before { + content: "\f005" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:20 */ +.fa-star-o:before { + content: "\f006" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:21 */ +.fa-user:before { + content: "\f007" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:22 */ +.fa-film:before { + content: "\f008" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:23 */ +.fa-th-large:before { + content: "\f009" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:24 */ +.fa-th:before { + content: "\f00a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:25 */ +.fa-th-list:before { + content: "\f00b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:26 */ +.fa-check:before { + content: "\f00c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:27 */ +.fa-remove:before, +.fa-close:before, +.fa-times:before { + content: "\f00d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:30 */ +.fa-search-plus:before { + content: "\f00e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:31 */ +.fa-search-minus:before { + content: "\f010" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:32 */ +.fa-power-off:before { + content: "\f011" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:33 */ +.fa-signal:before { + content: "\f012" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:34 */ +.fa-gear:before, +.fa-cog:before { + content: "\f013" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:36 */ +.fa-trash-o:before { + content: "\f014" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:37 */ +.fa-home:before { + content: "\f015" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:38 */ +.fa-file-o:before { + content: "\f016" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:39 */ +.fa-clock-o:before { + content: "\f017" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:40 */ +.fa-road:before { + content: "\f018" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:41 */ +.fa-download:before { + content: "\f019" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:42 */ +.fa-arrow-circle-o-down:before { + content: "\f01a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:43 */ +.fa-arrow-circle-o-up:before { + content: "\f01b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:44 */ +.fa-inbox:before { + content: "\f01c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:45 */ +.fa-play-circle-o:before { + content: "\f01d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:46 */ +.fa-rotate-right:before, +.fa-repeat:before { + content: "\f01e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:48 */ +.fa-refresh:before { + content: "\f021" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:49 */ +.fa-list-alt:before { + content: "\f022" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:50 */ +.fa-lock:before { + content: "\f023" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:51 */ +.fa-flag:before { + content: "\f024" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:52 */ +.fa-headphones:before { + content: "\f025" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:53 */ +.fa-volume-off:before { + content: "\f026" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:54 */ +.fa-volume-down:before { + content: "\f027" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:55 */ +.fa-volume-up:before { + content: "\f028" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:56 */ +.fa-qrcode:before { + content: "\f029" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:57 */ +.fa-barcode:before { + content: "\f02a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:58 */ +.fa-tag:before { + content: "\f02b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:59 */ +.fa-tags:before { + content: "\f02c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:60 */ +.fa-book:before { + content: "\f02d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:61 */ +.fa-bookmark:before { + content: "\f02e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:62 */ +.fa-print:before { + content: "\f02f" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:63 */ +.fa-camera:before { + content: "\f030" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:64 */ +.fa-font:before { + content: "\f031" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:65 */ +.fa-bold:before { + content: "\f032" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:66 */ +.fa-italic:before { + content: "\f033" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:67 */ +.fa-text-height:before { + content: "\f034" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:68 */ +.fa-text-width:before { + content: "\f035" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:69 */ +.fa-align-left:before { + content: "\f036" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:70 */ +.fa-align-center:before { + content: "\f037" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:71 */ +.fa-align-right:before { + content: "\f038" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:72 */ +.fa-align-justify:before { + content: "\f039" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:73 */ +.fa-list:before { + content: "\f03a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:74 */ +.fa-dedent:before, +.fa-outdent:before { + content: "\f03b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:76 */ +.fa-indent:before { + content: "\f03c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:77 */ +.fa-video-camera:before { + content: "\f03d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:78 */ +.fa-photo:before, +.fa-image:before, +.fa-picture-o:before { + content: "\f03e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:81 */ +.fa-pencil:before { + content: "\f040" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:82 */ +.fa-map-marker:before { + content: "\f041" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:83 */ +.fa-adjust:before { + content: "\f042" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:84 */ +.fa-tint:before { + content: "\f043" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:85 */ +.fa-edit:before, +.fa-pencil-square-o:before { + content: "\f044" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:87 */ +.fa-share-square-o:before { + content: "\f045" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:88 */ +.fa-check-square-o:before { + content: "\f046" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:89 */ +.fa-arrows:before { + content: "\f047" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:90 */ +.fa-step-backward:before { + content: "\f048" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:91 */ +.fa-fast-backward:before { + content: "\f049" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:92 */ +.fa-backward:before { + content: "\f04a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:93 */ +.fa-play:before { + content: "\f04b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:94 */ +.fa-pause:before { + content: "\f04c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:95 */ +.fa-stop:before { + content: "\f04d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:96 */ +.fa-forward:before { + content: "\f04e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:97 */ +.fa-fast-forward:before { + content: "\f050" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:98 */ +.fa-step-forward:before { + content: "\f051" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:99 */ +.fa-eject:before { + content: "\f052" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:100 */ +.fa-chevron-left:before { + content: "\f053" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:101 */ +.fa-chevron-right:before { + content: "\f054" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:102 */ +.fa-plus-circle:before { + content: "\f055" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:103 */ +.fa-minus-circle:before { + content: "\f056" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:104 */ +.fa-times-circle:before { + content: "\f057" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:105 */ +.fa-check-circle:before { + content: "\f058" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:106 */ +.fa-question-circle:before { + content: "\f059" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:107 */ +.fa-info-circle:before { + content: "\f05a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:108 */ +.fa-crosshairs:before { + content: "\f05b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:109 */ +.fa-times-circle-o:before { + content: "\f05c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:110 */ +.fa-check-circle-o:before { + content: "\f05d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:111 */ +.fa-ban:before { + content: "\f05e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:112 */ +.fa-arrow-left:before { + content: "\f060" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:113 */ +.fa-arrow-right:before { + content: "\f061" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:114 */ +.fa-arrow-up:before { + content: "\f062" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:115 */ +.fa-arrow-down:before { + content: "\f063" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:116 */ +.fa-mail-forward:before, +.fa-share:before { + content: "\f064" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:118 */ +.fa-expand:before { + content: "\f065" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:119 */ +.fa-compress:before { + content: "\f066" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:120 */ +.fa-plus:before { + content: "\f067" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:121 */ +.fa-minus:before { + content: "\f068" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:122 */ +.fa-asterisk:before { + content: "\f069" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:123 */ +.fa-exclamation-circle:before { + content: "\f06a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:124 */ +.fa-gift:before { + content: "\f06b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:125 */ +.fa-leaf:before { + content: "\f06c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:126 */ +.fa-fire:before { + content: "\f06d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:127 */ +.fa-eye:before { + content: "\f06e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:128 */ +.fa-eye-slash:before { + content: "\f070" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:129 */ +.fa-warning:before, +.fa-exclamation-triangle:before { + content: "\f071" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:131 */ +.fa-plane:before { + content: "\f072" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:132 */ +.fa-calendar:before { + content: "\f073" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:133 */ +.fa-random:before { + content: "\f074" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:134 */ +.fa-comment:before { + content: "\f075" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:135 */ +.fa-magnet:before { + content: "\f076" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:136 */ +.fa-chevron-up:before { + content: "\f077" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:137 */ +.fa-chevron-down:before { + content: "\f078" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:138 */ +.fa-retweet:before { + content: "\f079" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:139 */ +.fa-shopping-cart:before { + content: "\f07a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:140 */ +.fa-folder:before { + content: "\f07b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:141 */ +.fa-folder-open:before { + content: "\f07c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:142 */ +.fa-arrows-v:before { + content: "\f07d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:143 */ +.fa-arrows-h:before { + content: "\f07e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:144 */ +.fa-bar-chart-o:before, +.fa-bar-chart:before { + content: "\f080" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:146 */ +.fa-twitter-square:before { + content: "\f081" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:147 */ +.fa-facebook-square:before { + content: "\f082" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:148 */ +.fa-camera-retro:before { + content: "\f083" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:149 */ +.fa-key:before { + content: "\f084" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:150 */ +.fa-gears:before, +.fa-cogs:before { + content: "\f085" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:152 */ +.fa-comments:before { + content: "\f086" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:153 */ +.fa-thumbs-o-up:before { + content: "\f087" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:154 */ +.fa-thumbs-o-down:before { + content: "\f088" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:155 */ +.fa-star-half:before { + content: "\f089" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:156 */ +.fa-heart-o:before { + content: "\f08a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:157 */ +.fa-sign-out:before { + content: "\f08b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:158 */ +.fa-linkedin-square:before { + content: "\f08c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:159 */ +.fa-thumb-tack:before { + content: "\f08d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:160 */ +.fa-external-link:before { + content: "\f08e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:161 */ +.fa-sign-in:before { + content: "\f090" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:162 */ +.fa-trophy:before { + content: "\f091" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:163 */ +.fa-github-square:before { + content: "\f092" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:164 */ +.fa-upload:before { + content: "\f093" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:165 */ +.fa-lemon-o:before { + content: "\f094" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:166 */ +.fa-phone:before { + content: "\f095" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:167 */ +.fa-square-o:before { + content: "\f096" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:168 */ +.fa-bookmark-o:before { + content: "\f097" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:169 */ +.fa-phone-square:before { + content: "\f098" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:170 */ +.fa-twitter:before { + content: "\f099" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:171 */ +.fa-facebook-f:before, +.fa-facebook:before { + content: "\f09a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:173 */ +.fa-github:before { + content: "\f09b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:174 */ +.fa-unlock:before { + content: "\f09c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:175 */ +.fa-credit-card:before { + content: "\f09d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:176 */ +.fa-feed:before, +.fa-rss:before { + content: "\f09e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:178 */ +.fa-hdd-o:before { + content: "\f0a0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:179 */ +.fa-bullhorn:before { + content: "\f0a1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:180 */ +.fa-bell:before { + content: "\f0f3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:181 */ +.fa-certificate:before { + content: "\f0a3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:182 */ +.fa-hand-o-right:before { + content: "\f0a4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:183 */ +.fa-hand-o-left:before { + content: "\f0a5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:184 */ +.fa-hand-o-up:before { + content: "\f0a6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:185 */ +.fa-hand-o-down:before { + content: "\f0a7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:186 */ +.fa-arrow-circle-left:before { + content: "\f0a8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:187 */ +.fa-arrow-circle-right:before { + content: "\f0a9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:188 */ +.fa-arrow-circle-up:before { + content: "\f0aa" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:189 */ +.fa-arrow-circle-down:before { + content: "\f0ab" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:190 */ +.fa-globe:before { + content: "\f0ac" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:191 */ +.fa-wrench:before { + content: "\f0ad" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:192 */ +.fa-tasks:before { + content: "\f0ae" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:193 */ +.fa-filter:before { + content: "\f0b0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:194 */ +.fa-briefcase:before { + content: "\f0b1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:195 */ +.fa-arrows-alt:before { + content: "\f0b2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:196 */ +.fa-group:before, +.fa-users:before { + content: "\f0c0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:198 */ +.fa-chain:before, +.fa-link:before { + content: "\f0c1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:200 */ +.fa-cloud:before { + content: "\f0c2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:201 */ +.fa-flask:before { + content: "\f0c3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:202 */ +.fa-cut:before, +.fa-scissors:before { + content: "\f0c4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:204 */ +.fa-copy:before, +.fa-files-o:before { + content: "\f0c5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:206 */ +.fa-paperclip:before { + content: "\f0c6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:207 */ +.fa-save:before, +.fa-floppy-o:before { + content: "\f0c7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:209 */ +.fa-square:before { + content: "\f0c8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:210 */ +.fa-navicon:before, +.fa-reorder:before, +.fa-bars:before { + content: "\f0c9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:213 */ +.fa-list-ul:before { + content: "\f0ca" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:214 */ +.fa-list-ol:before { + content: "\f0cb" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:215 */ +.fa-strikethrough:before { + content: "\f0cc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:216 */ +.fa-underline:before { + content: "\f0cd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:217 */ +.fa-table:before { + content: "\f0ce" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:218 */ +.fa-magic:before { + content: "\f0d0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:219 */ +.fa-truck:before { + content: "\f0d1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:220 */ +.fa-pinterest:before { + content: "\f0d2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:221 */ +.fa-pinterest-square:before { + content: "\f0d3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:222 */ +.fa-google-plus-square:before { + content: "\f0d4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:223 */ +.fa-google-plus:before { + content: "\f0d5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:224 */ +.fa-money:before { + content: "\f0d6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:225 */ +.fa-caret-down:before { + content: "\f0d7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:226 */ +.fa-caret-up:before { + content: "\f0d8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:227 */ +.fa-caret-left:before { + content: "\f0d9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:228 */ +.fa-caret-right:before { + content: "\f0da" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:229 */ +.fa-columns:before { + content: "\f0db" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:230 */ +.fa-unsorted:before, +.fa-sort:before { + content: "\f0dc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:232 */ +.fa-sort-down:before, +.fa-sort-desc:before { + content: "\f0dd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:234 */ +.fa-sort-up:before, +.fa-sort-asc:before { + content: "\f0de" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:236 */ +.fa-envelope:before { + content: "\f0e0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:237 */ +.fa-linkedin:before { + content: "\f0e1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:238 */ +.fa-rotate-left:before, +.fa-undo:before { + content: "\f0e2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:240 */ +.fa-legal:before, +.fa-gavel:before { + content: "\f0e3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:242 */ +.fa-dashboard:before, +.fa-tachometer:before { + content: "\f0e4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:244 */ +.fa-comment-o:before { + content: "\f0e5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:245 */ +.fa-comments-o:before { + content: "\f0e6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:246 */ +.fa-flash:before, +.fa-bolt:before { + content: "\f0e7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:248 */ +.fa-sitemap:before { + content: "\f0e8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:249 */ +.fa-umbrella:before { + content: "\f0e9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:250 */ +.fa-paste:before, +.fa-clipboard:before { + content: "\f0ea" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:252 */ +.fa-lightbulb-o:before { + content: "\f0eb" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:253 */ +.fa-exchange:before { + content: "\f0ec" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:254 */ +.fa-cloud-download:before { + content: "\f0ed" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:255 */ +.fa-cloud-upload:before { + content: "\f0ee" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:256 */ +.fa-user-md:before { + content: "\f0f0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:257 */ +.fa-stethoscope:before { + content: "\f0f1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:258 */ +.fa-suitcase:before { + content: "\f0f2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:259 */ +.fa-bell-o:before { + content: "\f0a2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:260 */ +.fa-coffee:before { + content: "\f0f4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:261 */ +.fa-cutlery:before { + content: "\f0f5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:262 */ +.fa-file-text-o:before { + content: "\f0f6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:263 */ +.fa-building-o:before { + content: "\f0f7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:264 */ +.fa-hospital-o:before { + content: "\f0f8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:265 */ +.fa-ambulance:before { + content: "\f0f9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:266 */ +.fa-medkit:before { + content: "\f0fa" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:267 */ +.fa-fighter-jet:before { + content: "\f0fb" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:268 */ +.fa-beer:before { + content: "\f0fc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:269 */ +.fa-h-square:before { + content: "\f0fd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:270 */ +.fa-plus-square:before { + content: "\f0fe" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:271 */ +.fa-angle-double-left:before { + content: "\f100" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:272 */ +.fa-angle-double-right:before { + content: "\f101" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:273 */ +.fa-angle-double-up:before { + content: "\f102" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:274 */ +.fa-angle-double-down:before { + content: "\f103" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:275 */ +.fa-angle-left:before { + content: "\f104" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:276 */ +.fa-angle-right:before { + content: "\f105" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:277 */ +.fa-angle-up:before { + content: "\f106" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:278 */ +.fa-angle-down:before { + content: "\f107" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:279 */ +.fa-desktop:before { + content: "\f108" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:280 */ +.fa-laptop:before { + content: "\f109" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:281 */ +.fa-tablet:before { + content: "\f10a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:282 */ +.fa-mobile-phone:before, +.fa-mobile:before { + content: "\f10b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:284 */ +.fa-circle-o:before { + content: "\f10c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:285 */ +.fa-quote-left:before { + content: "\f10d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:286 */ +.fa-quote-right:before { + content: "\f10e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:287 */ +.fa-spinner:before { + content: "\f110" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:288 */ +.fa-circle:before { + content: "\f111" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:289 */ +.fa-mail-reply:before, +.fa-reply:before { + content: "\f112" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:291 */ +.fa-github-alt:before { + content: "\f113" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:292 */ +.fa-folder-o:before { + content: "\f114" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:293 */ +.fa-folder-open-o:before { + content: "\f115" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:294 */ +.fa-smile-o:before { + content: "\f118" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:295 */ +.fa-frown-o:before { + content: "\f119" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:296 */ +.fa-meh-o:before { + content: "\f11a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:297 */ +.fa-gamepad:before { + content: "\f11b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:298 */ +.fa-keyboard-o:before { + content: "\f11c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:299 */ +.fa-flag-o:before { + content: "\f11d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:300 */ +.fa-flag-checkered:before { + content: "\f11e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:301 */ +.fa-terminal:before { + content: "\f120" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:302 */ +.fa-code:before { + content: "\f121" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:303 */ +.fa-mail-reply-all:before, +.fa-reply-all:before { + content: "\f122" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:305 */ +.fa-star-half-empty:before, +.fa-star-half-full:before, +.fa-star-half-o:before { + content: "\f123" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:308 */ +.fa-location-arrow:before { + content: "\f124" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:309 */ +.fa-crop:before { + content: "\f125" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:310 */ +.fa-code-fork:before { + content: "\f126" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:311 */ +.fa-unlink:before, +.fa-chain-broken:before { + content: "\f127" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:313 */ +.fa-question:before { + content: "\f128" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:314 */ +.fa-info:before { + content: "\f129" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:315 */ +.fa-exclamation:before { + content: "\f12a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:316 */ +.fa-superscript:before { + content: "\f12b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:317 */ +.fa-subscript:before { + content: "\f12c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:318 */ +.fa-eraser:before { + content: "\f12d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:319 */ +.fa-puzzle-piece:before { + content: "\f12e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:320 */ +.fa-microphone:before { + content: "\f130" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:321 */ +.fa-microphone-slash:before { + content: "\f131" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:322 */ +.fa-shield:before { + content: "\f132" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:323 */ +.fa-calendar-o:before { + content: "\f133" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:324 */ +.fa-fire-extinguisher:before { + content: "\f134" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:325 */ +.fa-rocket:before { + content: "\f135" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:326 */ +.fa-maxcdn:before { + content: "\f136" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:327 */ +.fa-chevron-circle-left:before { + content: "\f137" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:328 */ +.fa-chevron-circle-right:before { + content: "\f138" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:329 */ +.fa-chevron-circle-up:before { + content: "\f139" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:330 */ +.fa-chevron-circle-down:before { + content: "\f13a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:331 */ +.fa-html5:before { + content: "\f13b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:332 */ +.fa-css3:before { + content: "\f13c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:333 */ +.fa-anchor:before { + content: "\f13d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:334 */ +.fa-unlock-alt:before { + content: "\f13e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:335 */ +.fa-bullseye:before { + content: "\f140" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:336 */ +.fa-ellipsis-h:before { + content: "\f141" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:337 */ +.fa-ellipsis-v:before { + content: "\f142" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:338 */ +.fa-rss-square:before { + content: "\f143" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:339 */ +.fa-play-circle:before { + content: "\f144" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:340 */ +.fa-ticket:before { + content: "\f145" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:341 */ +.fa-minus-square:before { + content: "\f146" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:342 */ +.fa-minus-square-o:before { + content: "\f147" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:343 */ +.fa-level-up:before { + content: "\f148" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:344 */ +.fa-level-down:before { + content: "\f149" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:345 */ +.fa-check-square:before { + content: "\f14a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:346 */ +.fa-pencil-square:before { + content: "\f14b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:347 */ +.fa-external-link-square:before { + content: "\f14c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:348 */ +.fa-share-square:before { + content: "\f14d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:349 */ +.fa-compass:before { + content: "\f14e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:350 */ +.fa-toggle-down:before, +.fa-caret-square-o-down:before { + content: "\f150" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:352 */ +.fa-toggle-up:before, +.fa-caret-square-o-up:before { + content: "\f151" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:354 */ +.fa-toggle-right:before, +.fa-caret-square-o-right:before { + content: "\f152" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:356 */ +.fa-euro:before, +.fa-eur:before { + content: "\f153" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:358 */ +.fa-gbp:before { + content: "\f154" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:359 */ +.fa-dollar:before, +.fa-usd:before { + content: "\f155" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:361 */ +.fa-rupee:before, +.fa-inr:before { + content: "\f156" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:363 */ +.fa-cny:before, +.fa-rmb:before, +.fa-yen:before, +.fa-jpy:before { + content: "\f157" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:367 */ +.fa-ruble:before, +.fa-rouble:before, +.fa-rub:before { + content: "\f158" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:370 */ +.fa-won:before, +.fa-krw:before { + content: "\f159" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:372 */ +.fa-bitcoin:before, +.fa-btc:before { + content: "\f15a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:374 */ +.fa-file:before { + content: "\f15b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:375 */ +.fa-file-text:before { + content: "\f15c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:376 */ +.fa-sort-alpha-asc:before { + content: "\f15d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:377 */ +.fa-sort-alpha-desc:before { + content: "\f15e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:378 */ +.fa-sort-amount-asc:before { + content: "\f160" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:379 */ +.fa-sort-amount-desc:before { + content: "\f161" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:380 */ +.fa-sort-numeric-asc:before { + content: "\f162" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:381 */ +.fa-sort-numeric-desc:before { + content: "\f163" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:382 */ +.fa-thumbs-up:before { + content: "\f164" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:383 */ +.fa-thumbs-down:before { + content: "\f165" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:384 */ +.fa-youtube-square:before { + content: "\f166" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:385 */ +.fa-youtube:before { + content: "\f167" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:386 */ +.fa-xing:before { + content: "\f168" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:387 */ +.fa-xing-square:before { + content: "\f169" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:388 */ +.fa-youtube-play:before { + content: "\f16a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:389 */ +.fa-dropbox:before { + content: "\f16b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:390 */ +.fa-stack-overflow:before { + content: "\f16c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:391 */ +.fa-instagram:before { + content: "\f16d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:392 */ +.fa-flickr:before { + content: "\f16e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:393 */ +.fa-adn:before { + content: "\f170" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:394 */ +.fa-bitbucket:before { + content: "\f171" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:395 */ +.fa-bitbucket-square:before { + content: "\f172" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:396 */ +.fa-tumblr:before { + content: "\f173" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:397 */ +.fa-tumblr-square:before { + content: "\f174" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:398 */ +.fa-long-arrow-down:before { + content: "\f175" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:399 */ +.fa-long-arrow-up:before { + content: "\f176" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:400 */ +.fa-long-arrow-left:before { + content: "\f177" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:401 */ +.fa-long-arrow-right:before { + content: "\f178" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:402 */ +.fa-apple:before { + content: "\f179" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:403 */ +.fa-windows:before { + content: "\f17a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:404 */ +.fa-android:before { + content: "\f17b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:405 */ +.fa-linux:before { + content: "\f17c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:406 */ +.fa-dribbble:before { + content: "\f17d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:407 */ +.fa-skype:before { + content: "\f17e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:408 */ +.fa-foursquare:before { + content: "\f180" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:409 */ +.fa-trello:before { + content: "\f181" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:410 */ +.fa-female:before { + content: "\f182" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:411 */ +.fa-male:before { + content: "\f183" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:412 */ +.fa-gittip:before, +.fa-gratipay:before { + content: "\f184" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:414 */ +.fa-sun-o:before { + content: "\f185" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:415 */ +.fa-moon-o:before { + content: "\f186" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:416 */ +.fa-archive:before { + content: "\f187" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:417 */ +.fa-bug:before { + content: "\f188" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:418 */ +.fa-vk:before { + content: "\f189" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:419 */ +.fa-weibo:before { + content: "\f18a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:420 */ +.fa-renren:before { + content: "\f18b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:421 */ +.fa-pagelines:before { + content: "\f18c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:422 */ +.fa-stack-exchange:before { + content: "\f18d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:423 */ +.fa-arrow-circle-o-right:before { + content: "\f18e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:424 */ +.fa-arrow-circle-o-left:before { + content: "\f190" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:425 */ +.fa-toggle-left:before, +.fa-caret-square-o-left:before { + content: "\f191" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:427 */ +.fa-dot-circle-o:before { + content: "\f192" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:428 */ +.fa-wheelchair:before { + content: "\f193" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:429 */ +.fa-vimeo-square:before { + content: "\f194" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:430 */ +.fa-turkish-lira:before, +.fa-try:before { + content: "\f195" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:432 */ +.fa-plus-square-o:before { + content: "\f196" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:433 */ +.fa-space-shuttle:before { + content: "\f197" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:434 */ +.fa-slack:before { + content: "\f198" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:435 */ +.fa-envelope-square:before { + content: "\f199" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:436 */ +.fa-wordpress:before { + content: "\f19a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:437 */ +.fa-openid:before { + content: "\f19b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:438 */ +.fa-institution:before, +.fa-bank:before, +.fa-university:before { + content: "\f19c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:441 */ +.fa-mortar-board:before, +.fa-graduation-cap:before { + content: "\f19d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:443 */ +.fa-yahoo:before { + content: "\f19e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:444 */ +.fa-google:before { + content: "\f1a0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:445 */ +.fa-reddit:before { + content: "\f1a1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:446 */ +.fa-reddit-square:before { + content: "\f1a2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:447 */ +.fa-stumbleupon-circle:before { + content: "\f1a3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:448 */ +.fa-stumbleupon:before { + content: "\f1a4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:449 */ +.fa-delicious:before { + content: "\f1a5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:450 */ +.fa-digg:before { + content: "\f1a6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:451 */ +.fa-pied-piper-pp:before { + content: "\f1a7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:452 */ +.fa-pied-piper-alt:before { + content: "\f1a8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:453 */ +.fa-drupal:before { + content: "\f1a9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:454 */ +.fa-joomla:before { + content: "\f1aa" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:455 */ +.fa-language:before { + content: "\f1ab" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:456 */ +.fa-fax:before { + content: "\f1ac" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:457 */ +.fa-building:before { + content: "\f1ad" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:458 */ +.fa-child:before { + content: "\f1ae" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:459 */ +.fa-paw:before { + content: "\f1b0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:460 */ +.fa-spoon:before { + content: "\f1b1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:461 */ +.fa-cube:before { + content: "\f1b2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:462 */ +.fa-cubes:before { + content: "\f1b3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:463 */ +.fa-behance:before { + content: "\f1b4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:464 */ +.fa-behance-square:before { + content: "\f1b5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:465 */ +.fa-steam:before { + content: "\f1b6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:466 */ +.fa-steam-square:before { + content: "\f1b7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:467 */ +.fa-recycle:before { + content: "\f1b8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:468 */ +.fa-automobile:before, +.fa-car:before { + content: "\f1b9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:470 */ +.fa-cab:before, +.fa-taxi:before { + content: "\f1ba" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:472 */ +.fa-tree:before { + content: "\f1bb" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:473 */ +.fa-spotify:before { + content: "\f1bc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:474 */ +.fa-deviantart:before { + content: "\f1bd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:475 */ +.fa-soundcloud:before { + content: "\f1be" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:476 */ +.fa-database:before { + content: "\f1c0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:477 */ +.fa-file-pdf-o:before { + content: "\f1c1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:478 */ +.fa-file-word-o:before { + content: "\f1c2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:479 */ +.fa-file-excel-o:before { + content: "\f1c3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:480 */ +.fa-file-powerpoint-o:before { + content: "\f1c4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:481 */ +.fa-file-photo-o:before, +.fa-file-picture-o:before, +.fa-file-image-o:before { + content: "\f1c5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:484 */ +.fa-file-zip-o:before, +.fa-file-archive-o:before { + content: "\f1c6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:486 */ +.fa-file-sound-o:before, +.fa-file-audio-o:before { + content: "\f1c7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:488 */ +.fa-file-movie-o:before, +.fa-file-video-o:before { + content: "\f1c8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:490 */ +.fa-file-code-o:before { + content: "\f1c9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:491 */ +.fa-vine:before { + content: "\f1ca" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:492 */ +.fa-codepen:before { + content: "\f1cb" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:493 */ +.fa-jsfiddle:before { + content: "\f1cc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:494 */ +.fa-life-bouy:before, +.fa-life-buoy:before, +.fa-life-saver:before, +.fa-support:before, +.fa-life-ring:before { + content: "\f1cd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:499 */ +.fa-circle-o-notch:before { + content: "\f1ce" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:500 */ +.fa-ra:before, +.fa-resistance:before, +.fa-rebel:before { + content: "\f1d0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:503 */ +.fa-ge:before, +.fa-empire:before { + content: "\f1d1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:505 */ +.fa-git-square:before { + content: "\f1d2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:506 */ +.fa-git:before { + content: "\f1d3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:507 */ +.fa-y-combinator-square:before, +.fa-yc-square:before, +.fa-hacker-news:before { + content: "\f1d4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:510 */ +.fa-tencent-weibo:before { + content: "\f1d5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:511 */ +.fa-qq:before { + content: "\f1d6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:512 */ +.fa-wechat:before, +.fa-weixin:before { + content: "\f1d7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:514 */ +.fa-send:before, +.fa-paper-plane:before { + content: "\f1d8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:516 */ +.fa-send-o:before, +.fa-paper-plane-o:before { + content: "\f1d9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:518 */ +.fa-history:before { + content: "\f1da" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:519 */ +.fa-circle-thin:before { + content: "\f1db" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:520 */ +.fa-header:before { + content: "\f1dc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:521 */ +.fa-paragraph:before { + content: "\f1dd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:522 */ +.fa-sliders:before { + content: "\f1de" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:523 */ +.fa-share-alt:before { + content: "\f1e0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:524 */ +.fa-share-alt-square:before { + content: "\f1e1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:525 */ +.fa-bomb:before { + content: "\f1e2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:526 */ +.fa-soccer-ball-o:before, +.fa-futbol-o:before { + content: "\f1e3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:528 */ +.fa-tty:before { + content: "\f1e4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:529 */ +.fa-binoculars:before { + content: "\f1e5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:530 */ +.fa-plug:before { + content: "\f1e6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:531 */ +.fa-slideshare:before { + content: "\f1e7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:532 */ +.fa-twitch:before { + content: "\f1e8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:533 */ +.fa-yelp:before { + content: "\f1e9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:534 */ +.fa-newspaper-o:before { + content: "\f1ea" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:535 */ +.fa-wifi:before { + content: "\f1eb" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:536 */ +.fa-calculator:before { + content: "\f1ec" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:537 */ +.fa-paypal:before { + content: "\f1ed" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:538 */ +.fa-google-wallet:before { + content: "\f1ee" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:539 */ +.fa-cc-visa:before { + content: "\f1f0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:540 */ +.fa-cc-mastercard:before { + content: "\f1f1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:541 */ +.fa-cc-discover:before { + content: "\f1f2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:542 */ +.fa-cc-amex:before { + content: "\f1f3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:543 */ +.fa-cc-paypal:before { + content: "\f1f4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:544 */ +.fa-cc-stripe:before { + content: "\f1f5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:545 */ +.fa-bell-slash:before { + content: "\f1f6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:546 */ +.fa-bell-slash-o:before { + content: "\f1f7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:547 */ +.fa-trash:before { + content: "\f1f8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:548 */ +.fa-copyright:before { + content: "\f1f9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:549 */ +.fa-at:before { + content: "\f1fa" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:550 */ +.fa-eyedropper:before { + content: "\f1fb" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:551 */ +.fa-paint-brush:before { + content: "\f1fc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:552 */ +.fa-birthday-cake:before { + content: "\f1fd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:553 */ +.fa-area-chart:before { + content: "\f1fe" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:554 */ +.fa-pie-chart:before { + content: "\f200" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:555 */ +.fa-line-chart:before { + content: "\f201" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:556 */ +.fa-lastfm:before { + content: "\f202" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:557 */ +.fa-lastfm-square:before { + content: "\f203" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:558 */ +.fa-toggle-off:before { + content: "\f204" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:559 */ +.fa-toggle-on:before { + content: "\f205" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:560 */ +.fa-bicycle:before { + content: "\f206" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:561 */ +.fa-bus:before { + content: "\f207" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:562 */ +.fa-ioxhost:before { + content: "\f208" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:563 */ +.fa-angellist:before { + content: "\f209" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:564 */ +.fa-cc:before { + content: "\f20a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:565 */ +.fa-shekel:before, +.fa-sheqel:before, +.fa-ils:before { + content: "\f20b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:568 */ +.fa-meanpath:before { + content: "\f20c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:569 */ +.fa-buysellads:before { + content: "\f20d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:570 */ +.fa-connectdevelop:before { + content: "\f20e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:571 */ +.fa-dashcube:before { + content: "\f210" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:572 */ +.fa-forumbee:before { + content: "\f211" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:573 */ +.fa-leanpub:before { + content: "\f212" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:574 */ +.fa-sellsy:before { + content: "\f213" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:575 */ +.fa-shirtsinbulk:before { + content: "\f214" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:576 */ +.fa-simplybuilt:before { + content: "\f215" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:577 */ +.fa-skyatlas:before { + content: "\f216" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:578 */ +.fa-cart-plus:before { + content: "\f217" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:579 */ +.fa-cart-arrow-down:before { + content: "\f218" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:580 */ +.fa-diamond:before { + content: "\f219" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:581 */ +.fa-ship:before { + content: "\f21a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:582 */ +.fa-user-secret:before { + content: "\f21b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:583 */ +.fa-motorcycle:before { + content: "\f21c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:584 */ +.fa-street-view:before { + content: "\f21d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:585 */ +.fa-heartbeat:before { + content: "\f21e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:586 */ +.fa-venus:before { + content: "\f221" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:587 */ +.fa-mars:before { + content: "\f222" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:588 */ +.fa-mercury:before { + content: "\f223" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:589 */ +.fa-intersex:before, +.fa-transgender:before { + content: "\f224" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:591 */ +.fa-transgender-alt:before { + content: "\f225" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:592 */ +.fa-venus-double:before { + content: "\f226" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:593 */ +.fa-mars-double:before { + content: "\f227" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:594 */ +.fa-venus-mars:before { + content: "\f228" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:595 */ +.fa-mars-stroke:before { + content: "\f229" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:596 */ +.fa-mars-stroke-v:before { + content: "\f22a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:597 */ +.fa-mars-stroke-h:before { + content: "\f22b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:598 */ +.fa-neuter:before { + content: "\f22c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:599 */ +.fa-genderless:before { + content: "\f22d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:600 */ +.fa-facebook-official:before { + content: "\f230" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:601 */ +.fa-pinterest-p:before { + content: "\f231" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:602 */ +.fa-whatsapp:before { + content: "\f232" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:603 */ +.fa-server:before { + content: "\f233" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:604 */ +.fa-user-plus:before { + content: "\f234" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:605 */ +.fa-user-times:before { + content: "\f235" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:606 */ +.fa-hotel:before, +.fa-bed:before { + content: "\f236" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:608 */ +.fa-viacoin:before { + content: "\f237" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:609 */ +.fa-train:before { + content: "\f238" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:610 */ +.fa-subway:before { + content: "\f239" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:611 */ +.fa-medium:before { + content: "\f23a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:612 */ +.fa-yc:before, +.fa-y-combinator:before { + content: "\f23b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:614 */ +.fa-optin-monster:before { + content: "\f23c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:615 */ +.fa-opencart:before { + content: "\f23d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:616 */ +.fa-expeditedssl:before { + content: "\f23e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:617 */ +.fa-battery-4:before, +.fa-battery:before, +.fa-battery-full:before { + content: "\f240" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:620 */ +.fa-battery-3:before, +.fa-battery-three-quarters:before { + content: "\f241" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:622 */ +.fa-battery-2:before, +.fa-battery-half:before { + content: "\f242" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:624 */ +.fa-battery-1:before, +.fa-battery-quarter:before { + content: "\f243" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:626 */ +.fa-battery-0:before, +.fa-battery-empty:before { + content: "\f244" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:628 */ +.fa-mouse-pointer:before { + content: "\f245" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:629 */ +.fa-i-cursor:before { + content: "\f246" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:630 */ +.fa-object-group:before { + content: "\f247" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:631 */ +.fa-object-ungroup:before { + content: "\f248" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:632 */ +.fa-sticky-note:before { + content: "\f249" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:633 */ +.fa-sticky-note-o:before { + content: "\f24a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:634 */ +.fa-cc-jcb:before { + content: "\f24b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:635 */ +.fa-cc-diners-club:before { + content: "\f24c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:636 */ +.fa-clone:before { + content: "\f24d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:637 */ +.fa-balance-scale:before { + content: "\f24e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:638 */ +.fa-hourglass-o:before { + content: "\f250" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:639 */ +.fa-hourglass-1:before, +.fa-hourglass-start:before { + content: "\f251" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:641 */ +.fa-hourglass-2:before, +.fa-hourglass-half:before { + content: "\f252" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:643 */ +.fa-hourglass-3:before, +.fa-hourglass-end:before { + content: "\f253" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:645 */ +.fa-hourglass:before { + content: "\f254" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:646 */ +.fa-hand-grab-o:before, +.fa-hand-rock-o:before { + content: "\f255" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:648 */ +.fa-hand-stop-o:before, +.fa-hand-paper-o:before { + content: "\f256" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:650 */ +.fa-hand-scissors-o:before { + content: "\f257" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:651 */ +.fa-hand-lizard-o:before { + content: "\f258" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:652 */ +.fa-hand-spock-o:before { + content: "\f259" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:653 */ +.fa-hand-pointer-o:before { + content: "\f25a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:654 */ +.fa-hand-peace-o:before { + content: "\f25b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:655 */ +.fa-trademark:before { + content: "\f25c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:656 */ +.fa-registered:before { + content: "\f25d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:657 */ +.fa-creative-commons:before { + content: "\f25e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:658 */ +.fa-gg:before { + content: "\f260" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:659 */ +.fa-gg-circle:before { + content: "\f261" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:660 */ +.fa-tripadvisor:before { + content: "\f262" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:661 */ +.fa-odnoklassniki:before { + content: "\f263" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:662 */ +.fa-odnoklassniki-square:before { + content: "\f264" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:663 */ +.fa-get-pocket:before { + content: "\f265" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:664 */ +.fa-wikipedia-w:before { + content: "\f266" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:665 */ +.fa-safari:before { + content: "\f267" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:666 */ +.fa-chrome:before { + content: "\f268" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:667 */ +.fa-firefox:before { + content: "\f269" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:668 */ +.fa-opera:before { + content: "\f26a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:669 */ +.fa-internet-explorer:before { + content: "\f26b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:670 */ +.fa-tv:before, +.fa-television:before { + content: "\f26c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:672 */ +.fa-contao:before { + content: "\f26d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:673 */ +.fa-500px:before { + content: "\f26e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:674 */ +.fa-amazon:before { + content: "\f270" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:675 */ +.fa-calendar-plus-o:before { + content: "\f271" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:676 */ +.fa-calendar-minus-o:before { + content: "\f272" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:677 */ +.fa-calendar-times-o:before { + content: "\f273" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:678 */ +.fa-calendar-check-o:before { + content: "\f274" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:679 */ +.fa-industry:before { + content: "\f275" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:680 */ +.fa-map-pin:before { + content: "\f276" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:681 */ +.fa-map-signs:before { + content: "\f277" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:682 */ +.fa-map-o:before { + content: "\f278" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:683 */ +.fa-map:before { + content: "\f279" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:684 */ +.fa-commenting:before { + content: "\f27a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:685 */ +.fa-commenting-o:before { + content: "\f27b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:686 */ +.fa-houzz:before { + content: "\f27c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:687 */ +.fa-vimeo:before { + content: "\f27d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:688 */ +.fa-black-tie:before { + content: "\f27e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:689 */ +.fa-fonticons:before { + content: "\f280" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:690 */ +.fa-reddit-alien:before { + content: "\f281" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:691 */ +.fa-edge:before { + content: "\f282" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:692 */ +.fa-credit-card-alt:before { + content: "\f283" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:693 */ +.fa-codiepie:before { + content: "\f284" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:694 */ +.fa-modx:before { + content: "\f285" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:695 */ +.fa-fort-awesome:before { + content: "\f286" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:696 */ +.fa-usb:before { + content: "\f287" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:697 */ +.fa-product-hunt:before { + content: "\f288" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:698 */ +.fa-mixcloud:before { + content: "\f289" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:699 */ +.fa-scribd:before { + content: "\f28a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:700 */ +.fa-pause-circle:before { + content: "\f28b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:701 */ +.fa-pause-circle-o:before { + content: "\f28c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:702 */ +.fa-stop-circle:before { + content: "\f28d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:703 */ +.fa-stop-circle-o:before { + content: "\f28e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:704 */ +.fa-shopping-bag:before { + content: "\f290" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:705 */ +.fa-shopping-basket:before { + content: "\f291" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:706 */ +.fa-hashtag:before { + content: "\f292" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:707 */ +.fa-bluetooth:before { + content: "\f293" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:708 */ +.fa-bluetooth-b:before { + content: "\f294" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:709 */ +.fa-percent:before { + content: "\f295" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:710 */ +.fa-gitlab:before { + content: "\f296" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:711 */ +.fa-wpbeginner:before { + content: "\f297" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:712 */ +.fa-wpforms:before { + content: "\f298" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:713 */ +.fa-envira:before { + content: "\f299" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:714 */ +.fa-universal-access:before { + content: "\f29a" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:715 */ +.fa-wheelchair-alt:before { + content: "\f29b" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:716 */ +.fa-question-circle-o:before { + content: "\f29c" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:717 */ +.fa-blind:before { + content: "\f29d" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:718 */ +.fa-audio-description:before { + content: "\f29e" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:719 */ +.fa-volume-control-phone:before { + content: "\f2a0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:720 */ +.fa-braille:before { + content: "\f2a1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:721 */ +.fa-assistive-listening-systems:before { + content: "\f2a2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:722 */ +.fa-asl-interpreting:before, +.fa-american-sign-language-interpreting:before { + content: "\f2a3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:724 */ +.fa-deafness:before, +.fa-hard-of-hearing:before, +.fa-deaf:before { + content: "\f2a4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:727 */ +.fa-glide:before { + content: "\f2a5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:728 */ +.fa-glide-g:before { + content: "\f2a6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:729 */ +.fa-signing:before, +.fa-sign-language:before { + content: "\f2a7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:731 */ +.fa-low-vision:before { + content: "\f2a8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:732 */ +.fa-viadeo:before { + content: "\f2a9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:733 */ +.fa-viadeo-square:before { + content: "\f2aa" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:734 */ +.fa-snapchat:before { + content: "\f2ab" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:735 */ +.fa-snapchat-ghost:before { + content: "\f2ac" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:736 */ +.fa-snapchat-square:before { + content: "\f2ad" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:737 */ +.fa-pied-piper:before { + content: "\f2ae" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:738 */ +.fa-first-order:before { + content: "\f2b0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:739 */ +.fa-yoast:before { + content: "\f2b1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:740 */ +.fa-themeisle:before { + content: "\f2b2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:741 */ +.fa-google-plus-circle:before, +.fa-google-plus-official:before { + content: "\f2b3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:743 */ +.fa-fa:before, +.fa-font-awesome:before { + content: "\f2b4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:745 */ +.fa-handshake-o:before { + content: "\f2b5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:746 */ +.fa-envelope-open:before { + content: "\f2b6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:747 */ +.fa-envelope-open-o:before { + content: "\f2b7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:748 */ +.fa-linode:before { + content: "\f2b8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:749 */ +.fa-address-book:before { + content: "\f2b9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:750 */ +.fa-address-book-o:before { + content: "\f2ba" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:751 */ +.fa-vcard:before, +.fa-address-card:before { + content: "\f2bb" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:753 */ +.fa-vcard-o:before, +.fa-address-card-o:before { + content: "\f2bc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:755 */ +.fa-user-circle:before { + content: "\f2bd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:756 */ +.fa-user-circle-o:before { + content: "\f2be" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:757 */ +.fa-user-o:before { + content: "\f2c0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:758 */ +.fa-id-badge:before { + content: "\f2c1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:759 */ +.fa-drivers-license:before, +.fa-id-card:before { + content: "\f2c2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:761 */ +.fa-drivers-license-o:before, +.fa-id-card-o:before { + content: "\f2c3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:763 */ +.fa-quora:before { + content: "\f2c4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:764 */ +.fa-free-code-camp:before { + content: "\f2c5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:765 */ +.fa-telegram:before { + content: "\f2c6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:766 */ +.fa-thermometer-4:before, +.fa-thermometer:before, +.fa-thermometer-full:before { + content: "\f2c7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:769 */ +.fa-thermometer-3:before, +.fa-thermometer-three-quarters:before { + content: "\f2c8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:771 */ +.fa-thermometer-2:before, +.fa-thermometer-half:before { + content: "\f2c9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:773 */ +.fa-thermometer-1:before, +.fa-thermometer-quarter:before { + content: "\f2ca" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:775 */ +.fa-thermometer-0:before, +.fa-thermometer-empty:before { + content: "\f2cb" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:777 */ +.fa-shower:before { + content: "\f2cc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:778 */ +.fa-bathtub:before, +.fa-s15:before, +.fa-bath:before { + content: "\f2cd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:781 */ +.fa-podcast:before { + content: "\f2ce" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:782 */ +.fa-window-maximize:before { + content: "\f2d0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:783 */ +.fa-window-minimize:before { + content: "\f2d1" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:784 */ +.fa-window-restore:before { + content: "\f2d2" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:785 */ +.fa-times-rectangle:before, +.fa-window-close:before { + content: "\f2d3" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:787 */ +.fa-times-rectangle-o:before, +.fa-window-close-o:before { + content: "\f2d4" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:789 */ +.fa-bandcamp:before { + content: "\f2d5" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:790 */ +.fa-grav:before { + content: "\f2d6" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:791 */ +.fa-etsy:before { + content: "\f2d7" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:792 */ +.fa-imdb:before { + content: "\f2d8" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:793 */ +.fa-ravelry:before { + content: "\f2d9" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:794 */ +.fa-eercast:before { + content: "\f2da" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:795 */ +.fa-microchip:before { + content: "\f2db" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:796 */ +.fa-snowflake-o:before { + content: "\f2dc" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:797 */ +.fa-superpowers:before { + content: "\f2dd" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:798 */ +.fa-wpexplorer:before { + content: "\f2de" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/etc/_icons.scss:799 */ +.fa-meetup:before { + content: "\f2e0" !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-awesome/sass/src/all.scss:20 */ +.x-fa:before { + font-family: FontAwesome !important; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:3 */ +@font-face { + font-family: 'ExtJS'; + src: url('font-ext/fonts/ExtJS.eot?-tqegh9'); + src: url('font-ext/fonts/ExtJS.eot?#iefix-tqegh9') format('embedded-opentype'), url('font-ext/fonts/ExtJS.ttf?-tqegh9') format('truetype'), url('font-ext/fonts/ExtJS.woff?-tqegh9') format('woff'), url('font-ext/fonts/ExtJS.svg?-tqegh9#ExtJS') format('svg'); + font-weight: normal; + font-style: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:14 */ +.ext { + font-family: ExtJS; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:18 */ +.ext-sencha:before { + content: "\e61e"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:21 */ +.ext-checkbox-checked:before { + content: "\e613"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:24 */ +.ext-checkbox-unchecked:before { + content: "\e614"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:27 */ +.ext-chevron-left:before { + content: "\e615"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:30 */ +.ext-chevron-right:before { + content: "\e616"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:33 */ +.ext-double-chevron-left:before { + content: "\e617"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:36 */ +.ext-double-chevron-right:before { + content: "\e618"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:39 */ +.ext-sort-down:before { + content: "\e619"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:42 */ +.ext-sort-up:before { + content: "\e61a"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:45 */ +.ext-spinner-down:before { + content: "\e61b"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:48 */ +.ext-spinner-up:before { + content: "\e61c"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:51 */ +.ext-square-edit:before { + content: "\e61d"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:54 */ +.ext-equals-vertical:before { + content: "\e612"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:57 */ +.ext-expand:before { + content: "\e600"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:60 */ +.ext-columns:before { + content: "\e601"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:63 */ +.ext-dirty:before { + content: "\e602"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:66 */ +.ext-dirty-rtl:before { + content: "\e603"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:69 */ +.ext-edit-html:before { + content: "\e604"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:72 */ +.ext-equals:before { + content: "\e605"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:75 */ +.ext-collapse:before { + content: "\e606"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:78 */ +.ext-group-by:before { + content: "\e607"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:81 */ +.ext-minimize:before { + content: "\e608"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:84 */ +.ext-nw-handle:before { + content: "\e609"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:87 */ +.ext-ne-handle:before { + content: "\e60a"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:90 */ +.ext-sw-handle:before { + content: "\e60b"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:93 */ +.ext-se-handle:before { + content: "\e60c"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:96 */ +.ext-text-background-color:before { + content: "\e60d"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:99 */ +.ext-text-color:before { + content: "\e60e"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:102 */ +.ext-text-decrease:before { + content: "\e60f"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:105 */ +.ext-text-increase:before { + content: "\e610"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/packages/font-ext/sass/src/all.scss:108 */ +.ext-unpin:before { + content: "\e611"; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:3 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-Light"); + src: url('fonts/OpenSans-Light.ttf'); + font-weight: 300; + font-style: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:11 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-LightItalic"); + src: url('fonts/OpenSans-LightItalic.ttf'); + font-weight: 300; + font-style: italic; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:19 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-Regular"); + src: url('fonts/OpenSans-Regular.ttf'); + font-weight: 400; + font-style: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:27 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-Italic"); + src: url('fonts/OpenSans-Italic.ttf'); + font-weight: 400; + font-style: italic; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:35 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-Semibold"); + src: url('fonts/OpenSans-Semibold.ttf'); + font-weight: 600; + font-style: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:43 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-SemiboldItalic"); + src: url('fonts/OpenSans-SemiboldItalic.ttf'); + font-weight: 600; + font-style: italic; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:51 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-Bold"); + src: url('fonts/OpenSans-Bold.ttf'); + font-weight: 700; + font-style: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:59 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-BoldItalic"); + src: url('fonts/OpenSans-BoldItalic.ttf'); + font-weight: 700; + font-style: italic; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:67 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-ExtraBold"); + src: url('fonts/OpenSans-ExtraBold.ttf'); + font-weight: 800; + font-style: normal; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/Component.scss:75 */ +@font-face { + font-family: 'Open Sans'; + src: local("OpenSans-ExtraBoldItalic"); + src: url('fonts/OpenSans-ExtraBoldItalic.ttf'); + font-weight: 800; + font-style: italic; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/form/FieldSet.scss:1 */ +.x-fieldset { + border-top: 1px solid #bbb !important; + background: #f6f6f6; + position: static; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/form/FieldSet.scss:6 */ +.x-fieldset .x-fieldset-body { + position: relative; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/form/FieldSet.scss:10 */ +.x-fieldset.x-fieldset-collapsed { + background: none; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/menu/Menu.scss:1 */ +.x-menu-item-active .x-menu-item-text { + font-weight: 400; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/tab/Tab.scss:1 */ +.x-tab-close-btn:before { + display: block; + width: 16px; + line-height: 16px; + text-align: center; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/toolbar/Breadcrumb.scss:2 */ +.x-breadcrumb-btn > .x-btn-arrow-right:after { + content: ''; +} +/* /home/teamcity/buildAgent/work/47e72153b7b97580/sencha/ext/classic/theme-triton/sass/src/window/Toast.scss:1 */ +.x-toast { + -webkit-box-shadow: rgba(0, 0, 0, 0.5) 0 2px 2px; + -moz-box-shadow: rgba(0, 0, 0, 0.5) 0 2px 2px; + box-shadow: rgba(0, 0, 0, 0.5) 0 2px 2px; +} \ No newline at end of file diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all.css new file mode 100644 index 0000000..3e49d8c --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all.css @@ -0,0 +1,2 @@ +@import 'theme-triton-all_1.css'; +@import 'theme-triton-all_2.css'; diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all_1.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all_1.css new file mode 100644 index 0000000..a42a837 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all_1.css @@ -0,0 +1,13362 @@ +.x-size-monitored { + position: relative; +} +.x-size-monitors { + position: absolute; + left: 0; + top: 0; + width: 100%; + height: 100%; + visibility: hidden; + overflow: hidden; +} +.x-size-monitors > * { + width: 100%; + height: 100%; + overflow: hidden; +} +.x-size-monitors.scroll > *.shrink::after { + content: ""; + display: block; + width: 200%; + height: 200%; + min-width: 1px; + min-height: 1px; +} +.x-size-monitors.scroll > *.expand::after { + content: ""; + display: block; + width: 100000px; + height: 100000px; +} +.x-size-monitors.overflowchanged > *.shrink > * { + width: 100%; + height: 100%; +} +.x-size-monitors.overflowchanged > *.expand > * { + width: 200%; + height: 200%; +} +.x-size-change-detector { + visibility: hidden; + position: absolute; + left: 0; + top: 0; + z-index: -1; + width: 100%; + height: 100%; + overflow: hidden; +} +.x-size-change-detector > * { + visibility: hidden; +} +.x-size-change-detector-shrink > * { + width: 200%; + height: 200%; +} +.x-size-change-detector-expand > * { + width: 100000px; + height: 100000px; +} +@-webkit-keyframes x-paint-monitor-helper { + from { + zoom: 1; + } + to { + zoom: 1; + } +} +@keyframes x-paint-monitor-helper { + from { + zoom: 1; + } + to { + zoom: 1; + } +} +.x-paint-monitored { + position: relative; +} +.x-paint-monitor { + width: 0 !important; + height: 0 !important; + visibility: hidden; +} +.x-paint-monitor.cssanimation { + -webkit-animation-duration: 0.0001ms; + -webkit-animation-name: x-paint-monitor-helper; + animation-duration: 0.0001ms; + animation-name: x-paint-monitor-helper; +} +.x-paint-monitor.overflowchange { + overflow: hidden; +} +.x-paint-monitor.overflowchange::after { + content: ""; + display: block; + width: 1px !important; + height: 1px !important; +} +.x-unselectable { + user-select: none; + -o-user-select: none; + -ms-user-select: none; + -moz-user-select: -moz-none; + -webkit-user-select: none; + -webkit-tap-highlight-color: transparent; + -webkit-user-drag: none; + cursor: default; +} +.x-hidden-clip { + position: absolute !important; + clip: rect(0, 0, 0, 0); +} +.x-hidden-display { + display: none !important; +} +.x-hidden-offsets, +.x-hidden { + display: block !important; + visibility: hidden !important; + position: absolute !important; + top: -10000px !important; +} +.x-hidden-opacity { + opacity: 0 !important; + pointer-events: none; +} +.x-hidden-visibility { + visibility: hidden !important; +} +.x-pressed .x-ripple-transition, +.x-pressing .x-ripple-transition { + transition: background-color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1), + color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1); +} +.x-pressed .x-ripple-transition .x-icon-el, +.x-pressed .x-ripple-transition .x-arrow-el, +.x-pressing .x-ripple-transition .x-icon-el, +.x-pressing .x-ripple-transition .x-arrow-el { + transition: background-color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1), + color 0.15s 0.2s cubic-bezier(0.4, 0, 0.2, 1); +} +.x-rippling { + position: relative; +} +.x-rippling.x-component-confirm .x-ripple { + background-color: green; +} +.x-rippling.x-component-decline .x-ripple { + background-color: red; +} +.x-rippling.x-rippling-unbound { + overflow: visible !important; +} +.x-rippling.x-rippling-unbound .x-ripple-container { + overflow: visible; + position: absolute; +} +.x-safari .x-rippling:not(.x-rippling-unbound) .x-ripple-container { + -webkit-transform: rotate(0); + -moz-transform: rotate(0); + -ms-transform: rotate(0); + -o-transform: rotate(0); + transform: rotate(0); +} +.x-ripple-container { + overflow: hidden; + position: absolute; + top: 0; + bottom: 0; + left: 0; + right: 0; + pointer-events: none; +} +.x-ripple-wrapper { + z-index: 1000; +} +.x-button-fab .x-ripple-container, +.x-button-round .x-ripple-container { + border-radius: 10000px; +} +.x-splitButton-fab .x-ripple-container, +.x-splitButton-round .x-ripple-container { + border-radius: 10000px; +} +.x-ripple { + position: absolute; + border-radius: 50%; + background-color: white; + -webkit-transform: scale(1, 1); + -moz-transform: scale(1, 1); + -ms-transform: scale(1, 1); + -o-transform: scale(1, 1); + transform: scale(1, 1); + opacity: 0.4; + pointer-events: none; +} +.x-rippling.x-rippling-unbound .x-ripple { + -webkit-animation: x-ripple-unbound-animation 0.3s ease-out forwards; + animation: x-ripple-unbound-animation 0.3s ease-out forwards; +} +.x-rippling:not(.x-rippling-unbound) .x-ripple { + -webkit-animation: x-ripple-animation 0.35s ease-out forwards; + animation: x-ripple-animation 0.35s ease-out forwards; +} +@-webkit-keyframes x-ripple-animation { + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + 75% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0.2; + } + 100% { + -webkit-transform: scale(2.35, 2.35); + -moz-transform: scale(2.35, 2.35); + -ms-transform: scale(2.35, 2.35); + -o-transform: scale(2.35, 2.35); + transform: scale(2.35, 2.35); + opacity: 0; + } +} +@keyframes x-ripple-animation { + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + 75% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0.2; + } + 100% { + -webkit-transform: scale(2.35, 2.35); + -moz-transform: scale(2.35, 2.35); + -ms-transform: scale(2.35, 2.35); + -o-transform: scale(2.35, 2.35); + transform: scale(2.35, 2.35); + opacity: 0; + } +} +@-webkit-keyframes x-ripple-unbound-animation { + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + 75% { + -webkit-transform: scale(1.75, 1.75); + -moz-transform: scale(1.75, 1.75); + -ms-transform: scale(1.75, 1.75); + -o-transform: scale(1.75, 1.75); + transform: scale(1.75, 1.75); + opacity: 0.2; + } + 100% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0; + } +} +@keyframes x-ripple-unbound-animation { + 0% { + -webkit-transform: scale(0, 0); + -moz-transform: scale(0, 0); + -ms-transform: scale(0, 0); + -o-transform: scale(0, 0); + transform: scale(0, 0); + opacity: 0.4; + } + 75% { + -webkit-transform: scale(1.75, 1.75); + -moz-transform: scale(1.75, 1.75); + -ms-transform: scale(1.75, 1.75); + -o-transform: scale(1.75, 1.75); + transform: scale(1.75, 1.75); + opacity: 0.2; + } + 100% { + -webkit-transform: scale(2, 2); + -moz-transform: scale(2, 2); + -ms-transform: scale(2, 2); + -o-transform: scale(2, 2); + transform: scale(2, 2); + opacity: 0; + } +} +.x-progress { + overflow: hidden; + position: relative; +} +.x-progress-bar { + height: 100%; + width: 0; +} +.x-progress-text { + overflow: hidden; +} +.x-progress-bar { + overflow: hidden; + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-scroller { + -webkit-overflow-scrolling: touch; + overflow-anchor: none; +} +.x-scroller-spacer { + position: absolute; + top: 0; + overflow: hidden; + height: 1px; + width: 1px; + font-size: 0; + line-height: 0; + pointer-events: none; +} +.x-scroller-snappable { + -ms-scroll-snap-type: mandatory; + -webkit-scroll-snap-type: mandatory; + scroll-snap-type: mandatory; +} +.x-no-scrollbars { + -ms-overflow-style: none; +} +.x-no-scrollbars::-webkit-scrollbar { + width: 0; +} +.x-touch-action-pan-y { + overflow-x: hidden !important; +} +.x-touch-action-pan-x { + overflow-y: hidden !important; +} +.x-drag-body { + cursor: default; +} +.x-drag-body * { + -webkit-user-select: none; + -moz-user-select: none; + user-select: none; +} +.x-drag-dragging { + z-index: 1000000 !important; + pointer-events: none; +} +.x-treelist { + background-color: #fff; + background-position: 16px 0%; + overflow: hidden; + padding: 0 0 0 0; +} +.x-treelist-container, +.x-treelist-root-container { + width: 100%; +} +.x-treelist-toolstrip { + display: none; +} +.x-treelist-micro > .x-treelist-toolstrip { + display: inline-block; +} +.x-treelist-micro > .x-treelist-root-container { + display: none; +} +.x-treelist-item, +.x-treelist-container, +.x-treelist-root-container { + position: relative; + overflow: hidden; + list-style: none; + padding: 0; + margin: 0; +} +.x-treelist-item-tool, +.x-treelist-row, +.x-treelist-item-wrap { + position: relative; +} +.x-treelist-item-icon, +.x-treelist-item-expander { + display: none; + position: absolute; + top: 0; +} +.x-treelist-item-expander { + right: 0; + cursor: pointer; +} +.x-treelist-expander-only + .x-treelist-item-expandable + > * + > .x-treelist-item-wrap + > * { + cursor: pointer; +} +.x-treelist-item-text { + cursor: pointer; + white-space: nowrap; + overflow: hidden; +} +.x-treelist-item-collapsed > .x-treelist-container { + display: none; +} +.x-treelist-item-expandable > * > * > .x-treelist-item-expander, +.x-treelist-item-icon { + display: block; +} +.x-treelist-item-floated > * > * > .x-treelist-item-expander, +.x-treelist-item-floated > * > * > .x-treelist-item-icon { + display: none; +} +.x-treelist-expander-first .x-treelist-item-expander { + left: 0; + right: auto; +} +.x-treelist-toolstrip { + background-color: #f8f8f8; +} +.x-treelist-item-selected > .x-treelist-row { + background-color: #ffefbb; +} +.x-treelist-item-selected > .x-treelist-row-over { + background-color: #ffefbb; +} +.x-treelist-item-tool { + padding-left: 6px; + padding-right: 10px; +} +.x-treelist-item-icon:before, +.x-treelist-item-tool:before, +.x-treelist-item-expander { + line-height: 32px; +} +.x-treelist-item-icon, +.x-treelist-item-tool, +.x-treelist-item-expander { + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; +} +.x-treelist-item-loading .x-treelist-item-icon { + background-image: url(images/tree/loading.gif); + color: transparent; +} +.x-treelist-item-icon, +.x-treelist-item-tool { + color: #5fa2dd; + font-size: 16px; + width: 16px; +} +.x-treelist-item-tool { + width: 32px; +} +.x-treelist-item-expander { + color: #5fa2dd; + font-size: 16px; + width: 18px; +} +.x-treelist-item-expander:after { + content: "\f0da"; + font: 16px/32px FontAwesome; +} +.x-treelist-item-expanded > * > * > .x-treelist-item-expander:after { + content: "\f0d7"; + font: 16px/32px FontAwesome; +} +.x-treelist-item-text { + color: #404040; + margin-left: 22px; + margin-right: 18px; + font-size: 13px; + line-height: 32px; + text-overflow: ellipsis; +} +.x-treelist-row { + padding-left: 6px; + padding-right: 10px; +} +.x-treelist-item-floated .x-treelist-container { + width: auto; +} +.x-treelist-item-floated > .x-treelist-row { + background-color: #f8f8f8; +} +.x-treelist-item-floated > .x-treelist-container { + margin-left: -6px; +} +.x-big .x-treelist-item-floated > .x-treelist-container { + margin-left: -6px; +} +.x-treelist-item-floated > * > * > .x-treelist-item-text { + margin-left: 0; +} +.x-treelist-item-floated > * .x-treelist-row { + cursor: pointer; + padding-left: 0; +} +.x-treelist-item-floated .x-treelist-row:before { + width: 0; +} +.x-treelist-item-floated > .x-treelist-row-over { + background-color: #f8f8f8; +} +.x-treelist-item-floated > .x-treelist-row-over > * > .x-treelist-item-text { + color: #404040; +} +.x-treelist-item-expanded > .x-treelist-item-expander:after { + content: "\f0d7"; + font: 16px/1 FontAwesome; +} +.x-treelist-item-collapsed > * > .x-treelist-item-expander:after { + content: "\f0da"; + font: 16px/1 FontAwesome; +} +.x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-icon { + color: #5fa2dd; + transition: color 0.5s; +} +.x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-text { + color: #404040; + transition: color 0.5s; +} +.x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-expander { + color: #5fa2dd; + transition: color 0.5s; +} +.x-treelist-row-over { + background-color: #eaeff4; +} +.x-treelist-row-over > * > .x-treelist-item-icon { + color: #5fa2dd; + transition: color 0.5s; +} +.x-treelist-row-over > * > .x-treelist-item-text { + color: #404040; + transition: color 0.5s; +} +.x-treelist-row-over > * > .x-treelist-item-expander { + color: #5fa2dd; + transition: color 0.5s; +} +.x-treelist-expander-first .x-treelist-item-icon { + left: 18px; +} +.x-treelist-expander-first .x-treelist-item-text { + margin-left: 40px; + margin-right: 0; +} +.x-treelist-expander-first + .x-treelist-item-hide-icon + > * + > * + > .x-treelist-item-text { + margin-left: 21px; +} +.x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 3px; +} +.x-treelist-nav { + background-color: #32404e; + background-position: 24px 0%; + padding: 0 0 0 0; +} +.x-treelist-nav .x-treelist-toolstrip { + background-color: #32404e; +} +.x-treelist-nav .x-treelist-item-selected.x-treelist-item-tool { + color: #f0f0f0; + background-color: #5fa2dd; +} +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row { + background-color: #3f505f; +} +.x-treelist-nav .x-treelist-item-tool { + padding-left: 10px; + padding-right: 10px; +} +.x-treelist-nav .x-treelist-item-tool-floated:after { + height: 44px; + position: absolute; + top: 0; + left: 0; + content: " "; + width: 4px; + background-color: #5fa2dd; +} +.x-treelist-nav .x-treelist-item-icon:before, +.x-treelist-nav .x-treelist-item-tool:before, +.x-treelist-nav .x-treelist-item-expander { + line-height: 30px; +} +.x-treelist-nav .x-treelist-item-icon, +.x-treelist-nav .x-treelist-item-tool, +.x-treelist-nav .x-treelist-item-expander { + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; +} +.x-treelist-nav .x-treelist-item-loading .x-treelist-item-icon { + background-image: url(images/tree/loading.gif); + color: transparent; +} +.x-treelist-nav .x-treelist-item-icon, +.x-treelist-nav .x-treelist-item-tool { + color: #adb3b8; + font-size: 18px; + width: 24px; +} +.x-treelist-nav .x-treelist-item-tool { + width: 44px; +} +.x-treelist-nav .x-treelist-item-expander { + color: #adb3b8; + font-size: 16px; + width: 24px; +} +.x-treelist-nav .x-treelist-item-text { + color: #adb3b8; + margin-left: 30px; + margin-right: 24px; + font-size: 16px; + line-height: 44px; +} +.x-treelist-nav .x-treelist-row { + padding-left: 10px; + padding-right: 10px; +} +.x-treelist-nav .x-treelist-row-over:before, +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before { + content: " "; + position: absolute; + display: block; + left: 0; + top: 0; + width: 6px; + height: 100%; +} +.x-treelist-nav .x-treelist-row-over:before { + background-color: #89bae6; +} +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row-over:before { + background-color: #89bae6; +} +.x-treelist-nav .x-treelist-item-selected > .x-treelist-row:before { + background-color: #5fa2dd; +} +.x-treelist-nav .x-treelist-item-floated .x-treelist-container { + width: auto; +} +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row { + background-color: #32404e; +} +.x-treelist-nav .x-treelist-item-floated > .x-treelist-container { + margin-left: -10px; +} +.x-big .x-treelist-nav .x-treelist-item-floated > .x-treelist-container { + margin-left: -10px; +} +.x-treelist-nav .x-treelist-item-floated > * > * > .x-treelist-item-text { + margin-left: 0; +} +.x-treelist-nav .x-treelist-item-floated > * .x-treelist-row { + cursor: pointer; + padding-left: 0; +} +.x-treelist-nav .x-treelist-item-floated .x-treelist-row:before { + width: 0; +} +.x-treelist-nav .x-treelist-item-floated > .x-treelist-row-over { + background-color: #32404e; +} +.x-treelist-nav + .x-treelist-item-floated + > .x-treelist-row-over + > * + > .x-treelist-item-text { + color: #adb3b8; +} +.x-treelist-nav .x-treelist-item-expanded { + background-color: #2c3845; +} +.x-treelist-nav + .x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-icon { + color: #fff; +} +.x-treelist-nav + .x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-text { + color: #fff; +} +.x-treelist-nav + .x-treelist-highlight-path + .x-treelist-item-over + > * + > * + > .x-treelist-item-expander { + color: #fff; +} +.x-treelist-nav .x-treelist-row-over { + background-color: #4f606f; +} +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-icon { + color: #fff; +} +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-text { + color: #fff; +} +.x-treelist-nav .x-treelist-row-over > * > .x-treelist-item-expander { + color: #fff; +} +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-icon { + left: 24px; +} +.x-treelist-nav .x-treelist-expander-first .x-treelist-item-text { + margin-left: 54px; + margin-right: 0; +} +.x-treelist-nav + .x-treelist-expander-first + .x-treelist-item-hide-icon + > * + > * + > .x-treelist-item-text { + margin-left: 27px; +} +.x-treelist-nav .x-treelist-item-hide-icon > * > * > .x-treelist-item-text { + margin-left: 3px; +} +.x-body { + margin: 0; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} +@-ms-viewport { + width: device-width; +} +img { + border: 0; +} +.x-border-box, +.x-border-box * { + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +.x-ltr { + direction: ltr; +} +.x-clear { + overflow: hidden; + clear: both; + font-size: 0; + line-height: 0; + display: table; +} +.x-layer { + position: absolute !important; + top: 0; + left: 0; + overflow: hidden; +} +.x-fixed-layer { + position: fixed !important; + overflow: hidden; +} +.x-shim { + position: absolute; + left: 0; + top: 0; + overflow: hidden; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +.x-hidden-clip { + position: absolute !important; + clip: rect(0, 0, 0, 0); +} +.x-masked-relative { + position: relative; +} +.x-ie-shadow { + background-color: #777; + position: absolute; + overflow: hidden; +} +.x-selectable { + cursor: auto; + -moz-user-select: text; + -webkit-user-select: text; + -ms-user-select: text; + user-select: text; + -o-user-select: text; +} +.x-list-plain { + list-style-type: none; + margin: 0; + padding: 0; +} +.x-table-plain { + border-collapse: collapse; + border-spacing: 0; + font-size: 1em; +} +.x-frame-tl, +.x-frame-tr, +.x-frame-tc, +.x-frame-bl, +.x-frame-br, +.x-frame-bc { + overflow: hidden; + background-repeat: no-repeat; +} +.x-frame-tc, +.x-frame-bc { + background-repeat: repeat-x; +} +td.x-frame-tl, +td.x-frame-tr, +td.x-frame-bl, +td.x-frame-br { + width: 1px; +} +.x-frame-mc { + background-repeat: repeat-x; + overflow: hidden; +} +.x-proxy-el { + position: absolute; + background: #b4b4b4; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +.x-css-shadow { + position: absolute; + -webkit-border-radius: 5px; + -moz-border-radius: 5px; + -ms-border-radius: 5px; + -o-border-radius: 5px; + border-radius: 5px; +} +.x-item-disabled, +.x-item-disabled * { + cursor: default; + pointer-events: none; +} +.x-component, +.x-container { + position: relative; +} +:focus { + outline: none; +} +.x-body .x-sync-repaint:before, +.x-body .x-sync-repaint:after { + content: none !important; +} +.x-position-relative { + position: relative !important; +} +.x-tab-guard { + position: absolute; + clip: rect(0, 0, 0, 0); +} +.x-box-item { + position: absolute !important; + left: 0; + top: 0; +} +.x-autocontainer-outerCt { + display: table; +} +.x-mobile-safari .x-autocontainer-outerCt { + transform: translateZ(0); +} +.x-clipped .x-autocontainer-outerCt { + transform: initial; +} +.x-autocontainer-innerCt { + display: table-cell; + height: 100%; + vertical-align: top; +} +.x-mask { + z-index: 100; + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + outline: none !important; +} +.x-ie8 .x-mask { + background-image: url(data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7); +} +.x-mask-fixed { + position: fixed; +} +.x-mask-msg { + position: absolute; +} +.x-progress { + border-style: solid; +} +.x-btn { + display: inline-block; + outline: 0; + cursor: pointer; + white-space: nowrap; + text-decoration: none; + vertical-align: top; + overflow: hidden; + position: relative; +} +.x-btn > .x-frame { + height: 100%; + width: 100%; +} +.x-btn-wrap { + height: 100%; + width: 100%; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: stretch; + -ms-flex-align: stretch; + align-items: stretch; +} +.x-btn-wrap.x-btn-arrow-bottom, +.x-btn-wrap.x-btn-split-bottom { + -webkit-box-orient: vertical; + -ms-flex-direction: column; + flex-direction: column; +} +.x-ie9m .x-btn-wrap { + display: table; + border-spacing: 0; +} +.x-btn-button { + white-space: nowrap; + line-height: 0; + position: relative; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: center; + -ms-flex-align: center; + align-items: center; + -webkit-box-flex: 1; + -ms-flex: 1 1 auto; + flex: 1 1 auto; + min-width: 0; +} +.x-btn-button.x-btn-icon-top, +.x-btn-button.x-btn-icon-bottom { + -webkit-box-orient: vertical; + -ms-flex-direction: column; + flex-direction: column; + -webkit-box-align: stretch; + -ms-flex-align: stretch; + align-items: stretch; + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +.x-ie10p .x-btn-button.x-btn-icon-top, +.x-ie10p .x-btn-button.x-btn-icon-bottom { + overflow: hidden; +} +.x-ie9m .x-btn-button { + display: table-cell; + vertical-align: middle; +} +.x-btn-inner { + overflow: hidden; + text-overflow: ellipsis; + -ms-flex-negative: 1; + display: block; +} +.x-ie9m .x-btn-inner { + display: inline-block; + vertical-align: middle; +} +.x-btn-icon.x-btn-no-text > .x-btn-inner { + display: none; +} +.x-btn-icon-el { + display: none; + vertical-align: middle; + text-align: center; + background-position: center center; + background-repeat: no-repeat; + flex-shrink: 0; +} +.x-btn-icon > .x-btn-icon-el { + display: block; +} +.x-ie9m .x-btn-icon-left > .x-btn-icon-el, +.x-ie9m .x-btn-icon-right > .x-btn-icon-el { + display: inline-block; +} +.x-btn-button-center { + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +.x-ie9m .x-btn-button-center { + text-align: center; +} +.x-btn-button-center.x-btn-icon-top, +.x-btn-button-center.x-btn-icon-bottom { + text-align: center; +} +.x-btn-button-left { + text-align: left; + -webkit-box-pack: start; + -ms-flex-pack: start; + justify-content: flex-start; +} +.x-btn-button-right { + text-align: right; + -webkit-box-pack: end; + -ms-flex-pack: end; + justify-content: flex-end; +} +.x-btn-arrow:after, +.x-btn-split:after { + display: block; + background-repeat: no-repeat; + content: ""; + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; + text-align: center; +} +.x-btn-arrow-right:after, +.x-btn-split-right:after { + background-position: right center; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-align: center; + -ms-flex-align: center; + align-items: center; + -webkit-box-pack: center; + -ms-flex-pack: center; + justify-content: center; +} +.x-ie9m .x-btn-arrow-right:after, +.x-ie9m .x-btn-split-right:after { + display: table-cell; + vertical-align: middle; +} +.x-btn-arrow-bottom:after, +.x-btn-split-bottom:after { + background-position: center bottom; + content: "\00a0"; + line-height: 0; +} +.x-ie9m .x-btn-arrow-bottom:after, +.x-ie9m .x-btn-split-bottom:after { + display: table-row; +} +.x-btn-split-right > .x-btn-button:after { + position: absolute; + display: block; + top: -100%; + right: 0; + height: 300%; + content: ""; +} +.x-btn-split-bottom > .x-btn-button:after { + position: absolute; + display: block; + bottom: 0; + left: -100%; + font-size: 0; + width: 300%; + content: ""; +} +.x-btn-mc { + overflow: visible; +} +.x-segmented-button { + display: table; + table-layout: fixed; +} +.x-segmented-button-item { + display: table-cell; + vertical-align: top; +} +.x-segmented-button-item > .x-frame { + width: 100%; + height: 100%; +} +.x-segmented-button-item .x-btn-mc { + width: 100%; +} +.x-segmented-button-item-horizontal { + display: table-cell; + height: 100%; +} +.x-segmented-button-item-horizontal.x-segmented-button-first { + border-top-right-radius: 0; + border-bottom-right-radius: 0; +} +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-tr, +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-mr, +.x-segmented-button-item-horizontal.x-segmented-button-first .x-btn-br { + display: none; +} +.x-segmented-button-item-horizontal.x-segmented-button-middle { + border-radius: 0; + border-left: 0; +} +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tl, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-tr, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-ml, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-mr, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-bl, +.x-segmented-button-item-horizontal.x-segmented-button-middle .x-btn-br { + display: none; +} +.x-segmented-button-item-horizontal.x-segmented-button-last { + border-left: 0; + border-top-left-radius: 0; + border-bottom-left-radius: 0; +} +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-tl, +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-ml, +.x-segmented-button-item-horizontal.x-segmented-button-last .x-btn-bl { + display: none; +} +.x-segmented-button-row { + display: table-row; +} +.x-segmented-button-item-vertical.x-segmented-button-first { + border-bottom-right-radius: 0; + border-bottom-left-radius: 0; +} +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bl, +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-bc, +.x-segmented-button-item-vertical.x-segmented-button-first .x-btn-br { + display: none; +} +.x-segmented-button-item-vertical.x-segmented-button-middle { + border-radius: 0; + border-top: 0; +} +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tl, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tc, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-tr, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bl, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-bc, +.x-segmented-button-item-vertical.x-segmented-button-middle .x-btn-br { + display: none; +} +.x-segmented-button-item-vertical.x-segmented-button-last { + border-top: 0; + border-top-right-radius: 0; + border-top-left-radius: 0; +} +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tl, +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tc, +.x-segmented-button-item-vertical.x-segmented-button-last .x-btn-tr { + display: none; +} +.x-title-icon { + background-repeat: no-repeat; + background-position: 0 0; + vertical-align: middle; + line-height: 1; + text-align: center; +} +.x-title { + display: table; + table-layout: fixed; +} +.x-title-text { + display: table-cell; + overflow: hidden; + white-space: nowrap; + -o-text-overflow: ellipsis; + text-overflow: ellipsis; + vertical-align: middle; +} +.x-title-align-left { + text-align: left; +} +.x-title-align-center { + text-align: center; +} +.x-title-align-right { + text-align: right; +} +.x-title-rotate-right { + -webkit-transform: rotate(90deg); + -webkit-transform-origin: 0 0; + -moz-transform: rotate(90deg); + -moz-transform-origin: 0 0; + -ms-transform: rotate(90deg); + -ms-transform-origin: 0 0; + transform: rotate(90deg); + transform-origin: 0 0; +} +.x-ie8 .x-title-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +.x-title-rotate-left { + -webkit-transform: rotate(270deg); + -webkit-transform-origin: 100% 0; + -moz-transform: rotate(270deg); + -moz-transform-origin: 100% 0; + -ms-transform: rotate(270deg); + -ms-transform-origin: 100% 0; + transform: rotate(270deg); + transform-origin: 100% 0; +} +.x-ie8 .x-title-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +.x-horizontal.x-header + .x-title-rotate-right.x-title-align-left + > .x-title-item { + vertical-align: bottom; +} +.x-horizontal.x-header + .x-title-rotate-right.x-title-align-center + > .x-title-item { + vertical-align: middle; +} +.x-horizontal.x-header + .x-title-rotate-right.x-title-align-right + > .x-title-item { + vertical-align: top; +} +.x-horizontal.x-header .x-title-rotate-left.x-title-align-left > .x-title-item { + vertical-align: top; +} +.x-horizontal.x-header + .x-title-rotate-left.x-title-align-center + > .x-title-item { + vertical-align: middle; +} +.x-horizontal.x-header + .x-title-rotate-left.x-title-align-right + > .x-title-item { + vertical-align: bottom; +} +.x-vertical.x-header .x-title-rotate-none.x-title-align-left > .x-title-item { + vertical-align: top; +} +.x-vertical.x-header .x-title-rotate-none.x-title-align-center > .x-title-item { + vertical-align: middle; +} +.x-vertical.x-header .x-title-rotate-none.x-title-align-right > .x-title-item { + vertical-align: bottom; +} +.x-title-icon-wrap { + display: table-cell; + text-align: center; + vertical-align: middle; + line-height: 0; +} +.x-title-icon-wrap.x-title-icon-top, +.x-title-icon-wrap.x-title-icon-bottom { + display: table-row; +} +.x-title-icon { + display: inline-block; + vertical-align: middle; + background-position: center; + background-repeat: no-repeat; +} +.x-tool { + font-size: 16px; + line-height: 1; +} +.x-header > .x-box-inner, +.x-panel-header-mc > .x-box-inner, +.x-window-header-mc > .x-box-inner { + overflow: visible; +} +.x-splitter { + font-size: 1px; +} +.x-splitter-horizontal { + cursor: e-resize; + cursor: row-resize; +} +.x-splitter-vertical { + cursor: e-resize; + cursor: col-resize; +} +.x-splitter-collapsed, +.x-splitter-horizontal-noresize, +.x-splitter-vertical-noresize { + cursor: default; +} +.x-splitter-active { + z-index: 4; +} +.x-collapse-el { + position: absolute; + background-repeat: no-repeat; +} +.x-splitter-focus { + z-index: 4; +} +.x-box-layout-ct { + overflow: hidden; +} +.x-box-target { + position: absolute; + width: 20000px; + top: 0; + left: 0; + min-height: 1px; +} +.x-box-inner { + overflow: hidden; + position: relative; + left: 0; + top: 0; +} +.x-box-scroller { + position: absolute; + background-repeat: no-repeat; + background-position: center; + line-height: 0; + font-size: 0; + text-align: center; +} +.x-box-scroller-top { + top: 0; +} +.x-box-scroller-right { + right: 0; +} +.x-box-scroller-bottom { + bottom: 0; +} +.x-box-scroller-left { + left: 0; +} +.x-box-menu-body-horizontal { + float: left; +} +.x-box-menu-after { + position: relative; + float: left; +} +.x-box-scroller-body-vertical, +.x-box-scroller-body-horizontal { + -ms-overflow-style: none; +} +.x-box-scroller-body-vertical .x-scroller, +.x-box-scroller-body-horizontal .x-scroller { + -ms-overflow-style: auto; +} +.x-box-scroller-body-vertical :not(.x-scroller)::-webkit-scrollbar, +.x-box-scroller-body-horizontal :not(.x-scroller)::-webkit-scrollbar { + display: none; +} +.x-toolbar-text { + white-space: nowrap; +} +.x-toolbar-separator { + display: block; + font-size: 1px; + overflow: hidden; + cursor: default; + border: 0; + width: 0; + height: 0; + line-height: 0px; +} +.x-toolbar-scroller { + padding-left: 0; +} +.x-toolbar-plain { + border: 0; +} +.x-dd-drag-proxy, +.x-dd-drag-current { + z-index: 1000000 !important; + pointer-events: none; +} +.x-dd-drag-proxy { + display: table; +} +.x-dd-drag-repair .x-dd-drag-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +.x-dd-drag-repair .x-dd-drop-icon { + display: none; +} +.x-dd-drag-ghost, +.x-dd-drop-icon { + display: table-cell; + vertical-align: middle; +} +.x-dd-drag-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=85)"; + opacity: 0.85; + white-space: nowrap; +} +.x-dd-drop-icon { + height: 26px; + width: 26px; + background-color: transparent; + background-position: center; + background-repeat: no-repeat; +} +.x-docked { + position: absolute !important; + z-index: 2; +} +.x-docked-vertical { + position: static; +} +.x-docked-top { + border-bottom-width: 0 !important; +} +.x-docked-bottom { + border-top-width: 0 !important; +} +.x-docked-left { + border-right-width: 0 !important; +} +.x-docked-right { + border-left-width: 0 !important; +} +.x-docked-noborder-top { + border-top-width: 0 !important; +} +.x-docked-noborder-right { + border-right-width: 0 !important; +} +.x-docked-noborder-bottom { + border-bottom-width: 0 !important; +} +.x-docked-noborder-left { + border-left-width: 0 !important; +} +.x-noborder-l { + border-left-width: 0 !important; +} +.x-noborder-b { + border-bottom-width: 0 !important; +} +.x-noborder-bl { + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-r { + border-right-width: 0 !important; +} +.x-noborder-rl { + border-right-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-rb { + border-right-width: 0 !important; + border-bottom-width: 0 !important; +} +.x-noborder-rbl { + border-right-width: 0 !important; + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-t { + border-top-width: 0 !important; +} +.x-noborder-tl { + border-top-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-tb { + border-top-width: 0 !important; + border-bottom-width: 0 !important; +} +.x-noborder-tbl { + border-top-width: 0 !important; + border-bottom-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-tr { + border-top-width: 0 !important; + border-right-width: 0 !important; +} +.x-noborder-trl { + border-top-width: 0 !important; + border-right-width: 0 !important; + border-left-width: 0 !important; +} +.x-noborder-trb { + border-top-width: 0 !important; + border-right-width: 0 !important; + border-bottom-width: 0 !important; +} +.x-noborder-trbl { + border-width: 0 !important; +} +.x-panel, +.x-plain { + overflow: hidden; + position: relative; +} +.x-panel { + outline: none; +} +td.x-frame-mc { + vertical-align: top; +} +.x-panel-bodyWrap { + overflow: hidden; + position: static; + height: 100%; + width: 100%; +} +.x-panel-body { + overflow: hidden; + position: relative; +} +.x-panel-header-plain, +.x-panel-body-plain { + border: 0; + padding: 0; +} +.x-panel-collapsed-mini { + visibility: hidden; +} +.x-viewport > .x-body.x-panel > .x-panel-bodyWrap { + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; +} +.x-table-layout { + font-size: 1em; +} +.x-btn-group { + position: relative; + overflow: hidden; +} +.x-btn-group-body { + position: relative; +} +.x-btn-group-body .x-table-layout-cell { + vertical-align: top; +} +.x-viewport, +.x-viewport > .x-body { + margin: 0; + padding: 0; + border: 0 none; +} +.x-viewport { + width: 100%; + height: 100%; + position: static; +} +.x-viewport > .x-body { + position: fixed; + top: 0; + left: 0; + min-width: 100%; + min-height: 100%; +} +@media print { + .x-viewport > .x-body { + position: static; + } +} +.x-column { + float: left; +} +.x-resizable-overlay { + position: absolute; + left: 0; + top: 0; + width: 100%; + height: 100%; + display: none; + z-index: 200000; + background-color: #fff; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +.x-window { + outline: none; + overflow: hidden; +} +.x-window .x-window-wrap { + position: relative; +} +.x-window-body { + position: relative; + overflow: hidden; +} +.x-form-item { + display: table; + table-layout: fixed; + border-spacing: 0; + border-collapse: separate; +} +.x-form-item-label { + overflow: hidden; +} +.x-form-item.x-form-item-no-label > .x-form-item-label { + display: none; +} +.x-form-item-label, +.x-form-item-body { + display: table-cell; +} +.x-form-item-body { + vertical-align: middle; + height: 100%; +} +.x-form-item-label-inner { + display: inline-block; +} +.x-form-item-label-top { + display: table-row; + height: 1px; +} +.x-form-item-label-top > .x-form-item-label-inner { + display: table-cell; +} +.x-form-item-label-top-side-error:after { + display: table-cell; + content: ""; +} +.x-form-item-label-right { + text-align: right; +} +.x-form-error-wrap-side { + display: table-cell; + vertical-align: middle; +} +.x-form-error-wrap-under { + display: table-row; + height: 1px; +} +.x-form-error-wrap-under > .x-form-error-msg { + display: table-cell; +} +.x-form-error-wrap-under-side-label:before { + display: table-cell; + content: ""; + pointer-events: none; +} +.x-form-invalid-icon { + overflow: hidden; +} +.x-form-invalid-icon ul { + display: none; +} +.x-form-trigger-wrap { + display: table; + width: 100%; +} +.x-form-text-heighted .x-form-trigger-wrap { + height: 100%; +} +.x-gecko .x-form-trigger-wrap { + display: -moz-inline-box; + display: inline-flex; + vertical-align: top; +} +.x-form-type-text.x-has-min-height { + height: 1px; +} +.x-form-type-text.x-has-min-height .x-form-text-field-body, +.x-form-type-text.x-has-min-height .x-form-trigger-wrap, +.x-form-type-text.x-has-min-height .x-form-text-wrap { + min-height: inherit; +} +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-field-body, +.x-ie8 .x-form-type-text.x-has-min-height .x-form-trigger-wrap, +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text-wrap { + min-height: inherit; +} +.x-ie8 .x-form-type-text.x-has-min-height .x-form-text { + min-height: inherit; +} +.x-form-type-text.x-has-min-height .x-form-text { + height: 100%; +} +.x-form-text-wrap { + display: table-cell; + overflow: hidden; + height: 100%; + position: relative; +} +.x-gecko .x-form-text-wrap { + display: block; + -moz-box-flex: 1; + flex: 1; +} +.x-form-text-wrap .x-placeholder-label { + position: absolute; + top: 0; + left: 0; + cursor: text; + white-space: nowrap; + overflow: hidden; +} +.x-form-item-body.x-form-text-grow { + min-width: inherit; + max-width: inherit; +} +.x-form-text { + border: 0; + margin: 0; + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + display: block; + background: repeat-x 0 0; + width: 100%; + height: 100%; +} +.x-form-trigger { + display: table-cell; + vertical-align: top; + cursor: pointer; + overflow: hidden; + background-repeat: no-repeat; + text-align: center; + line-height: 0; + white-space: nowrap; +} +.x-item-disabled .x-form-trigger { + cursor: default; +} +.x-form-trigger.x-form-trigger-cmp { + background: none; + border: 0; +} +.x-gecko .x-form-trigger { + display: block; +} +.x-form-textarea-body.x-form-text-grow > .x-form-trigger-wrap { + height: 100%; +} +.x-form-textarea { + overflow: auto; + resize: none; +} +div.x-form-text-grow .x-form-textarea { + min-height: inherit; +} +.x-message-box .x-form-display-field { + height: auto; +} +.x-safari .x-form-fieldcontainer { + table-layout: auto; +} +.x-ie8 + .x-form-fieldcontainer + > .x-form-item-body.x-field-container-body-vertical { + display: table-row; +} +.x-form-cb-wrap { + vertical-align: top; +} +.x-form-cb-wrap-inner { + position: relative; +} +.x-form-cb { + position: absolute; + left: 0; + right: auto; + vertical-align: top; + overflow: hidden; + padding: 0; + border: 0; +} +.x-form-cb::-moz-focus-inner { + padding: 0; + border: 0; +} +.x-form-cb-input { + position: absolute; + margin: 0; + padding: 0; + border: 0; + top: 0; + left: 0; + width: 100%; + height: 100%; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +.x-form-cb-after { + left: auto; + right: 0; +} +.x-form-cb-label { + display: inline-block; +} +.x-form-cb-label.x-form-cb-no-box-label { + display: none; +} +.x-fieldset { + display: block; + position: relative; + overflow: hidden; +} +.x-fieldset-header { + overflow: hidden; +} +.x-fieldset-header .x-form-item, +.x-fieldset-header .x-tool { + float: left; +} +.x-fieldset-header .x-fieldset-header-text { + float: left; +} +.x-fieldset-header .x-form-cb-wrap { + font-size: 0; + line-height: 0; + min-height: 0; + height: auto; +} +.x-fieldset-header .x-form-cb { + margin: 0; + position: static; + display: inherit; +} +.x-fieldset-body { + overflow: hidden; +} +.x-fieldset-collapsed { + padding-bottom: 0 !important; +} +.x-fieldset-collapsed > .x-fieldset-body { + display: none; +} +.x-fieldset-header-text-collapsible { + cursor: pointer; +} +.x-keyboard-mode .x-view-item-focused { + outline: 1px dashed #5fa2dd !important; + outline-offset: -1px; +} +.x-ie9 .x-boundlist-list-ct { + min-height: 0%; +} +.x-datepicker { + position: relative; +} +.x-datepicker .x-monthpicker { + left: 0; + top: 0; + display: block; +} +.x-datepicker .x-monthpicker-months, +.x-datepicker .x-monthpicker-years { + height: 100%; +} +.x-datepicker-inner { + table-layout: fixed; + width: 100%; + border-collapse: separate; +} +.x-datepicker-cell { + padding: 0; +} +.x-datepicker-header { + position: relative; +} +.x-datepicker-arrow { + position: absolute; + outline: none; + font-size: 0; + display: table; +} +.x-datepicker-arrow:before { + display: table-cell; + text-align: center; + vertical-align: middle; +} +.x-datepicker-column-header { + padding: 0; +} +.x-datepicker-date { + display: block; + text-decoration: none; +} +.x-monthpicker { + display: table; +} +.x-monthpicker-body { + height: 100%; + position: relative; +} +.x-monthpicker-months, +.x-monthpicker-years { + float: left; +} +.x-monthpicker-item { + float: left; +} +.x-monthpicker-item-inner { + display: block; + text-decoration: none; +} +.x-monthpicker-yearnav-button-ct { + float: left; + text-align: center; +} +.x-monthpicker-yearnav-button { + display: inline-block; + outline: none; + font-size: 0; +} +.x-monthpicker-buttons { + width: 100%; +} +.x-datepicker .x-monthpicker-buttons { + position: absolute; + bottom: 0; +} +.x-datepicker-month .x-btn-split > .x-btn-button:after { + content: none; +} +.x-form-display-field-body { + vertical-align: top; +} +.x-form-display-field-body .x-form-display-field { + overflow-wrap: break-word; + word-wrap: break-word; + -ms-word-break: break-all; + word-break: break-all; + word-break: break-word; + -ms-hyphens: auto; + -moz-hyphens: auto; + -webkit-hyphens: auto; + hyphens: auto; +} +.x-form-trigger.x-form-trigger-cmp:before { + content: none; +} +.x-form-file-btn { + overflow: hidden; + position: relative; +} +.x-form-file-input { + border: 0; + position: absolute; + cursor: pointer; + top: 0; + right: 0; + width: 100%; + height: 100%; + overflow: hidden; + text-indent: -10000px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; + font-size: 1000px; +} +.x-form-item-hidden { + margin: 0; +} +.x-tip { + position: absolute; + overflow: visible; +} +.x-tip-body { + overflow: hidden; + position: relative; +} +.x-tip-anchor { + position: absolute; + border-style: solid; + height: 0; + width: 0; +} +.x-color-picker-item { + float: left; + text-decoration: none; +} +.x-color-picker-item-inner { + display: block; + font-size: 1px; +} +.x-html-editor-tb .x-toolbar { + position: static !important; +} +.x-htmleditor-iframe, +.x-htmleditor-textarea { + display: block; + overflow: auto; + width: 100%; + height: 100%; + border: 0; +} +.x-tagfield-body { + vertical-align: top; +} +.x-tagfield { + height: auto !important; + cursor: text; + overflow-y: auto; +} +.x-tagfield .x-tagfield-list { + padding: 0; + margin: 0; +} +.x-tagfield-list.x-tagfield-singleselect { + white-space: nowrap; + overflow: hidden; +} +.x-tagfield-input, +.x-tagfield-item { + vertical-align: top; + display: inline-block; + position: relative; +} +.x-tagfield-input-field { + font: inherit; + border: 0; + margin: 0; + background: none; + width: 100%; +} +.x-tagfield-stacked .x-tagfield-item { + display: block; +} +.x-tagfield-item { + cursor: default; +} +.x-tagfield-item-close { + cursor: pointer; + position: absolute; +} +.x-tagfield-arialist { + list-style-type: none; + position: absolute; + clip: rect(0, 0, 0, 0); +} +.x-tagfield-arialist-item { + list-style-type: none; +} +.x-fit-item { + position: relative; +} +.x-grid-view { + overflow: hidden; + position: relative; +} +.x-grid-row-table { + width: 0; + table-layout: fixed; + border: 0 none; + border-collapse: separate; + border-spacing: 0; +} +.x-grid-item { + table-layout: fixed; + outline: none; + position: relative; +} +.x-ie10 .x-grid-item { + transform: translateZ(0); +} +.x-grid-row { + outline: none; +} +.x-grid-td { + overflow: hidden; + border-width: 0; + vertical-align: top; +} +.x-grid-cell-inner { + overflow: hidden; + white-space: nowrap; +} +.x-wrap-cell .x-grid-cell-inner { + white-space: normal; +} +.x-grid-resize-marker { + position: absolute; + z-index: 5; + top: 0; +} +.x-grid-item-container { + min-height: 1px; + position: relative; +} +.x-col-move-top, +.x-col-move-bottom { + position: absolute; + top: 0; + line-height: 0; + font-size: 0; + overflow: hidden; + z-index: 20000; + background: no-repeat center top transparent; +} +.x-grid-header-ct { + cursor: default; +} +.x-column-header { + position: absolute; + overflow: hidden; + background-repeat: repeat-x; +} +.x-column-header-inner { + white-space: nowrap; + position: relative; + overflow: hidden; +} +.x-leaf-column-header { + height: 100%; +} +.x-leaf-column-header .x-column-header-text-container { + height: 100%; +} +.x-column-header-text-container { + width: 100%; + display: table; + table-layout: fixed; +} +.x-column-header-text-container.x-column-header-text-container-auto { + table-layout: auto; +} +.x-column-header-text-wrapper { + display: table-cell; + vertical-align: middle; +} +.x-column-header-text { + display: block; + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; +} +.x-column-header-sort-DESC .x-column-header-text, +.x-column-header-sort-ASC .x-column-header-text { + overflow: visible; +} +.x-column-header-text-inner { + background-repeat: no-repeat; +} +.x-column-header-inner-empty .x-column-header-text-inner { + display: none; +} +.x-column-header-inner-empty .x-column-header-text-container { + line-height: 0; +} +.x-column-header-trigger { + display: none; + height: 100%; + background-repeat: no-repeat; + position: absolute; + right: 0; + top: 0; + text-align: center; +} +.x-ie9m .x-column-header-trigger { + z-index: 6; +} +.x-column-header-over .x-column-header-trigger, +.x-column-header-open .x-column-header-trigger { + display: block; +} +.x-column-header-align-right { + text-align: right; +} +.x-column-header-align-left { + text-align: left; +} +.x-column-header-align-center { + text-align: center; +} +.x-grid-cell-inner-action-col { + line-height: 0; + font-size: 0; +} +.x-keyboard-mode .x-grid-cell-inner-action-col :focus { + outline: 1px solid #5fa2dd; +} +.x-action-col-icon { + display: inline-block; + line-height: 1; +} +.x-column-header-checkbox .x-column-header-text { + margin-bottom: 0.4em; +} +.x-column-header-checkbox .x-column-header-inner-empty .x-column-header-text { + margin-bottom: 0; +} +.x-grid-checkcolumn-cell-inner { + line-height: 0; +} +.x-keyboard-mode .x-grid-checkcolumn-cell-inner :focus { + outline: 1px solid #5fa2dd; +} +.x-group-hd-container { + overflow: hidden; +} +.x-grid-group-hd { + white-space: nowrap; + outline: none; +} +.x-grid-group-title { + position: relative; +} +.x-grid-group-title:before { + position: absolute; + left: 0; +} +.x-grid-row-body-hidden, +.x-grid-group-collapsed { + display: none; +} +.x-grid-row-body-hidden { + display: none; +} +.x-menu { + outline: none; +} +.x-menu-body { + position: relative; +} +.x-menu-item { + white-space: nowrap; + overflow: hidden; + border-color: transparent; + border-style: solid; +} +.x-menu-item-cmp { + margin: 2px; +} +.x-menu-item-cmp .x-field-label-cell { + vertical-align: middle; +} +.x-menu-icon-separator { + position: absolute; + top: 0px; + z-index: 0; + height: 100%; + overflow: hidden; +} +.x-menu-plain .x-menu-icon-separator { + display: none; +} +.x-menu-item-link { + -webkit-tap-highlight-color: transparent; + -webkit-touch-callout: none; + text-decoration: none; + outline: 0; + display: block; +} +.x-menu-item-link-href { + -webkit-touch-callout: default; +} +.x-menu-item-text { + display: inline-block; +} +.x-menu-item-icon, +.x-menu-item-icon-right, +.x-menu-item-arrow { + font-size: 0; + position: absolute; + text-align: center; + background-repeat: no-repeat; +} +.x-grid-scroll-container { + position: absolute; + z-index: 1; +} +.x-grid-scrollbar-clipper-floated, +.x-grid-scrollbar-floated { + z-index: 2; +} +.x-grid-scroll-body { + width: 100%; + position: relative; +} +.x-grid-scrollbar-clipper { + overflow: hidden; + position: absolute; + top: 0; + left: 0; +} +.x-grid-scrollbar-clipper > .x-grid-view, +.x-grid-scrollbar-clipper > .x-tree-view { + overflow-y: hidden !important; +} +.x-grid-with-col-lines .x-grid-scrollbar-clipper-locked .x-grid-cell-last { + border-right-width: 0; +} +.x-grid-scrollbar { + position: absolute; + bottom: 0; + left: 0; + display: none; +} +.x-grid-scrollbar-visible { + display: block; +} +.x-grid-locking-body > .x-grid { + z-index: 2; + pointer-events: none; +} +.x-grid-locking-body > .x-grid .x-docked { + pointer-events: auto; +} +.x-grid-locking-body .x-grid-body { + background: transparent; +} +.x-grid-locking-body > .x-splitter { + z-index: 2; +} +.x-grid-locking-body > .x-splitter-active { + z-index: 4; +} +.x-grid-locking-body > .x-splitter-focus { + z-index: 4; +} +.x-grid-inner-locked.x-border-region-slide-in { + z-index: 3; +} +.x-grid-inner-locked.x-border-region-slide-in + > .x-panel-bodyWrap + > .x-grid-body + > .x-grid-view, +.x-grid-inner-locked.x-border-region-slide-in + > .x-panel-bodyWrap + > .x-grid-body + > .x-tree-view { + overflow-y: hidden !important; +} +.x-grid-editor .x-form-cb-wrap { + text-align: center; +} +.x-grid-editor .x-form-cb { + position: static; + display: inline-block; +} +.x-grid-editor .x-form-display-field { + margin: 0; + white-space: nowrap; + overflow: hidden; +} +.x-grid-editor div.x-form-action-col-field { + line-height: 0; +} +.x-grid-row-editor-wrap { + position: absolute; + overflow: visible; + z-index: 2; +} +.x-grid-row-editor { + position: absolute; + z-index: 0; +} +.x-grid-row-editor-buttons { + position: absolute; + white-space: nowrap; +} +.x-grid-row-expander { + font-size: 0; + line-height: 0; + text-align: center; +} +.x-keyboard-mode .x-grid-row-expander:focus { + outline: 1px solid #5fa2dd; +} +.x-grid-hide-row-expander-spacer .x-grid-row-expander-spacer { + display: none; +} +.x-grid-row-expander-spacer { + border: 0 none; +} +.x-ssm-row-numberer-hd { + cursor: se-resize !important; +} +.x-ssm-row-numberer-cell { + cursor: e-resize; +} +.x-ssm-column-select .x-column-header { + cursor: s-resize; +} +.x-ssm-extender-drag-handle { + position: absolute; + z-index: 1; + cursor: crosshair; +} +.x-ssm-extender-mask { + position: absolute; + z-index: 1; + pointer-events: none; +} +.x-abs-layout-ct { + position: relative; +} +.x-abs-layout-item { + position: absolute !important; +} +.x-border-layout-ct { + overflow: hidden; +} +.x-border-layout-ct { + position: relative; +} +.x-border-region-slide-in { + z-index: 6; +} +.x-region-collapsed-placeholder { + z-index: 4; +} +.x-center-layout-item { + position: absolute; +} +.x-center-target { + position: relative; +} +.x-form-layout-wrap { + display: table; + width: 100%; + border-collapse: separate; +} +.x-form-layout-colgroup { + display: table-column-group; +} +.x-form-layout-column { + display: table-column; +} +.x-form-layout-auto-label > * > .x-form-item-label { + width: auto !important; +} +.x-form-layout-auto-label > * > .x-form-item-label > .x-form-item-label-inner { + width: auto !important; + white-space: nowrap; +} +.x-form-layout-auto-label > * > .x-form-layout-label-column { + width: 1px; +} +.x-form-layout-sized-label > * > .x-form-item-label { + width: auto !important; +} +.x-form-form-item { + display: table-row; +} +.x-form-form-item > .x-form-item-label { + padding-left: 0 !important; + padding-right: 0 !important; + padding-bottom: 0 !important; +} +.x-form-form-item > .x-form-item-body { + max-width: none; +} +.x-form-form-item.x-form-item-no-label:before { + content: " "; + display: table-cell; + pointer-events: none; +} +.x-resizable-wrapped { + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +.x-slider { + outline: none; + position: relative; +} +.x-slider-inner { + position: relative; + left: 0; + top: 0; + overflow: visible; +} +.x-slider-vert .x-slider-inner { + background: repeat-y 0 0; +} +.x-slider-thumb { + position: absolute; + background: no-repeat 0 0; + cursor: default; + -webkit-user-callout: none; + display: table; + table-layout: fixed; +} +.x-slider-horz .x-slider-thumb { + left: 0; +} +.x-slider-vert .x-slider-thumb { + bottom: 0; +} +.x-slider-thumb:before { + display: table-cell; + vertical-align: middle; + text-align: center; +} +.x-tab { + display: block; + outline: 0; + cursor: pointer; + white-space: nowrap; + text-decoration: none; + vertical-align: top; + overflow: hidden; + position: relative; +} +.x-tab > .x-frame { + height: 100%; + width: 100%; +} +.x-tab-wrap { + height: 100%; + width: 100%; + display: table; + border-spacing: 0; +} +.x-tab-button { + white-space: nowrap; + line-height: 0; + position: relative; + display: table-cell; + vertical-align: middle; +} +.x-tab-inner { + overflow: hidden; + text-overflow: ellipsis; + display: inline-block; + vertical-align: middle; +} +.x-tab-icon.x-tab-no-text > .x-tab-inner { + display: none; +} +.x-tab-icon-el { + display: none; + vertical-align: middle; + text-align: center; + background-position: center center; + background-repeat: no-repeat; +} +.x-tab-icon > .x-tab-icon-el { + display: inline-block; +} +.x-tab-icon-top > .x-tab-icon-el, +.x-tab-icon-bottom > .x-tab-icon-el { + display: block; +} +.x-ie9m .x-tab-button-center { + text-align: center; +} +.x-tab-button-center.x-tab-icon-top, +.x-tab-button-center.x-tab-icon-bottom { + text-align: center; +} +.x-tab-button-left { + text-align: left; +} +.x-tab-button-right { + text-align: right; +} +.x-tab-mc { + overflow: visible; +} +.x-tab { + z-index: 1; +} +.x-tab-active { + z-index: 3; +} +.x-tab-button { + position: relative; +} +.x-tab-close-btn { + display: block; + position: absolute; + overflow: hidden; + font-size: 0; + line-height: 0; +} +.x-tab-rotate-left { + -webkit-transform: rotate(270deg); + -webkit-transform-origin: 100% 0; + -moz-transform: rotate(270deg); + -moz-transform-origin: 100% 0; + -ms-transform: rotate(270deg); + -ms-transform-origin: 100% 0; + transform: rotate(270deg); + transform-origin: 100% 0; +} +.x-ie8 .x-tab-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +.x-tab-rotate-right { + -webkit-transform: rotate(90deg); + -webkit-transform-origin: 0 0; + -moz-transform: rotate(90deg); + -moz-transform-origin: 0 0; + -ms-transform: rotate(90deg); + -ms-transform-origin: 0 0; + transform: rotate(90deg); + transform-origin: 0 0; +} +.x-ie8 .x-tab-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +.x-tab-tr, +.x-tab-br, +.x-tab-mr, +.x-tab-tl, +.x-tab-bl, +.x-tab-ml { + width: 1px; +} +.x-tab-bar { + z-index: 0; + position: relative; +} +.x-tab-bar-strip { + position: absolute; + line-height: 0; + font-size: 0; + z-index: 2; +} +.x-tab-bar-top > .x-tab-bar-strip { + bottom: 0; +} +.x-tab-bar-bottom > .x-tab-bar-strip { + top: 0; +} +.x-tab-bar-left > .x-tab-bar-strip { + right: 0; +} +.x-tab-bar-right > .x-tab-bar-strip { + left: 0; +} +.x-tab-bar-horizontal .x-tab-bar-strip { + width: 100%; + left: 0; +} +.x-tab-bar-vertical { + display: table-cell; +} +.x-tab-bar-vertical .x-tab-bar-strip { + height: 100%; + top: 0; +} +.x-tab-bar-plain { + background: transparent !important; +} +.x-box-scroller-plain { + background-color: transparent !important; +} +.x-breadcrumb-btn .x-box-target:first-child { + margin: 0; +} +.x-breadcrumb-btn > .x-btn-split-right > .x-btn-button:after { + content: none; +} +.x-breadcrumb-btn.x-btn-over > .x-btn-split-right > .x-btn-button:after, +.x-breadcrumb-btn.x-btn-menu-active > .x-btn-split-right > .x-btn-button:after { + content: ""; +} +.x-autowidth-table .x-grid-item-container { + overflow: visible; +} +.x-autowidth-table .x-grid-item { + table-layout: auto; + width: auto !important; +} +.x-tree-view { + overflow: hidden; +} +.x-tree-elbow-img, +.x-tree-icon { + display: inline-block; + text-align: center; + background-repeat: no-repeat; + background-position: 0 center; + vertical-align: top; +} +.x-tree-checkbox { + display: inline-block; + vertical-align: top; + position: relative; +} +.x-tree-animator-wrap { + overflow: hidden; +} +.x-body { + color: #404040; + font-size: 13px; + line-height: 17px; + font-weight: 300; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + background: #f6f6f6; +} +.x-animating-size, +.x-collapsed { + overflow: hidden !important; +} +.x-animating-size { + z-index: 10000; +} +.x-editor .x-form-item-body { + padding-bottom: 0; +} +.x-mask { + background-image: none; + background-color: rgba(208, 208, 208, 0.5); + cursor: default; + border-style: solid; + border-width: 1px; + border-color: transparent; +} +.x-ie8 .x-mask { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#80d0d0d0, endColorstr=#80d0d0d0)"; + zoom: 1; +} +body > .x-mask { + background-image: none; + background-color: rgba(0, 0, 0, 0.75); +} +.x-ie8 body > .x-mask { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#bf000000, endColorstr=#bf000000)"; + zoom: 1; +} +.x-keyboard-mode .x-mask.x-focus { + border-style: solid; + border-width: 1px; + border-color: #5fa2dd; +} +.x-mask-msg { + padding: 10px; + background: #d0d0d0; +} +.x-mask-msg-inner { + padding: 0; + background-color: transparent; + color: #404040; + font: 300 13px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; +} +.x-mask-msg-text { + padding: 25px 0 0; + background-image: url(images/loadmask/loading.gif); + background-repeat: no-repeat; + background-position: center 0; +} +.x-progress-default { + background-color: #ececec; + border-width: 0; + height: 24px; + border-color: #5fa2dd; + border-style: solid; +} +.x-progress-default .x-progress-bar-default { + background-image: none; + background-color: #7fb5e4; +} +.x-progress-default .x-progress-text { + color: #fff; + font-weight: 400; + font-size: 13px; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + text-align: center; + line-height: 24px; +} +.x-progress-default .x-progress-text-back { + color: #404040; + line-height: 24px; +} +.x-keyboard-mode .x-progress-default.x-progress-focus:after { + position: absolute; + content: " "; + top: 0; + right: 0; + bottom: 0; + left: 0; + border: 0 solid #5fa2dd; + pointer-events: none; +} +.x-progressbar-default-cell > .x-grid-cell-inner, +.x-progress-default-cell > .x-grid-cell-inner, +.x-progressbarwidget-default-cell > .x-grid-cell-inner { + padding-top: 4px; + padding-bottom: 4px; +} +.x-progressbar-default-cell > .x-grid-cell-inner .x-progress-default, +.x-progress-default-cell > .x-grid-cell-inner .x-progress-default, +.x-progressbarwidget-default-cell > .x-grid-cell-inner .x-progress-default { + height: 24px; +} +.x-btn-default-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #5fa2dd; +} +.x-btn-default-small-mc { + background-color: #5fa2dd; +} +.x-nbr .x-btn-default-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-default-small-tl { + background-position: 0 -2px; +} +.x-btn-default-small-tr { + background-position: right -3px; +} +.x-btn-default-small-bl { + background-position: 0 -4px; +} +.x-btn-default-small-br { + background-position: right -5px; +} +.x-btn-default-small-ml { + background-position: 0 top; +} +.x-btn-default-small-mr { + background-position: right top; +} +.x-btn-default-small-tc { + background-position: 0 0; +} +.x-btn-default-small-bc { + background-position: 0 -1px; +} +.x-btn-default-small-tr, +.x-btn-default-small-br, +.x-btn-default-small-mr { + padding-right: 1px; +} +.x-btn-default-small-tl, +.x-btn-default-small-bl, +.x-btn-default-small-ml { + padding-left: 1px; +} +.x-btn-default-small-tc { + height: 1px; +} +.x-btn-default-small-bc { + height: 1px; +} +.x-btn-default-small-tl, +.x-btn-default-small-bl, +.x-btn-default-small-tr, +.x-btn-default-small-br, +.x-btn-default-small-tc, +.x-btn-default-small-bc, +.x-btn-default-small-ml, +.x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-corners.gif); +} +.x-btn-default-small-ml, +.x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-default-small { + border-color: #5897ce; +} +.x-btn-button-default-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-default-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-default-small { + font: 400 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-default-small { + max-width: none; +} +.x-btn-icon-el-default-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-default-small, +.x-btn-icon-right > .x-btn-icon-el-default-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-default-small, +.x-btn-icon-bottom > .x-btn-icon-el-default-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-default-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-default-small, +.x-btn-split-bottom > .x-btn-button-default-small { + padding-bottom: 7px; +} +.x-btn-wrap-default-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-default-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-default-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-default-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-default-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-default-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-small { + background-image: none; + background-color: #5fa2dd; + -webkit-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, + #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + -moz-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, + #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, + #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; +} +.x-btn-default-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #d3e0ec; +} +.x-btn-over.x-btn-default-small { + border-color: #518bbd; + background-image: none; + background-color: #5795cb; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-small { + -webkit-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, + #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + -moz-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, + #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, + #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-small, +.x-btn.x-btn-pressed.x-btn-default-small { + border-color: #42719a; + background-image: none; + background-color: #477aa6; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-small { + -webkit-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, + #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + -moz-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, + #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, + #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-small { + background-image: none; + background-color: #5fa2dd; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-small-mc { + background-color: #5fa2dd; +} +.x-btn-over .x-btn-default-small-tl, +.x-btn-over .x-btn-default-small-bl, +.x-btn-over .x-btn-default-small-tr, +.x-btn-over .x-btn-default-small-br, +.x-btn-over .x-btn-default-small-tc, +.x-btn-over .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-over-corners.gif); +} +.x-btn-over .x-btn-default-small-ml, +.x-btn-over .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-over-sides.gif); +} +.x-btn-over .x-btn-default-small-mc { + background-color: #5795cb; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-small-mc { + background-color: #5795cb; +} +.x-btn.x-btn-menu-active .x-btn-default-small-tl, +.x-btn.x-btn-menu-active .x-btn-default-small-bl, +.x-btn.x-btn-menu-active .x-btn-default-small-tr, +.x-btn.x-btn-menu-active .x-btn-default-small-br, +.x-btn.x-btn-menu-active .x-btn-default-small-tc, +.x-btn.x-btn-menu-active .x-btn-default-small-bc, +.x-btn.x-btn-pressed .x-btn-default-small-tl, +.x-btn.x-btn-pressed .x-btn-default-small-bl, +.x-btn.x-btn-pressed .x-btn-default-small-tr, +.x-btn.x-btn-pressed .x-btn-default-small-br, +.x-btn.x-btn-pressed .x-btn-default-small-tc, +.x-btn.x-btn-pressed .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-small-ml, +.x-btn.x-btn-menu-active .x-btn-default-small-mr, +.x-btn.x-btn-pressed .x-btn-default-small-ml, +.x-btn.x-btn-pressed .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-small-mc, +.x-btn.x-btn-pressed .x-btn-default-small-mc { + background-color: #477aa6; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-small-mc { + background-color: #477aa6; +} +.x-btn.x-btn-disabled .x-btn-default-small-tl, +.x-btn.x-btn-disabled .x-btn-default-small-bl, +.x-btn.x-btn-disabled .x-btn-default-small-tr, +.x-btn.x-btn-disabled .x-btn-default-small-br, +.x-btn.x-btn-disabled .x-btn-default-small-tc, +.x-btn.x-btn-disabled .x-btn-default-small-bc { + background-image: url(images/btn/btn-default-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-small-ml, +.x-btn.x-btn-disabled .x-btn-default-small-mr { + background-image: url(images/btn/btn-default-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-small-mc { + background-color: #5fa2dd; +} +.x-nbr .x-btn-default-small { + background-image: none; +} +.x-btn-disabled.x-btn-default-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first + .x-btn-default-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-middle + .x-btn-default-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last + .x-btn-default-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first + .x-btn-default-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-middle + .x-btn-default-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last + .x-btn-default-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-small:after { + border-width: 1px; + border-color: #d3e0ec; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-small:after { + border-width: 1px; + border-color: #d1dee9; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-small:after { + border-width: 1px; + border-color: #ced8e1; +} +.x-button-default-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +.x-button-default-small-cell > .x-grid-cell-inner > .x-btn-default-small { + vertical-align: top; +} +.x-btn-default-medium { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 8px 8px 8px; + border-width: 1px; + border-style: solid; + background-color: #5fa2dd; +} +.x-btn-default-medium-mc { + background-color: #5fa2dd; +} +.x-nbr .x-btn-default-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-medium-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-8-8-8-8; +} +.x-btn-default-medium-tl { + background-position: 0 -2px; +} +.x-btn-default-medium-tr { + background-position: right -3px; +} +.x-btn-default-medium-bl { + background-position: 0 -4px; +} +.x-btn-default-medium-br { + background-position: right -5px; +} +.x-btn-default-medium-ml { + background-position: 0 top; +} +.x-btn-default-medium-mr { + background-position: right top; +} +.x-btn-default-medium-tc { + background-position: 0 0; +} +.x-btn-default-medium-bc { + background-position: 0 -1px; +} +.x-btn-default-medium-tr, +.x-btn-default-medium-br, +.x-btn-default-medium-mr { + padding-right: 1px; +} +.x-btn-default-medium-tl, +.x-btn-default-medium-bl, +.x-btn-default-medium-ml { + padding-left: 1px; +} +.x-btn-default-medium-tc { + height: 1px; +} +.x-btn-default-medium-bc { + height: 1px; +} +.x-btn-default-medium-tl, +.x-btn-default-medium-bl, +.x-btn-default-medium-tr, +.x-btn-default-medium-br, +.x-btn-default-medium-tc, +.x-btn-default-medium-bc, +.x-btn-default-medium-ml, +.x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-corners.gif); +} +.x-btn-default-medium-ml, +.x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-medium-mc { + padding: 8px 8px 8px 8px; +} +.x-btn-default-medium { + border-color: #5897ce; +} +.x-btn-button-default-medium { + min-height: 20px; +} +.x-ie9m .x-btn-button-default-medium { + min-height: auto; + height: 20px; +} +.x-btn-inner-default-medium { + font: 400 14px/18px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 8px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-medium { + max-width: calc(100% - 20px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-medium { + max-width: calc(100% - 19px); +} +.x-ie10p .x-btn-inner-default-medium { + max-width: none; +} +.x-btn-icon-el-default-medium { + font-size: 20px; + height: 20px; + color: #f0f0f0; + line-height: 20px; +} +.x-btn-icon-left > .x-btn-icon-el-default-medium, +.x-btn-icon-right > .x-btn-icon-el-default-medium { + width: 20px; +} +.x-btn-icon-top > .x-btn-icon-el-default-medium, +.x-btn-icon-bottom > .x-btn-icon-el-default-medium { + min-width: 20px; +} +.x-ie8 .x-btn-icon-el-default-medium.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-medium { + margin-right: 0px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-medium { + margin-left: 0px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-medium { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-medium { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-medium { + margin-right: 8px; +} +.x-btn-arrow-bottom > .x-btn-button-default-medium, +.x-btn-split-bottom > .x-btn-button-default-medium { + padding-bottom: 8px; +} +.x-btn-wrap-default-medium.x-btn-arrow-right:after { + width: 20px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-medium.x-btn-arrow-bottom:after { + height: 14px; + content: "\f0d7"; + font: 20px/14px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-medium.x-btn-split-right > .x-btn-button { + padding-right: 8px; +} +.x-btn-wrap-default-medium.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-default-medium.x-btn-split-right:after { + width: 26px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #f0f0f0; + padding-left: 8px; +} +.x-btn-wrap-default-medium.x-btn-split-bottom { + margin-bottom: -8px; +} +.x-btn-wrap-default-medium.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-default-medium.x-btn-split-bottom:after { + height: 24px; + content: "\f0d7"; + font: 20px/24px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-medium { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-medium { + margin-right: 8px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-medium { + background-image: none; + background-color: #5fa2dd; + -webkit-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, + #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + -moz-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, + #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, + #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; +} +.x-btn-default-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 34px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #d3e0ec; +} +.x-btn-over.x-btn-default-medium { + border-color: #518bbd; + background-image: none; + background-color: #5795cb; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-medium { + -webkit-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, + #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + -moz-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, + #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, + #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-medium, +.x-btn.x-btn-pressed.x-btn-default-medium { + border-color: #42719a; + background-image: none; + background-color: #477aa6; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-medium { + -webkit-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, + #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + -moz-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, + #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, + #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-medium { + background-image: none; + background-color: #5fa2dd; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-medium-mc { + background-color: #5fa2dd; +} +.x-btn-over .x-btn-default-medium-tl, +.x-btn-over .x-btn-default-medium-bl, +.x-btn-over .x-btn-default-medium-tr, +.x-btn-over .x-btn-default-medium-br, +.x-btn-over .x-btn-default-medium-tc, +.x-btn-over .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-over-corners.gif); +} +.x-btn-over .x-btn-default-medium-ml, +.x-btn-over .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-over-sides.gif); +} +.x-btn-over .x-btn-default-medium-mc { + background-color: #5795cb; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-medium-mc { + background-color: #5795cb; +} +.x-btn.x-btn-menu-active .x-btn-default-medium-tl, +.x-btn.x-btn-menu-active .x-btn-default-medium-bl, +.x-btn.x-btn-menu-active .x-btn-default-medium-tr, +.x-btn.x-btn-menu-active .x-btn-default-medium-br, +.x-btn.x-btn-menu-active .x-btn-default-medium-tc, +.x-btn.x-btn-menu-active .x-btn-default-medium-bc, +.x-btn.x-btn-pressed .x-btn-default-medium-tl, +.x-btn.x-btn-pressed .x-btn-default-medium-bl, +.x-btn.x-btn-pressed .x-btn-default-medium-tr, +.x-btn.x-btn-pressed .x-btn-default-medium-br, +.x-btn.x-btn-pressed .x-btn-default-medium-tc, +.x-btn.x-btn-pressed .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-medium-ml, +.x-btn.x-btn-menu-active .x-btn-default-medium-mr, +.x-btn.x-btn-pressed .x-btn-default-medium-ml, +.x-btn.x-btn-pressed .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-medium-mc, +.x-btn.x-btn-pressed .x-btn-default-medium-mc { + background-color: #477aa6; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-medium-mc { + background-color: #477aa6; +} +.x-btn.x-btn-disabled .x-btn-default-medium-tl, +.x-btn.x-btn-disabled .x-btn-default-medium-bl, +.x-btn.x-btn-disabled .x-btn-default-medium-tr, +.x-btn.x-btn-disabled .x-btn-default-medium-br, +.x-btn.x-btn-disabled .x-btn-default-medium-tc, +.x-btn.x-btn-disabled .x-btn-default-medium-bc { + background-image: url(images/btn/btn-default-medium-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-medium-ml, +.x-btn.x-btn-disabled .x-btn-default-medium-mr { + background-image: url(images/btn/btn-default-medium-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-medium-mc { + background-color: #5fa2dd; +} +.x-nbr .x-btn-default-medium { + background-image: none; +} +.x-btn-disabled.x-btn-default-medium { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first + .x-btn-default-medium-mc { + padding-right: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-middle + .x-btn-default-medium-mc { + padding-right: 8px !important; + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last + .x-btn-default-medium-mc { + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first + .x-btn-default-medium-mc { + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-middle + .x-btn-default-medium-mc { + padding-top: 8px !important; + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last + .x-btn-default-medium-mc { + padding-top: 8px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-medium:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-medium.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-medium.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-medium:after { + border-width: 1px; + border-color: #d3e0ec; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-medium:after { + border-width: 1px; + border-color: #d1dee9; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-medium:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-medium:after { + border-width: 1px; + border-color: #ced8e1; +} +.x-button-default-medium-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +.x-button-default-medium-cell > .x-grid-cell-inner > .x-btn-default-medium { + vertical-align: top; +} +.x-btn-default-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #5fa2dd; +} +.x-btn-default-large-mc { + background-color: #5fa2dd; +} +.x-nbr .x-btn-default-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +.x-btn-default-large-tl { + background-position: 0 -2px; +} +.x-btn-default-large-tr { + background-position: right -3px; +} +.x-btn-default-large-bl { + background-position: 0 -4px; +} +.x-btn-default-large-br { + background-position: right -5px; +} +.x-btn-default-large-ml { + background-position: 0 top; +} +.x-btn-default-large-mr { + background-position: right top; +} +.x-btn-default-large-tc { + background-position: 0 0; +} +.x-btn-default-large-bc { + background-position: 0 -1px; +} +.x-btn-default-large-tr, +.x-btn-default-large-br, +.x-btn-default-large-mr { + padding-right: 1px; +} +.x-btn-default-large-tl, +.x-btn-default-large-bl, +.x-btn-default-large-ml { + padding-left: 1px; +} +.x-btn-default-large-tc { + height: 1px; +} +.x-btn-default-large-bc { + height: 1px; +} +.x-btn-default-large-tl, +.x-btn-default-large-bl, +.x-btn-default-large-tr, +.x-btn-default-large-br, +.x-btn-default-large-tc, +.x-btn-default-large-bc, +.x-btn-default-large-ml, +.x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-corners.gif); +} +.x-btn-default-large-ml, +.x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-large-mc { + padding: 9px 9px 9px 9px; +} +.x-btn-default-large { + border-color: #5897ce; +} +.x-btn-button-default-large { + min-height: 24px; +} +.x-ie9m .x-btn-button-default-large { + min-height: auto; + height: 24px; +} +.x-btn-inner-default-large { + font: 400 16px/20px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 10px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-large { + max-width: calc(100% - 24px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-large { + max-width: calc(100% - 23px); +} +.x-ie10p .x-btn-inner-default-large { + max-width: none; +} +.x-btn-icon-el-default-large { + font-size: 24px; + height: 24px; + color: #f0f0f0; + line-height: 24px; +} +.x-btn-icon-left > .x-btn-icon-el-default-large, +.x-btn-icon-right > .x-btn-icon-el-default-large { + width: 24px; +} +.x-btn-icon-top > .x-btn-icon-el-default-large, +.x-btn-icon-bottom > .x-btn-icon-el-default-large { + min-width: 24px; +} +.x-ie8 .x-btn-icon-el-default-large.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-large { + margin-right: 0; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-large { + margin-left: 0; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-large { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-large { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-large { + margin-right: 10px; +} +.x-btn-arrow-bottom > .x-btn-button-default-large, +.x-btn-split-bottom > .x-btn-button-default-large { + padding-bottom: 9px; +} +.x-btn-wrap-default-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-default-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +.x-btn-wrap-default-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-default-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #f0f0f0; + padding-left: 9px; +} +.x-btn-wrap-default-large.x-btn-split-bottom { + margin-bottom: -9px; +} +.x-btn-wrap-default-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-default-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-default-large { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-large { + margin-right: 10px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-large { + background-image: none; + background-color: #5fa2dd; + -webkit-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, + #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + -moz-box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, + #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; + box-shadow: #d3e0ec 0 1px 0px 0 inset, #d3e0ec 0 -1px 0px 0 inset, + #d3e0ec -1px 0 0px 0 inset, #d3e0ec 1px 0 0px 0 inset; +} +.x-btn-default-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #d3e0ec; +} +.x-btn-over.x-btn-default-large { + border-color: #518bbd; + background-image: none; + background-color: #5795cb; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-large { + -webkit-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, + #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + -moz-box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, + #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; + box-shadow: #d1dee9 0 1px 0px 0 inset, #d1dee9 0 -1px 0px 0 inset, + #d1dee9 -1px 0 0px 0 inset, #d1dee9 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-large, +.x-btn.x-btn-pressed.x-btn-default-large { + border-color: #42719a; + background-image: none; + background-color: #477aa6; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-large { + -webkit-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, + #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + -moz-box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, + #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; + box-shadow: #ced8e1 0 1px 0px 0 inset, #ced8e1 0 -1px 0px 0 inset, + #ced8e1 -1px 0 0px 0 inset, #ced8e1 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-large { + background-image: none; + background-color: #5fa2dd; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-large-mc { + background-color: #5fa2dd; +} +.x-btn-over .x-btn-default-large-tl, +.x-btn-over .x-btn-default-large-bl, +.x-btn-over .x-btn-default-large-tr, +.x-btn-over .x-btn-default-large-br, +.x-btn-over .x-btn-default-large-tc, +.x-btn-over .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-over-corners.gif); +} +.x-btn-over .x-btn-default-large-ml, +.x-btn-over .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-over-sides.gif); +} +.x-btn-over .x-btn-default-large-mc { + background-color: #5795cb; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-large-mc { + background-color: #5795cb; +} +.x-btn.x-btn-menu-active .x-btn-default-large-tl, +.x-btn.x-btn-menu-active .x-btn-default-large-bl, +.x-btn.x-btn-menu-active .x-btn-default-large-tr, +.x-btn.x-btn-menu-active .x-btn-default-large-br, +.x-btn.x-btn-menu-active .x-btn-default-large-tc, +.x-btn.x-btn-menu-active .x-btn-default-large-bc, +.x-btn.x-btn-pressed .x-btn-default-large-tl, +.x-btn.x-btn-pressed .x-btn-default-large-bl, +.x-btn.x-btn-pressed .x-btn-default-large-tr, +.x-btn.x-btn-pressed .x-btn-default-large-br, +.x-btn.x-btn-pressed .x-btn-default-large-tc, +.x-btn.x-btn-pressed .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-large-ml, +.x-btn.x-btn-menu-active .x-btn-default-large-mr, +.x-btn.x-btn-pressed .x-btn-default-large-ml, +.x-btn.x-btn-pressed .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-large-mc, +.x-btn.x-btn-pressed .x-btn-default-large-mc { + background-color: #477aa6; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-large-mc { + background-color: #477aa6; +} +.x-btn.x-btn-disabled .x-btn-default-large-tl, +.x-btn.x-btn-disabled .x-btn-default-large-bl, +.x-btn.x-btn-disabled .x-btn-default-large-tr, +.x-btn.x-btn-disabled .x-btn-default-large-br, +.x-btn.x-btn-disabled .x-btn-default-large-tc, +.x-btn.x-btn-disabled .x-btn-default-large-bc { + background-image: url(images/btn/btn-default-large-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-large-ml, +.x-btn.x-btn-disabled .x-btn-default-large-mr { + background-image: url(images/btn/btn-default-large-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-large-mc { + background-color: #5fa2dd; +} +.x-nbr .x-btn-default-large { + background-image: none; +} +.x-btn-disabled.x-btn-default-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first + .x-btn-default-large-mc { + padding-right: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-middle + .x-btn-default-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last + .x-btn-default-large-mc { + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first + .x-btn-default-large-mc { + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-middle + .x-btn-default-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last + .x-btn-default-large-mc { + padding-top: 9px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-large:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-large.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-large.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-large:after { + border-width: 1px; + border-color: #d3e0ec; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-large:after { + border-width: 1px; + border-color: #d1dee9; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-large:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-large:after { + border-width: 1px; + border-color: #ced8e1; +} +.x-button-default-large-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +.x-button-default-large-cell > .x-grid-cell-inner > .x-btn-default-large { + vertical-align: top; +} +.x-btn-default-toolbar-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #f6f6f6; +} +.x-btn-default-toolbar-small-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-toolbar-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-default-toolbar-small-tl { + background-position: 0 -2px; +} +.x-btn-default-toolbar-small-tr { + background-position: right -3px; +} +.x-btn-default-toolbar-small-bl { + background-position: 0 -4px; +} +.x-btn-default-toolbar-small-br { + background-position: right -5px; +} +.x-btn-default-toolbar-small-ml { + background-position: 0 top; +} +.x-btn-default-toolbar-small-mr { + background-position: right top; +} +.x-btn-default-toolbar-small-tc { + background-position: 0 0; +} +.x-btn-default-toolbar-small-bc { + background-position: 0 -1px; +} +.x-btn-default-toolbar-small-tr, +.x-btn-default-toolbar-small-br, +.x-btn-default-toolbar-small-mr { + padding-right: 1px; +} +.x-btn-default-toolbar-small-tl, +.x-btn-default-toolbar-small-bl, +.x-btn-default-toolbar-small-ml { + padding-left: 1px; +} +.x-btn-default-toolbar-small-tc { + height: 1px; +} +.x-btn-default-toolbar-small-bc { + height: 1px; +} +.x-btn-default-toolbar-small-tl, +.x-btn-default-toolbar-small-bl, +.x-btn-default-toolbar-small-tr, +.x-btn-default-toolbar-small-br, +.x-btn-default-toolbar-small-tc, +.x-btn-default-toolbar-small-bc, +.x-btn-default-toolbar-small-ml, +.x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-corners.gif); +} +.x-btn-default-toolbar-small-ml, +.x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-toolbar-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-default-toolbar-small { + border-color: #e4e4e4; +} +.x-btn-button-default-toolbar-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-default-toolbar-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-default-toolbar-small { + font: 400 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #606060; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-default-toolbar-small { + max-width: none; +} +.x-btn-icon-el-default-toolbar-small { + font-size: 16px; + height: 16px; + color: #919191; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-default-toolbar-small.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-small { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-small, +.x-btn-split-bottom > .x-btn-button-default-toolbar-small { + padding-bottom: 7px; +} +.x-btn-wrap-default-toolbar-small.x-btn-arrow-right:after { + width: 18px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-small.x-btn-arrow-bottom:after { + height: 12px; + content: "\f0d7"; + font: 16px/12px FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-right:after { + width: 20px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #606060; + padding-left: 7px; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-small.x-btn-split-bottom:after { + height: 20px; + content: "\f0d7"; + font: 16px/20px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-small { + background-image: none; + background-color: #f6f6f6; + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +.x-btn-default-toolbar-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 27px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-toolbar-small.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5fa2dd; +} +.x-btn-over.x-btn-default-toolbar-small { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-small { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-toolbar-small, +.x-btn.x-btn-pressed.x-btn-default-toolbar-small { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-toolbar-small { + background-image: none; + background-color: #f6f6f6; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-small-mc { + background-color: #f6f6f6; +} +.x-btn-over .x-btn-default-toolbar-small-tl, +.x-btn-over .x-btn-default-toolbar-small-bl, +.x-btn-over .x-btn-default-toolbar-small-tr, +.x-btn-over .x-btn-default-toolbar-small-br, +.x-btn-over .x-btn-default-toolbar-small-tc, +.x-btn-over .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-over-corners.gif); +} +.x-btn-over .x-btn-default-toolbar-small-ml, +.x-btn-over .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-over-sides.gif); +} +.x-btn-over .x-btn-default-toolbar-small-mc { + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-small-mc { + background-color: #ececec; +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-small-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-small-mc { + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-small-mc { + background-color: #e2e2e2; +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-bc { + background-image: url(images/btn/btn-default-toolbar-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mr { + background-image: url(images/btn/btn-default-toolbar-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-small-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-small { + background-image: none; +} +.x-btn-disabled.x-btn-default-toolbar-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first + .x-btn-default-toolbar-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-middle + .x-btn-default-toolbar-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last + .x-btn-default-toolbar-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first + .x-btn-default-toolbar-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-middle + .x-btn-default-toolbar-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last + .x-btn-default-toolbar-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #5fa2dd; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #5fa2dd; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-small:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-small:after { + border-width: 1px; + border-color: #5fa2dd; +} +.x-button-default-toolbar-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +.x-button-default-toolbar-small-cell + > .x-grid-cell-inner + > .x-btn-default-toolbar-small { + vertical-align: top; +} +.x-btn-default-toolbar-medium { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 8px 8px 8px; + border-width: 1px; + border-style: solid; + background-color: #f6f6f6; +} +.x-btn-default-toolbar-medium-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-medium { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-toolbar-medium-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-8-8-8-8; +} +.x-btn-default-toolbar-medium-tl { + background-position: 0 -2px; +} +.x-btn-default-toolbar-medium-tr { + background-position: right -3px; +} +.x-btn-default-toolbar-medium-bl { + background-position: 0 -4px; +} +.x-btn-default-toolbar-medium-br { + background-position: right -5px; +} +.x-btn-default-toolbar-medium-ml { + background-position: 0 top; +} +.x-btn-default-toolbar-medium-mr { + background-position: right top; +} +.x-btn-default-toolbar-medium-tc { + background-position: 0 0; +} +.x-btn-default-toolbar-medium-bc { + background-position: 0 -1px; +} +.x-btn-default-toolbar-medium-tr, +.x-btn-default-toolbar-medium-br, +.x-btn-default-toolbar-medium-mr { + padding-right: 1px; +} +.x-btn-default-toolbar-medium-tl, +.x-btn-default-toolbar-medium-bl, +.x-btn-default-toolbar-medium-ml { + padding-left: 1px; +} +.x-btn-default-toolbar-medium-tc { + height: 1px; +} +.x-btn-default-toolbar-medium-bc { + height: 1px; +} +.x-btn-default-toolbar-medium-tl, +.x-btn-default-toolbar-medium-bl, +.x-btn-default-toolbar-medium-tr, +.x-btn-default-toolbar-medium-br, +.x-btn-default-toolbar-medium-tc, +.x-btn-default-toolbar-medium-bc, +.x-btn-default-toolbar-medium-ml, +.x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-corners.gif); +} +.x-btn-default-toolbar-medium-ml, +.x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-toolbar-medium-mc { + padding: 8px 8px 8px 8px; +} +.x-btn-default-toolbar-medium { + border-color: #e4e4e4; +} +.x-btn-button-default-toolbar-medium { + min-height: 20px; +} +.x-ie9m .x-btn-button-default-toolbar-medium { + min-height: auto; + height: 20px; +} +.x-btn-inner-default-toolbar-medium { + font: 400 14px/18px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #606060; + padding: 0 8px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-medium, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-medium { + max-width: calc(100% - 20px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-medium, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-medium { + max-width: calc(100% - 19px); +} +.x-ie10p .x-btn-inner-default-toolbar-medium { + max-width: none; +} +.x-btn-icon-el-default-toolbar-medium { + font-size: 20px; + height: 20px; + color: #919191; + line-height: 20px; +} +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + width: 20px; +} +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium { + min-width: 20px; +} +.x-ie8 .x-btn-icon-el-default-toolbar-medium.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-medium { + margin-right: 0px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-medium { + margin-left: 0px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-medium { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-medium { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-medium { + margin-right: 8px; +} +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-medium, +.x-btn-split-bottom > .x-btn-button-default-toolbar-medium { + padding-bottom: 8px; +} +.x-btn-wrap-default-toolbar-medium.x-btn-arrow-right:after { + width: 20px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-medium.x-btn-arrow-bottom:after { + height: 14px; + content: "\f0d7"; + font: 20px/14px FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-right > .x-btn-button { + padding-right: 8px; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-right:after { + width: 26px; + content: "\f0d7"; + font: 20px/1 FontAwesome; + color: #606060; + padding-left: 8px; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom { + margin-bottom: -8px; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-medium.x-btn-split-bottom:after { + height: 24px; + content: "\f0d7"; + font: 20px/24px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-medium { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-medium { + margin-right: 8px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-medium { + background-image: none; + background-color: #f6f6f6; + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +.x-btn-default-toolbar-medium .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 34px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-toolbar-medium.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5fa2dd; +} +.x-btn-over.x-btn-default-toolbar-medium { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-medium { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-toolbar-medium, +.x-btn.x-btn-pressed.x-btn-default-toolbar-medium { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-toolbar-medium { + background-image: none; + background-color: #f6f6f6; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-medium-mc { + background-color: #f6f6f6; +} +.x-btn-over .x-btn-default-toolbar-medium-tl, +.x-btn-over .x-btn-default-toolbar-medium-bl, +.x-btn-over .x-btn-default-toolbar-medium-tr, +.x-btn-over .x-btn-default-toolbar-medium-br, +.x-btn-over .x-btn-default-toolbar-medium-tc, +.x-btn-over .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-over-corners.gif); +} +.x-btn-over .x-btn-default-toolbar-medium-ml, +.x-btn-over .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-over-sides.gif); +} +.x-btn-over .x-btn-default-toolbar-medium-mc { + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-medium-mc { + background-color: #ececec; +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-medium-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-medium-mc { + background-color: #e2e2e2; +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-br, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-focus-pressed-corners.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-focus-pressed-sides.gif); +} +.x-keyboard-mode + .x-btn-focus.x-btn-menu-active + .x-btn-default-toolbar-medium-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-medium-mc { + background-color: #e2e2e2; +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-bc { + background-image: url(images/btn/btn-default-toolbar-medium-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mr { + background-image: url(images/btn/btn-default-toolbar-medium-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-medium-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-medium { + background-image: none; +} +.x-btn-disabled.x-btn-default-toolbar-medium { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first + .x-btn-default-toolbar-medium-mc { + padding-right: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-middle + .x-btn-default-toolbar-medium-mc { + padding-right: 8px !important; + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last + .x-btn-default-toolbar-medium-mc { + padding-left: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first + .x-btn-default-toolbar-medium-mc { + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-middle + .x-btn-default-toolbar-medium-mc { + padding-top: 8px !important; + padding-bottom: 8px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last + .x-btn-default-toolbar-medium-mc { + padding-top: 8px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-medium:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-medium.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-medium:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-medium.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #5fa2dd; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #5fa2dd; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-medium:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-medium:after { + border-width: 1px; + border-color: #5fa2dd; +} +.x-button-default-toolbar-medium-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +.x-button-default-toolbar-medium-cell + > .x-grid-cell-inner + > .x-btn-default-toolbar-medium { + vertical-align: top; +} +.x-btn-default-toolbar-large { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 9px 9px 9px 9px; + border-width: 1px; + border-style: solid; + background-color: #f6f6f6; +} +.x-btn-default-toolbar-large-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-large { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-default-toolbar-large-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-9-9-9-9; +} +.x-btn-default-toolbar-large-tl { + background-position: 0 -2px; +} +.x-btn-default-toolbar-large-tr { + background-position: right -3px; +} +.x-btn-default-toolbar-large-bl { + background-position: 0 -4px; +} +.x-btn-default-toolbar-large-br { + background-position: right -5px; +} +.x-btn-default-toolbar-large-ml { + background-position: 0 top; +} +.x-btn-default-toolbar-large-mr { + background-position: right top; +} +.x-btn-default-toolbar-large-tc { + background-position: 0 0; +} +.x-btn-default-toolbar-large-bc { + background-position: 0 -1px; +} +.x-btn-default-toolbar-large-tr, +.x-btn-default-toolbar-large-br, +.x-btn-default-toolbar-large-mr { + padding-right: 1px; +} +.x-btn-default-toolbar-large-tl, +.x-btn-default-toolbar-large-bl, +.x-btn-default-toolbar-large-ml { + padding-left: 1px; +} +.x-btn-default-toolbar-large-tc { + height: 1px; +} +.x-btn-default-toolbar-large-bc { + height: 1px; +} +.x-btn-default-toolbar-large-tl, +.x-btn-default-toolbar-large-bl, +.x-btn-default-toolbar-large-tr, +.x-btn-default-toolbar-large-br, +.x-btn-default-toolbar-large-tc, +.x-btn-default-toolbar-large-bc, +.x-btn-default-toolbar-large-ml, +.x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-corners.gif); +} +.x-btn-default-toolbar-large-ml, +.x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-sides.gif); + background-repeat: repeat-y; +} +.x-btn-default-toolbar-large-mc { + padding: 9px 9px 9px 9px; +} +.x-btn-default-toolbar-large { + border-color: #e4e4e4; +} +.x-btn-button-default-toolbar-large { + min-height: 24px; +} +.x-ie9m .x-btn-button-default-toolbar-large { + min-height: auto; + height: 24px; +} +.x-btn-inner-default-toolbar-large { + font: 400 16px/20px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #606060; + padding: 0 10px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-default-toolbar-large, +.x-ie9 .x-btn-icon-left > .x-btn-inner-default-toolbar-large { + max-width: calc(100% - 24px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-default-toolbar-large, +.x-safari8m .x-btn-icon-left > .x-btn-inner-default-toolbar-large { + max-width: calc(100% - 23px); +} +.x-ie10p .x-btn-inner-default-toolbar-large { + max-width: none; +} +.x-btn-icon-el-default-toolbar-large { + font-size: 24px; + height: 24px; + color: #919191; + line-height: 24px; +} +.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large, +.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + width: 24px; +} +.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large, +.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large { + min-width: 24px; +} +.x-ie8 .x-btn-icon-el-default-toolbar-large.x-btn-glyph { + color: #919191; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-default-toolbar-large { + margin-right: 0; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-default-toolbar-large { + margin-left: 0; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-default-toolbar-large { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-default-toolbar-large { + margin-top: 8px; +} +.x-btn-arrow-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-large { + margin-right: 10px; +} +.x-btn-arrow-bottom > .x-btn-button-default-toolbar-large, +.x-btn-split-bottom > .x-btn-button-default-toolbar-large { + padding-bottom: 9px; +} +.x-btn-wrap-default-toolbar-large.x-btn-arrow-right:after { + width: 22px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-large.x-btn-arrow-bottom:after { + height: 16px; + content: "\f0d7"; + font: 24px/16px FontAwesome; + color: #606060; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-right > .x-btn-button { + padding-right: 9px; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-right:after { + width: 32px; + content: "\f0d7"; + font: 24px/1 FontAwesome; + color: #606060; + padding-left: 9px; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom { + margin-bottom: -9px; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #e4e4e4; +} +.x-btn-wrap-default-toolbar-large.x-btn-split-bottom:after { + height: 28px; + content: "\f0d7"; + font: 24px/28px FontAwesome; + color: #606060; +} +.x-btn-split-right + > .x-btn-icon.x-btn-no-text.x-btn-button-default-toolbar-large { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-default-toolbar-large { + margin-right: 10px; +} +.x-keyboard-mode .x-btn-focus.x-btn-default-toolbar-large { + background-image: none; + background-color: #f6f6f6; + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +.x-btn-default-toolbar-large .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 41px; + pointer-events: none; +} +.x-keyboard-mode .x-btn-default-toolbar-large.x-arrow-focus .x-btn-arrow-el { + border: 1px solid #5fa2dd; +} +.x-btn-over.x-btn-default-toolbar-large { + border-color: #dbdbdb; + background-image: none; + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-default-toolbar-large { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +.x-btn.x-btn-menu-active.x-btn-default-toolbar-large, +.x-btn.x-btn-pressed.x-btn-default-toolbar-large { + border-color: #d2d2d2; + background-image: none; + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large, +.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large { + -webkit-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + -moz-box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; + box-shadow: #5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, + #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset; +} +.x-btn.x-btn-disabled.x-btn-default-toolbar-large { + background-image: none; + background-color: #f6f6f6; +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-default-toolbar-large-mc { + background-color: #f6f6f6; +} +.x-btn-over .x-btn-default-toolbar-large-tl, +.x-btn-over .x-btn-default-toolbar-large-bl, +.x-btn-over .x-btn-default-toolbar-large-tr, +.x-btn-over .x-btn-default-toolbar-large-br, +.x-btn-over .x-btn-default-toolbar-large-tc, +.x-btn-over .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-over-corners.gif); +} +.x-btn-over .x-btn-default-toolbar-large-ml, +.x-btn-over .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-over-sides.gif); +} +.x-btn-over .x-btn-default-toolbar-large-mc { + background-color: #ececec; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-default-toolbar-large-mc { + background-color: #ececec; +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-br, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-bc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-br, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mr, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-default-toolbar-large-mc, +.x-btn.x-btn-pressed .x-btn-default-toolbar-large-mc { + background-color: #e2e2e2; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-default-toolbar-large-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-default-toolbar-large-mc { + background-color: #e2e2e2; +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bl, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tr, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-br, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-tc, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-bc { + background-image: url(images/btn/btn-default-toolbar-large-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-ml, +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mr { + background-image: url(images/btn/btn-default-toolbar-large-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-default-toolbar-large-mc { + background-color: #f6f6f6; +} +.x-nbr .x-btn-default-toolbar-large { + background-image: none; +} +.x-btn-disabled.x-btn-default-toolbar-large { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first + .x-btn-default-toolbar-large-mc { + padding-right: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-middle + .x-btn-default-toolbar-large-mc { + padding-right: 9px !important; + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last + .x-btn-default-toolbar-large-mc { + padding-left: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first + .x-btn-default-toolbar-large-mc { + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-middle + .x-btn-default-toolbar-large-mc { + padding-top: 9px !important; + padding-bottom: 9px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last + .x-btn-default-toolbar-large-mc { + padding-top: 9px !important; +} +.x-nbr .x-segmented-button-item.x-btn-default-toolbar-large:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-default-toolbar-large:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-default-toolbar-large.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-default-toolbar-large:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-default-toolbar-large.x-segmented-button-last:after { + bottom: 1px; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #5fa2dd; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #5fa2dd; +} +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-default-toolbar-large:after, +.x-keyboard-mode + .x-nbr + .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-default-toolbar-large:after { + border-width: 1px; + border-color: #5fa2dd; +} +.x-button-default-toolbar-large-cell > .x-grid-cell-inner { + padding-top: 0; + padding-bottom: 0; +} +.x-button-default-toolbar-large-cell + > .x-grid-cell-inner + > .x-btn-default-toolbar-large { + vertical-align: top; +} +.x-tool { + cursor: pointer; +} +.x-tool-tool-el { + overflow: hidden; + width: 16px; + height: 16px; + margin: 0; + color: #fff; + text-align: center; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +.x-tool-over .x-tool-tool-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +.x-tool-pressed .x-tool-tool-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +.x-keyboard-mode .x-tool-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-tool-focus, +.x-edge .x-keyboard-mode .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +.x-tool-img { + background-image: url(images/tools/tool-sprites.png); +} +.x-tool-placeholder { + visibility: hidden; +} +.x-tool-close { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-close:before { + content: "\f00d"; +} +.x-tool-minimize { + font: 16px/1 ExtJS; + background: none; +} +.x-tool-minimize:before { + content: "\e608"; +} +.x-tool-maximize { + font: 16px/1 FontAwesome; + background: none; +} +.x-tool-maximize:before { + content: "\f065"; +} +.x-tool-restore { + font: 16px/1 FontAwesome; + background: none; +} +.x-tool-restore:before { + content: "\f066"; +} +.x-tool-toggle { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-toggle:before { + content: "\f077"; +} +.x-panel-collapsed .x-tool-toggle { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-panel-collapsed .x-tool-toggle:before { + content: "\f078"; +} +.x-tool-gear { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-gear:before { + content: "\f013"; +} +.x-tool-prev { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-prev:before { + content: "\f053"; +} +.x-tool-next { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-next:before { + content: "\f054"; +} +.x-tool-pin { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-pin:before { + content: "\f08d"; +} +.x-tool-unpin { + font: 16px/1 ExtJS; + background: none !important; +} +.x-tool-unpin:before { + content: "\e611"; +} +.x-tool-right { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-right:before { + content: "\f0da"; +} +.x-tool-left { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-left:before { + content: "\f0d9"; +} +.x-tool-down { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-down:before { + content: "\f0d7"; +} +.x-tool-up { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-up:before { + content: "\f0d8"; +} +.x-tool-refresh { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-refresh:before { + content: "\f021"; +} +.x-tool-plus { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-plus:before { + content: "\f067"; +} +.x-tool-minus { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-minus:before { + content: "\f068"; +} +.x-tool-search { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-search:before { + content: "\f002"; +} +.x-tool-save { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-save:before { + content: "\f00c"; +} +.x-tool-help { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-help:before { + content: "\f128"; +} +.x-tool-print { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-print:before { + content: "\f02f"; +} +.x-tool-expand { + font: 16px/1 ExtJS; + background: none !important; +} +.x-tool-expand:before { + content: "\e600"; +} +.x-tool-collapse { + font: 16px/1 ExtJS; + background: none !important; +} +.x-tool-collapse:before { + content: "\e606"; +} +.x-tool-resize { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-resize:before { + content: "\f07e"; +} +.x-tool-move { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-move:before { + content: "\f047"; +} +.x-tool-expand-bottom { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-expand-bottom:before { + content: "\f0d7"; +} +.x-tool-collapse-bottom { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-collapse-bottom:before { + content: "\f0d7"; +} +.x-tool-expand-top { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-expand-top:before { + content: "\f0d8"; +} +.x-tool-collapse-top { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-collapse-top:before { + content: "\f0d8"; +} +.x-tool-expand-left { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-expand-left:before { + content: "\f0d9"; +} +.x-tool-collapse-left { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-collapse-left:before { + content: "\f0d9"; +} +.x-tool-expand-right { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-expand-right:before { + content: "\f0da"; +} +.x-tool-collapse-right { + font: 16px/1 FontAwesome; + background: none !important; +} +.x-tool-collapse-right:before { + content: "\f0da"; +} +.x-header-draggable, +.x-header-ghost { + cursor: move; +} +.x-header-text { + white-space: nowrap; +} +.x-collapse-el { + cursor: pointer; + color: #919191; + display: table; + table-layout: fixed; + background-color: #e0e0e0; +} +.x-collapse-el:before { + display: table-cell; + vertical-align: middle; + text-align: center; +} +.x-layout-split-left { + font: 16px/1 FontAwesome; +} +.x-layout-split-left:before { + content: "\f0d9"; +} +.x-layout-split-right { + font: 16px/1 FontAwesome; + padding: 0 0 0 2px; +} +.x-layout-split-right:before { + content: "\f0da"; +} +.x-layout-split-top { + font: 16px/1 FontAwesome; + padding: 0 0 2px 0; +} +.x-layout-split-top:before { + content: "\f0d8"; +} +.x-layout-split-bottom { + font: 16px/1 FontAwesome; +} +.x-layout-split-bottom:before { + content: "\f0d7"; +} +.x-splitter-collapsed .x-layout-split-left { + font: 16px/1 FontAwesome; + padding: 0 0 0 2px; +} +.x-splitter-collapsed .x-layout-split-left:before { + content: "\f0da"; +} +.x-splitter-collapsed .x-layout-split-right { + font: 16px/1 FontAwesome; +} +.x-splitter-collapsed .x-layout-split-right:before { + content: "\f0d9"; +} +.x-splitter-collapsed .x-layout-split-top { + font: 16px/1 FontAwesome; +} +.x-splitter-collapsed .x-layout-split-top:before { + content: "\f0d7"; +} +.x-splitter-collapsed .x-layout-split-bottom { + font: 16px/1 FontAwesome; + padding: 0 0 2px 0; +} +.x-splitter-collapsed .x-layout-split-bottom:before { + content: "\f0d8"; +} +.x-splitter-active { + background-color: #b4b4b4; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +.x-splitter-active .x-collapse-el { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +.x-layout-split-left, +.x-layout-split-right { + top: 50%; + margin-top: -24px; + width: 100%; + height: 48px; +} +.x-layout-split-top, +.x-layout-split-bottom { + left: 50%; + width: 48px; + height: 100%; + margin-left: -24px; +} +.x-layout-split-top:before, +.x-layout-split-bottom:before { + width: 100%; + line-height: 10px; +} +.x-keyboard-mode .x-splitter-focus:after { + position: absolute; + content: " "; + top: 1px; + right: 1px; + bottom: 1px; + left: 1px; + border: 1px solid #4c82b1; + pointer-events: none; +} +.x-toolbar-default { + padding: 6px 0 6px 8px; + border-style: solid; + border-color: #d0d0d0; + border-width: 1px; + background-image: none; + background-color: #fff; +} +.x-toolbar-default .x-tool-img { + color: #919191; + background-color: #fff; +} +.x-toolbar-default .x-toolbar-item { + margin: 0 8px 0 0; +} +.x-toolbar-default .x-toolbar-separator-horizontal { + margin: 0 8px 0 0; + height: 14px; + border-style: solid; + border-width: 0 0 0 1px; + border-left-color: #d0d0d0; + border-right-color: #fff; +} +.x-toolbar-default .x-box-menu-after { + margin: 0 8px; +} +.x-toolbar-default-vertical { + padding: 6px 8px 0; +} +.x-toolbar-default-vertical .x-toolbar-item { + margin: 0 0 6px 0; +} +.x-toolbar-default-vertical .x-toolbar-separator-vertical { + margin: 0 5px 6px; + border-style: solid none; + border-width: 1px 0 0; + border-top-color: #d0d0d0; + border-bottom-color: #fff; +} +.x-toolbar-default-vertical .x-box-menu-after { + margin: 6px 0; +} +.x-toolbar-text-default { + padding: 0 4px; + color: #4b4c4c; + font: 300 13px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; +} +.x-toolbar-spacer-default { + width: 2px; +} +.x-toolbar-default-scroller .x-box-scroller-body-horizontal { + margin-left: 24px; +} +.x-toolbar-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 26px; +} +.x-box-scroller-toolbar-default { + cursor: pointer; + color: #919191; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +.x-box-scroller-toolbar-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +.x-box-scroller-toolbar-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +.x-box-scroller-toolbar-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +.x-box-scroller-toolbar-default.x-box-scroller-left, +.x-box-scroller-toolbar-default.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +.x-box-scroller-toolbar-default.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-default.x-box-scroller-left:before { + content: "\f053"; +} +.x-box-scroller-toolbar-default.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-default.x-box-scroller-right:before { + content: "\f054"; +} +.x-box-scroller-toolbar-default.x-box-scroller-top, +.x-box-scroller-toolbar-default.x-box-scroller-bottom { + height: 24px; + width: 24px; + left: 50%; + margin-left: -12px; +} +.x-box-scroller-toolbar-default.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-default.x-box-scroller-top:before { + content: "\f077"; +} +.x-box-scroller-toolbar-default.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-default.x-box-scroller-bottom:before { + content: "\f078"; +} +.x-ie8 .x-box-scroller-toolbar-default { + background-color: #fff; +} +.x-toolbar-more-icon { + font: 16px/1 FontAwesome; + color: #919191; +} +.x-toolbar-more-icon:before { + content: "\f0c9"; +} +.x-toolbar-footer { + padding: 6px 0 6px 6px; + border-style: solid; + border-color: #d0d0d0; + border-width: 0; + background-image: none; + background-color:#f6f6f6; +} +.x-toolbar-footer .x-tool-img { + color: #919191; + background-color: #ececec; +} +.x-toolbar-footer .x-toolbar-item { + margin: 0 6px 0 0; +} +.x-toolbar-footer .x-toolbar-separator-horizontal { + margin: 0 8px 0 0; + height: 14px; + border-style: solid; + border-width: 0 0 0 1px; + border-left-color: #d0d0d0; + border-right-color: #fff; +} +.x-toolbar-footer .x-box-menu-after { + margin: 0 6px; +} +.x-toolbar-footer-vertical { + padding: 6px 6px 0; +} +.x-toolbar-footer-vertical .x-toolbar-item { + margin: 0 0 6px 0; +} +.x-toolbar-footer-vertical .x-toolbar-separator-vertical { + margin: 0 5px 6px; + border-style: solid none; + border-width: 1px 0 0; + border-top-color: #d0d0d0; + border-bottom-color: #fff; +} +.x-toolbar-footer-vertical .x-box-menu-after { + margin: 6px 0; +} +.x-toolbar-text-footer { + padding: 0 4px; + color: #4b4c4c; + font: 300 13px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; +} +.x-toolbar-spacer-footer { + width: 2px; +} +.x-toolbar-footer-scroller .x-box-scroller-body-horizontal { + margin-left: 26px; +} +.x-toolbar-footer-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 26px; +} +.x-box-scroller-toolbar-footer { + cursor: pointer; + color: #919191; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +.x-box-scroller-toolbar-footer.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; +} +.x-box-scroller-toolbar-footer.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +.x-box-scroller-toolbar-footer.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +.x-box-scroller-toolbar-footer.x-box-scroller-left, +.x-box-scroller-toolbar-footer.x-box-scroller-right { + width: 24px; + height: 24px; + top: 50%; + margin-top: -12px; +} +.x-box-scroller-toolbar-footer.x-box-scroller-left { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-footer.x-box-scroller-left:before { + content: "\f053"; +} +.x-box-scroller-toolbar-footer.x-box-scroller-right { + margin-left: 4px; + margin-right: 4px; + margin-bottom: 0; + font: 16px/24px FontAwesome; +} +.x-box-scroller-toolbar-footer.x-box-scroller-right:before { + content: "\f054"; +} +.x-ie8 .x-box-scroller-toolbar-footer { + background-color: #ececec; +} +.x-toolbar-more-icon { + font: 16px/1 FontAwesome; + color: #919191; +} +.x-toolbar-more-icon:before { + content: "\f0c9"; +} +.x-dd-drag-proxy { + color: #404040; + font: 300 13px/17px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + border: 1px solid #d0d0d0; + background-color: #fff; +} +.x-dd-drag-ghost, +.x-dd-drop-icon { + padding: 5px; +} +.x-dd-drag-ghost { + padding-left: 0; +} +.x-dd-drop-ok .x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #a4cf6d; +} +.x-dd-drop-ok .x-dd-drop-icon:before { + content: "\f058"; +} +.x-dd-drop-ok-add .x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #a4cf6d; +} +.x-dd-drop-ok-add .x-dd-drop-icon:before { + content: "\f058"; +} +.x-dd-drop-nodrop div.x-dd-drop-icon { + font: 16px/1 FontAwesome; + color: #d9705d; +} +.x-dd-drop-nodrop div.x-dd-drop-icon:before { + content: "\f057"; +} +.x-panel-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-panel-default { + border-color: #5fa2dd; + padding: 0; +} +.x-panel-default.x-masked { + border-color: #afd1ee; +} +.x-panel-header-default { + font-size: 16px; + border: 1px solid #5fa2dd; +} +.x-panel-header-default .x-tool-tool-el { + background-color: #5fa2dd; +} +.x-panel-header-default-horizontal { + padding: 11px 15px 12px; +} +.x-panel-header-default-horizontal .x-panel-header-default-tab-bar { + margin-top: -11px; + margin-bottom: -12px; +} +.x-panel-header-default-horizontal.x-header-noborder { + padding: 12px 16px 12px 16px; +} +.x-panel-header-default-horizontal.x-header-noborder + .x-panel-header-default-tab-bar { + margin-top: -12px; + margin-bottom: -12px; +} +.x-panel-header-default-vertical { + padding: 15px 11px 15px 12px; +} +.x-panel-header-default-vertical .x-panel-header-default-tab-bar { + margin-right: -11px; + margin-left: -12px; +} +.x-panel-header-default-vertical.x-header-noborder { + padding: 16px 12px 16px 12px; +} +.x-panel-header-default-vertical.x-header-noborder + .x-panel-header-default-tab-bar { + margin-right: -12px; + margin-left: -12px; +} +.x-panel-header-title-default { + color: #f0f0f0; + font-size: 16px; + font-weight: 400; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 20px; +} +.x-keyboard-mode .x-panel-header-title-default.x-title-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-title-default.x-title-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-panel-header-title-default > .x-title-text-default { + text-transform: none; + padding: 0; +} +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +.x-panel-header-title-default > .x-title-icon-wrap-default.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +.x-panel-header-title-default + > .x-title-icon-wrap-default + > .x-title-icon-default { + width: 16px; + height: 16px; + font-size: 16px; + color: #f0f0f0; + background-position: center center; +} +.x-ie8 + .x-panel-header-title-default + > .x-title-icon-wrap-default + > .x-title-icon-default.x-title-glyph { + color: #f0f0f0; +} +.x-panel-body-default { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 13px; + font-weight: 300; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + border-width: 1px; + border-style: solid; +} +.x-panel-header-default { + background-image: none; + background-color: #5fa2dd; +} +.x-panel-header-default-vertical { + background-image: none; + background-color: #5fa2dd; +} +.x-panel .x-panel-header-default-collapsed-border-top { + border-bottom-width: 1px !important; +} +.x-panel .x-panel-header-default-collapsed-border-right { + border-left-width: 1px !important; +} +.x-panel .x-panel-header-default-collapsed-border-bottom { + border-top-width: 1px !important; +} +.x-panel .x-panel-header-default-collapsed-border-left { + border-right-width: 1px !important; +} +.x-panel-header-default-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-panel-header-default-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-panel-header-default-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +.x-panel-header-default-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +.x-keyboard-mode .x-panel-header-default .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-default .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-default .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-default .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-panel-default-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +.x-panel-default-outer-border-l { + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-b { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-panel-default-outer-border-bl { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-r { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +.x-panel-default-outer-border-rl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-rb { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-panel-default-outer-border-rbl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-t { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; +} +.x-panel-default-outer-border-tl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-tb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-panel-default-outer-border-tbl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-tr { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +.x-panel-default-outer-border-trl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-outer-border-trb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-panel-default-outer-border-trbl { + border-color: #5fa2dd !important; + border-width: 1px !important; +} +.x-panel-default-framed { + border-color: #5fa2dd; + padding: 0; +} +.x-panel-default-framed.x-masked { + border-color: #afd1ee; +} +.x-panel-header-default-framed { + font-size: 16px; + border: 2px solid #5fa2dd; +} +.x-panel-header-default-framed .x-tool-tool-el { + background-color: #5fa2dd; +} +.x-panel-header-default-framed-horizontal { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-horizontal + .x-panel-header-default-framed-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +.x-panel-header-default-framed-horizontal.x-header-noborder { + padding: 12px 16px 10px 16px; +} +.x-panel-header-default-framed-horizontal.x-header-noborder + .x-panel-header-default-framed-tab-bar { + margin-top: -12px; + margin-bottom: -10px; +} +.x-panel-header-default-framed-vertical { + padding: 14px 10px 14px 10px; +} +.x-panel-header-default-framed-vertical .x-panel-header-default-framed-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +.x-panel-header-default-framed-vertical.x-header-noborder { + padding: 16px 12px 16px 10px; +} +.x-panel-header-default-framed-vertical.x-header-noborder + .x-panel-header-default-framed-tab-bar { + margin-right: -12px; + margin-left: -10px; +} +.x-panel-header-title-default-framed { + color: #f0f0f0; + font-size: 16px; + font-weight: 400; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 20px; +} +.x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus, +.x-edge .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-title-default-framed.x-title-focus:after, +.x-ie10p + .x-keyboard-mode + .x-panel-header-title-default-framed.x-title-focus:after, +.x-edge + .x-keyboard-mode + .x-panel-header-title-default-framed.x-title-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-panel-header-title-default-framed > .x-title-text-default-framed { + text-transform: none; + padding: 0; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +.x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed + > .x-title-icon-default-framed { + width: 16px; + height: 16px; + font-size: 16px; + color: #f0f0f0; + background-position: center center; +} +.x-ie8 + .x-panel-header-title-default-framed + > .x-title-icon-wrap-default-framed + > .x-title-icon-default-framed.x-title-glyph { + color: #f0f0f0; +} +.x-panel-body-default-framed { + background: #fff; + border-color: #d0d0d0; + color: #404040; + font-size: 13px; + font-weight: 300; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + border-width: 1px; + border-style: solid; +} +.x-panel-default-framed { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 0 0 0 0; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +.x-panel-default-framed-mc { + background-color: #fff; +} +.x-nbr .x-panel-default-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-default-framed-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-0px-0px-0px-0px; +} +.x-panel-default-framed-tl { + background-position: 0 -4px; +} +.x-panel-default-framed-tr { + background-position: right -6px; +} +.x-panel-default-framed-bl { + background-position: 0 -8px; +} +.x-panel-default-framed-br { + background-position: right -10px; +} +.x-panel-default-framed-ml { + background-position: 0 top; +} +.x-panel-default-framed-mr { + background-position: right top; +} +.x-panel-default-framed-tc { + background-position: 0 0; +} +.x-panel-default-framed-bc { + background-position: 0 -2px; +} +.x-panel-default-framed-tr, +.x-panel-default-framed-br, +.x-panel-default-framed-mr { + padding-right: 2px; +} +.x-panel-default-framed-tl, +.x-panel-default-framed-bl, +.x-panel-default-framed-ml { + padding-left: 2px; +} +.x-panel-default-framed-tc { + height: 2px; +} +.x-panel-default-framed-bc { + height: 2px; +} +.x-panel-default-framed-tl, +.x-panel-default-framed-bl, +.x-panel-default-framed-tr, +.x-panel-default-framed-br, +.x-panel-default-framed-tc, +.x-panel-default-framed-bc, +.x-panel-default-framed-ml, +.x-panel-default-framed-mr { + background-image: url(images/panel/panel-default-framed-corners.gif); +} +.x-panel-default-framed-ml, +.x-panel-default-framed-mr { + background-image: url(images/panel/panel-default-framed-sides.gif); + background-repeat: repeat-y; +} +.x-panel-default-framed-mc { + padding: 0px 0px 0px 0px; +} +.x-panel-header-default-framed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 0 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-panel-header-default-framed-top-mc { + background-color: #5fa2dd; +} +.x-nbr .x-panel-header-default-framed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-top-frameInfo { + font-family: dh-2-2-0-2-2-2-0-2-10-14-10-14; +} +.x-panel-header-default-framed-top-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-top-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-top-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-top-br { + background-position: right -10px; +} +.x-panel-header-default-framed-top-ml { + background-position: 0 top; +} +.x-panel-header-default-framed-top-mr { + background-position: right top; +} +.x-panel-header-default-framed-top-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-top-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-top-tr, +.x-panel-header-default-framed-top-br, +.x-panel-header-default-framed-top-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-top-tl, +.x-panel-header-default-framed-top-bl, +.x-panel-header-default-framed-top-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-top-tc { + height: 2px; +} +.x-panel-header-default-framed-top-bc { + height: 0; +} +.x-panel-header-default-framed-top-tl, +.x-panel-header-default-framed-top-bl, +.x-panel-header-default-framed-top-tr, +.x-panel-header-default-framed-top-br, +.x-panel-header-default-framed-top-tc, +.x-panel-header-default-framed-top-bc, +.x-panel-header-default-framed-top-ml, +.x-panel-header-default-framed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-top-corners.gif); +} +.x-panel-header-default-framed-top-ml, +.x-panel-header-default-framed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-top-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-top-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 0; + border-style: solid; + background-color: #5fa2dd; +} +.x-panel-header-default-framed-right-mc { + background-color: #5fa2dd; +} +.x-nbr .x-panel-header-default-framed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-right-frameInfo { + font-family: dh-2-2-2-0-2-2-2-0-14-10-14-10; +} +.x-panel-header-default-framed-right-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-right-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-right-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-right-br { + background-position: right -10px; +} +.x-panel-header-default-framed-right-ml { + background-position: right 0; +} +.x-panel-header-default-framed-right-mr { + background-position: right 0; +} +.x-panel-header-default-framed-right-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-right-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-right-tr, +.x-panel-header-default-framed-right-br, +.x-panel-header-default-framed-right-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-right-tl, +.x-panel-header-default-framed-right-bl, +.x-panel-header-default-framed-right-ml { + padding-left: 0; +} +.x-panel-header-default-framed-right-tc { + height: 2px; +} +.x-panel-header-default-framed-right-bc { + height: 2px; +} +.x-panel-header-default-framed-right-tl, +.x-panel-header-default-framed-right-bl, +.x-panel-header-default-framed-right-tr, +.x-panel-header-default-framed-right-br, +.x-panel-header-default-framed-right-tc, +.x-panel-header-default-framed-right-bc, +.x-panel-header-default-framed-right-ml, +.x-panel-header-default-framed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-right-corners.gif); +} +.x-panel-header-default-framed-right-ml, +.x-panel-header-default-framed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-right-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-right-mc { + padding: 14px 10px 14px 10px; +} +.x-panel-header-default-framed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 0 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-panel-header-default-framed-bottom-mc { + background-color: #5fa2dd; +} +.x-nbr .x-panel-header-default-framed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-bottom-frameInfo { + font-family: dh-0-2-2-2-0-2-2-2-10-14-10-14; +} +.x-panel-header-default-framed-bottom-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-bottom-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-bottom-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-bottom-br { + background-position: right -10px; +} +.x-panel-header-default-framed-bottom-ml { + background-position: 0 bottom; +} +.x-panel-header-default-framed-bottom-mr { + background-position: right bottom; +} +.x-panel-header-default-framed-bottom-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-bottom-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-bottom-tr, +.x-panel-header-default-framed-bottom-br, +.x-panel-header-default-framed-bottom-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-bottom-tl, +.x-panel-header-default-framed-bottom-bl, +.x-panel-header-default-framed-bottom-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-bottom-tc { + height: 0; +} +.x-panel-header-default-framed-bottom-bc { + height: 2px; +} +.x-panel-header-default-framed-bottom-tl, +.x-panel-header-default-framed-bottom-bl, +.x-panel-header-default-framed-bottom-tr, +.x-panel-header-default-framed-bottom-br, +.x-panel-header-default-framed-bottom-tc, +.x-panel-header-default-framed-bottom-bc, +.x-panel-header-default-framed-bottom-ml, +.x-panel-header-default-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-bottom-corners.gif); +} +.x-panel-header-default-framed-bottom-ml, +.x-panel-header-default-framed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 0 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-panel-header-default-framed-left-mc { + background-color: #5fa2dd; +} +.x-nbr .x-panel-header-default-framed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-left-frameInfo { + font-family: dh-2-0-2-2-2-0-2-2-14-10-14-10; +} +.x-panel-header-default-framed-left-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-left-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-left-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-left-br { + background-position: right -10px; +} +.x-panel-header-default-framed-left-ml { + background-position: left 0; +} +.x-panel-header-default-framed-left-mr { + background-position: left 0; +} +.x-panel-header-default-framed-left-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-left-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-left-tr, +.x-panel-header-default-framed-left-br, +.x-panel-header-default-framed-left-mr { + padding-right: 0; +} +.x-panel-header-default-framed-left-tl, +.x-panel-header-default-framed-left-bl, +.x-panel-header-default-framed-left-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-left-tc { + height: 2px; +} +.x-panel-header-default-framed-left-bc { + height: 2px; +} +.x-panel-header-default-framed-left-tl, +.x-panel-header-default-framed-left-bl, +.x-panel-header-default-framed-left-tr, +.x-panel-header-default-framed-left-br, +.x-panel-header-default-framed-left-tc, +.x-panel-header-default-framed-left-bc, +.x-panel-header-default-framed-left-ml, +.x-panel-header-default-framed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-left-corners.gif); +} +.x-panel-header-default-framed-left-ml, +.x-panel-header-default-framed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-left-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-left-mc { + padding: 14px 10px 14px 10px; +} +.x-panel-header-default-framed-collapsed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-panel-header-default-framed-collapsed-top-mc { + background-color: #5fa2dd; +} +.x-nbr .x-panel-header-default-framed-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-collapsed-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-panel-header-default-framed-collapsed-top-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-collapsed-top-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-collapsed-top-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-collapsed-top-br { + background-position: right -10px; +} +.x-panel-header-default-framed-collapsed-top-ml { + background-position: 0 top; +} +.x-panel-header-default-framed-collapsed-top-mr { + background-position: right top; +} +.x-panel-header-default-framed-collapsed-top-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-collapsed-top-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-collapsed-top-tr, +.x-panel-header-default-framed-collapsed-top-br, +.x-panel-header-default-framed-collapsed-top-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-collapsed-top-tl, +.x-panel-header-default-framed-collapsed-top-bl, +.x-panel-header-default-framed-collapsed-top-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-collapsed-top-tc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-top-bc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-top-tl, +.x-panel-header-default-framed-collapsed-top-bl, +.x-panel-header-default-framed-collapsed-top-tr, +.x-panel-header-default-framed-collapsed-top-br, +.x-panel-header-default-framed-collapsed-top-tc, +.x-panel-header-default-framed-collapsed-top-bc, +.x-panel-header-default-framed-collapsed-top-ml, +.x-panel-header-default-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-top-corners.gif); +} +.x-panel-header-default-framed-collapsed-top-ml, +.x-panel-header-default-framed-collapsed-top-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-collapsed-top-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-collapsed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-panel-header-default-framed-collapsed-right-mc { + background-color: #5fa2dd; +} +.x-nbr .x-panel-header-default-framed-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-collapsed-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-panel-header-default-framed-collapsed-right-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-collapsed-right-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-collapsed-right-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-collapsed-right-br { + background-position: right -10px; +} +.x-panel-header-default-framed-collapsed-right-ml { + background-position: right 0; +} +.x-panel-header-default-framed-collapsed-right-mr { + background-position: right 0; +} +.x-panel-header-default-framed-collapsed-right-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-collapsed-right-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-collapsed-right-tr, +.x-panel-header-default-framed-collapsed-right-br, +.x-panel-header-default-framed-collapsed-right-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-collapsed-right-tl, +.x-panel-header-default-framed-collapsed-right-bl, +.x-panel-header-default-framed-collapsed-right-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-collapsed-right-tc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-right-bc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-right-tl, +.x-panel-header-default-framed-collapsed-right-bl, +.x-panel-header-default-framed-collapsed-right-tr, +.x-panel-header-default-framed-collapsed-right-br, +.x-panel-header-default-framed-collapsed-right-tc, +.x-panel-header-default-framed-collapsed-right-bc, +.x-panel-header-default-framed-collapsed-right-ml, +.x-panel-header-default-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-right-corners.gif); +} +.x-panel-header-default-framed-collapsed-right-ml, +.x-panel-header-default-framed-collapsed-right-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-collapsed-right-mc { + padding: 14px 10px 14px 10px; +} +.x-panel-header-default-framed-collapsed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-panel-header-default-framed-collapsed-bottom-mc { + background-color: #5fa2dd; +} +.x-nbr .x-panel-header-default-framed-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-collapsed-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-panel-header-default-framed-collapsed-bottom-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-collapsed-bottom-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-collapsed-bottom-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-collapsed-bottom-br { + background-position: right -10px; +} +.x-panel-header-default-framed-collapsed-bottom-ml { + background-position: 0 bottom; +} +.x-panel-header-default-framed-collapsed-bottom-mr { + background-position: right bottom; +} +.x-panel-header-default-framed-collapsed-bottom-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-collapsed-bottom-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-collapsed-bottom-tr, +.x-panel-header-default-framed-collapsed-bottom-br, +.x-panel-header-default-framed-collapsed-bottom-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-collapsed-bottom-tl, +.x-panel-header-default-framed-collapsed-bottom-bl, +.x-panel-header-default-framed-collapsed-bottom-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-collapsed-bottom-tc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-bottom-bc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-bottom-tl, +.x-panel-header-default-framed-collapsed-bottom-bl, +.x-panel-header-default-framed-collapsed-bottom-tr, +.x-panel-header-default-framed-collapsed-bottom-br, +.x-panel-header-default-framed-collapsed-bottom-tc, +.x-panel-header-default-framed-collapsed-bottom-bc, +.x-panel-header-default-framed-collapsed-bottom-ml, +.x-panel-header-default-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-bottom-corners.gif); +} +.x-panel-header-default-framed-collapsed-bottom-ml, +.x-panel-header-default-framed-collapsed-bottom-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-collapsed-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-panel-header-default-framed-collapsed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-panel-header-default-framed-collapsed-left-mc { + background-color: #5fa2dd; +} +.x-nbr .x-panel-header-default-framed-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-panel-header-default-framed-collapsed-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-panel-header-default-framed-collapsed-left-tl { + background-position: 0 -4px; +} +.x-panel-header-default-framed-collapsed-left-tr { + background-position: right -6px; +} +.x-panel-header-default-framed-collapsed-left-bl { + background-position: 0 -8px; +} +.x-panel-header-default-framed-collapsed-left-br { + background-position: right -10px; +} +.x-panel-header-default-framed-collapsed-left-ml { + background-position: left 0; +} +.x-panel-header-default-framed-collapsed-left-mr { + background-position: left 0; +} +.x-panel-header-default-framed-collapsed-left-tc { + background-position: 0 0; +} +.x-panel-header-default-framed-collapsed-left-bc { + background-position: 0 -2px; +} +.x-panel-header-default-framed-collapsed-left-tr, +.x-panel-header-default-framed-collapsed-left-br, +.x-panel-header-default-framed-collapsed-left-mr { + padding-right: 2px; +} +.x-panel-header-default-framed-collapsed-left-tl, +.x-panel-header-default-framed-collapsed-left-bl, +.x-panel-header-default-framed-collapsed-left-ml { + padding-left: 2px; +} +.x-panel-header-default-framed-collapsed-left-tc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-left-bc { + height: 2px; +} +.x-panel-header-default-framed-collapsed-left-tl, +.x-panel-header-default-framed-collapsed-left-bl, +.x-panel-header-default-framed-collapsed-left-tr, +.x-panel-header-default-framed-collapsed-left-br, +.x-panel-header-default-framed-collapsed-left-tc, +.x-panel-header-default-framed-collapsed-left-bc, +.x-panel-header-default-framed-collapsed-left-ml, +.x-panel-header-default-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-left-corners.gif); +} +.x-panel-header-default-framed-collapsed-left-ml, +.x-panel-header-default-framed-collapsed-left-mr { + background-image: url(images/panel-header/panel-header-default-framed-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +.x-panel-header-default-framed-collapsed-left-mc { + padding: 14px 10px 14px 10px; +} +.x-panel .x-panel-header-default-framed-top { + border-bottom-width: 2px !important; +} +.x-panel .x-panel-header-default-framed-right { + border-left-width: 2px !important; +} +.x-panel .x-panel-header-default-framed-bottom { + border-top-width: 2px !important; +} +.x-panel .x-panel-header-default-framed-left { + border-right-width: 2px !important; +} +.x-nbr .x-panel-header-default-framed-collapsed-top { + border-bottom-width: 0 !important; +} +.x-nbr .x-panel-header-default-framed-collapsed-right { + border-left-width: 0 !important; +} +.x-nbr .x-panel-header-default-framed-collapsed-bottom { + border-top-width: 0 !important; +} +.x-nbr .x-panel-header-default-framed-collapsed-left { + border-right-width: 0 !important; +} +.x-panel-header-default-framed-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-panel-header-default-framed-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-panel-header-default-framed-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +.x-panel-header-default-framed-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +.x-keyboard-mode .x-panel-header-default-framed .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus, +.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-panel-header-default-framed .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-panel-default-framed-resizable .x-panel-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +.x-panel-default-framed-outer-border-l { + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-b { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-panel-default-framed-outer-border-bl { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-r { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +.x-panel-default-framed-outer-border-rl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-rb { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-panel-default-framed-outer-border-rbl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-t { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; +} +.x-panel-default-framed-outer-border-tl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-tb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-panel-default-framed-outer-border-tbl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-tr { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +.x-panel-default-framed-outer-border-trl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-panel-default-framed-outer-border-trb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-panel-default-framed-outer-border-trbl { + border-color: #5fa2dd !important; + border-width: 1px !important; +} +.x-btn-group-default { + border-color: #d0d0d0; + -webkit-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, + #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + -moz-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, + #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, + #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; +} +.x-btn-group-header-default { + padding: 8px 8px 7px; + line-height: 16px; + background: #fff; + -moz-border-radius-topleft: 0px; + -webkit-border-top-left-radius: 0px; + border-top-left-radius: 0px; + -moz-border-radius-topright: 0px; + -webkit-border-top-right-radius: 0px; + border-top-right-radius: 0px; +} +.x-btn-group-header-default .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #fff; +} +.x-btn-group-header-title-default { + font: 300 14px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 16px; + color: #606060; +} +.x-btn-group-body-default { + padding: 0 1px; +} +.x-btn-group-body-default .x-table-layout { + border-spacing: 6px; +} +.x-btn-group-default-framed { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #fff; +} +.x-btn-group-default-framed-mc { + background-color: #fff; +} +.x-nbr .x-btn-group-default-framed { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-group-default-framed-frameInfo { + font-family: dh-2-2-2-2-1-1-1-1-1-1-1-1; +} +.x-btn-group-default-framed-tl { + background-position: 0 -4px; +} +.x-btn-group-default-framed-tr { + background-position: right -6px; +} +.x-btn-group-default-framed-bl { + background-position: 0 -8px; +} +.x-btn-group-default-framed-br { + background-position: right -10px; +} +.x-btn-group-default-framed-ml { + background-position: 0 top; +} +.x-btn-group-default-framed-mr { + background-position: right top; +} +.x-btn-group-default-framed-tc { + background-position: 0 0; +} +.x-btn-group-default-framed-bc { + background-position: 0 -2px; +} +.x-btn-group-default-framed-tr, +.x-btn-group-default-framed-br, +.x-btn-group-default-framed-mr { + padding-right: 2px; +} +.x-btn-group-default-framed-tl, +.x-btn-group-default-framed-bl, +.x-btn-group-default-framed-ml { + padding-left: 2px; +} +.x-btn-group-default-framed-tc { + height: 2px; +} +.x-btn-group-default-framed-bc { + height: 2px; +} +.x-btn-group-default-framed-tl, +.x-btn-group-default-framed-bl, +.x-btn-group-default-framed-tr, +.x-btn-group-default-framed-br, +.x-btn-group-default-framed-tc, +.x-btn-group-default-framed-bc, +.x-btn-group-default-framed-ml, +.x-btn-group-default-framed-mr { + background-image: url(images/btn-group/btn-group-default-framed-corners.gif); +} +.x-btn-group-default-framed-ml, +.x-btn-group-default-framed-mr { + background-image: url(images/btn-group/btn-group-default-framed-sides.gif); + background-repeat: repeat-y; +} +.x-btn-group-default-framed-mc { + padding: 0px 0px 0px 0px; +} +.x-btn-group-default-framed-notitle { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #fff; +} +.x-btn-group-default-framed-notitle-mc { + background-color: #fff; +} +.x-nbr .x-btn-group-default-framed-notitle { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-group-default-framed-notitle-frameInfo { + font-family: dh-2-2-2-2-1-1-1-1-1-1-1-1; +} +.x-btn-group-default-framed-notitle-tl { + background-position: 0 -4px; +} +.x-btn-group-default-framed-notitle-tr { + background-position: right -6px; +} +.x-btn-group-default-framed-notitle-bl { + background-position: 0 -8px; +} +.x-btn-group-default-framed-notitle-br { + background-position: right -10px; +} +.x-btn-group-default-framed-notitle-ml { + background-position: 0 top; +} +.x-btn-group-default-framed-notitle-mr { + background-position: right top; +} +.x-btn-group-default-framed-notitle-tc { + background-position: 0 0; +} +.x-btn-group-default-framed-notitle-bc { + background-position: 0 -2px; +} +.x-btn-group-default-framed-notitle-tr, +.x-btn-group-default-framed-notitle-br, +.x-btn-group-default-framed-notitle-mr { + padding-right: 2px; +} +.x-btn-group-default-framed-notitle-tl, +.x-btn-group-default-framed-notitle-bl, +.x-btn-group-default-framed-notitle-ml { + padding-left: 2px; +} +.x-btn-group-default-framed-notitle-tc { + height: 2px; +} +.x-btn-group-default-framed-notitle-bc { + height: 2px; +} +.x-btn-group-default-framed-notitle-tl, +.x-btn-group-default-framed-notitle-bl, +.x-btn-group-default-framed-notitle-tr, +.x-btn-group-default-framed-notitle-br, +.x-btn-group-default-framed-notitle-tc, +.x-btn-group-default-framed-notitle-bc, +.x-btn-group-default-framed-notitle-ml, +.x-btn-group-default-framed-notitle-mr { + background-image: url(images/btn-group/btn-group-default-framed-notitle-corners.gif); +} +.x-btn-group-default-framed-notitle-ml, +.x-btn-group-default-framed-notitle-mr { + background-image: url(images/btn-group/btn-group-default-framed-notitle-sides.gif); + background-repeat: repeat-y; +} +.x-btn-group-default-framed-notitle-mc { + padding: 0px 0px 0px 0px; +} +.x-btn-group-default-framed { + border-color: #d0d0d0; + -webkit-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, + #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + -moz-box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, + #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; + box-shadow: #fff 0 1px 0px 0 inset, #fff 0 -1px 0px 0 inset, + #fff -1px 0 0px 0 inset, #fff 1px 0 0px 0 inset; +} +.x-btn-group-header-default-framed { + padding: 8px 8px 7px; + line-height: 16px; + background: #fff; + -moz-border-radius-topleft: 2px; + -webkit-border-top-left-radius: 2px; + border-top-left-radius: 2px; + -moz-border-radius-topright: 2px; + -webkit-border-top-right-radius: 2px; + border-top-right-radius: 2px; +} +.x-btn-group-header-default-framed .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #fff; +} +.x-btn-group-header-title-default-framed { + font: 300 14px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 16px; + color: #606060; +} +.x-btn-group-body-default-framed { + padding: 0 1px; +} +.x-btn-group-body-default-framed .x-table-layout { + border-spacing: 6px; +} +.x-dashboard-column { + padding: 0 0 7px 0; +} +.x-dashboard-panel { + margin-top: 7px; +} +.x-dashboard-column-first { + padding-left: 7px; + clear: left; +} +.x-dashboard-column-last { + padding-right: 7px; +} +.x-dashboard .x-panel-dd-spacer { + border: 2px dashed #99bbe8; + background: #f6f6f6; + border-radius: 4px; + -moz-border-radius: 4px; + margin-top: 7px; +} +.x-dashboard-dd-over { + overflow: hidden !important; +} +.x-window-ghost { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-window-default { + border-color: #5fa2dd; + -webkit-border-radius: 0 0 0 0; + -moz-border-radius: 0 0 0 0; + -ms-border-radius: 0 0 0 0; + -o-border-radius: 0 0 0 0; + border-radius: 0 0 0 0; +} +.x-window-default { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 0 0 0 0; + border-width: 2px; + border-style: solid; + background-color: #fff; +} +.x-window-default-mc { + background-color: #fff; +} +.x-nbr .x-window-default { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-default-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-0px-0px-0px-0px; +} +.x-window-default-tl { + background-position: 0 -4px; +} +.x-window-default-tr { + background-position: right -6px; +} +.x-window-default-bl { + background-position: 0 -8px; +} +.x-window-default-br { + background-position: right -10px; +} +.x-window-default-ml { + background-position: 0 top; +} +.x-window-default-mr { + background-position: right top; +} +.x-window-default-tc { + background-position: 0 0; +} +.x-window-default-bc { + background-position: 0 -2px; +} +.x-window-default-tr, +.x-window-default-br, +.x-window-default-mr { + padding-right: 2px; +} +.x-window-default-tl, +.x-window-default-bl, +.x-window-default-ml { + padding-left: 2px; +} +.x-window-default-tc { + height: 2px; +} +.x-window-default-bc { + height: 2px; +} +.x-window-default-tl, +.x-window-default-bl, +.x-window-default-tr, +.x-window-default-br, +.x-window-default-tc, +.x-window-default-bc, +.x-window-default-ml, +.x-window-default-mr { + background-image: url(images/window/window-default-corners.gif); +} +.x-window-default-ml, +.x-window-default-mr { + background-image: url(images/window/window-default-sides.gif); + background-repeat: repeat-y; +} +.x-window-default-mc { + padding: 0px 0px 0px 0px; +} +.x-window-body-default { + border-color: #5fa2dd; + border-width: 1px; + border-style: solid; + background: #fff; + color: #000; + font-size: 13px; + font-weight: 300; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; +} +.x-window-header-default { + font-size: 16px; + border-color: #5fa2dd; + background-color: #5fa2dd; +} +.x-window-header-default .x-tool-img { + background-color: #5fa2dd; +} +.x-window-header-default-horizontal .x-window-header-default-tab-bar { + margin-top: -10px; + margin-bottom: -10px; +} +.x-window-header-default-vertical .x-window-header-default-tab-bar { + margin-right: -10px; + margin-left: -10px; +} +.x-window-header-title-default { + color: #f0f0f0; + font-size: 16px; + font-weight: 400; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 20px; +} +.x-window-header-title-default > .x-title-text-default { + padding: 0; + text-transform: none; +} +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-top { + height: 24px; + padding-bottom: 8px; +} +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-right { + width: 24px; + padding-left: 8px; +} +.x-window-header-title-default + > .x-title-icon-wrap-default.x-title-icon-bottom { + height: 24px; + padding-top: 8px; +} +.x-window-header-title-default > .x-title-icon-wrap-default.x-title-icon-left { + width: 24px; + padding-right: 8px; +} +.x-window-header-title-default + > .x-title-icon-wrap-default + > .x-title-icon-default { + width: 16px; + height: 16px; + font-size: 16px; + color: #f0f0f0; + background-position: center center; +} +.x-ie8 + .x-window-header-title-default + > .x-title-icon-wrap-default + > .x-title-icon-default.x-title-glyph { + color: #f0f0f0; +} +.x-window-header-default-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-window-header-default-top-mc { + background-color: #5fa2dd; +} +.x-nbr .x-window-header-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-window-header-default-top-tl { + background-position: 0 -4px; +} +.x-window-header-default-top-tr { + background-position: right -6px; +} +.x-window-header-default-top-bl { + background-position: 0 -8px; +} +.x-window-header-default-top-br { + background-position: right -10px; +} +.x-window-header-default-top-ml { + background-position: 0 top; +} +.x-window-header-default-top-mr { + background-position: right top; +} +.x-window-header-default-top-tc { + background-position: 0 0; +} +.x-window-header-default-top-bc { + background-position: 0 -2px; +} +.x-window-header-default-top-tr, +.x-window-header-default-top-br, +.x-window-header-default-top-mr { + padding-right: 2px; +} +.x-window-header-default-top-tl, +.x-window-header-default-top-bl, +.x-window-header-default-top-ml { + padding-left: 2px; +} +.x-window-header-default-top-tc { + height: 2px; +} +.x-window-header-default-top-bc { + height: 2px; +} +.x-window-header-default-top-tl, +.x-window-header-default-top-bl, +.x-window-header-default-top-tr, +.x-window-header-default-top-br, +.x-window-header-default-top-tc, +.x-window-header-default-top-bc, +.x-window-header-default-top-ml, +.x-window-header-default-top-mr { + background-image: url(images/window-header/window-header-default-top-corners.gif); +} +.x-window-header-default-top-ml, +.x-window-header-default-top-mr { + background-image: url(images/window-header/window-header-default-top-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-top-mc { + padding: 10px 14px 10px 14px; +} +.x-window-header-default-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-window-header-default-right-mc { + background-color: #5fa2dd; +} +.x-nbr .x-window-header-default-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-window-header-default-right-tl { + background-position: 0 -4px; +} +.x-window-header-default-right-tr { + background-position: right -6px; +} +.x-window-header-default-right-bl { + background-position: 0 -8px; +} +.x-window-header-default-right-br { + background-position: right -10px; +} +.x-window-header-default-right-ml { + background-position: 0 top; +} +.x-window-header-default-right-mr { + background-position: right top; +} +.x-window-header-default-right-tc { + background-position: 0 0; +} +.x-window-header-default-right-bc { + background-position: 0 -2px; +} +.x-window-header-default-right-tr, +.x-window-header-default-right-br, +.x-window-header-default-right-mr { + padding-right: 2px; +} +.x-window-header-default-right-tl, +.x-window-header-default-right-bl, +.x-window-header-default-right-ml { + padding-left: 2px; +} +.x-window-header-default-right-tc { + height: 2px; +} +.x-window-header-default-right-bc { + height: 2px; +} +.x-window-header-default-right-tl, +.x-window-header-default-right-bl, +.x-window-header-default-right-tr, +.x-window-header-default-right-br, +.x-window-header-default-right-tc, +.x-window-header-default-right-bc, +.x-window-header-default-right-ml, +.x-window-header-default-right-mr { + background-image: url(images/window-header/window-header-default-right-corners.gif); +} +.x-window-header-default-right-ml, +.x-window-header-default-right-mr { + background-image: url(images/window-header/window-header-default-right-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-right-mc { + padding: 14px 10px 14px 10px; +} +.x-window-header-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-window-header-default-bottom-mc { + background-color: #5fa2dd; +} +.x-nbr .x-window-header-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-window-header-default-bottom-tl { + background-position: 0 -4px; +} +.x-window-header-default-bottom-tr { + background-position: right -6px; +} +.x-window-header-default-bottom-bl { + background-position: 0 -8px; +} +.x-window-header-default-bottom-br { + background-position: right -10px; +} +.x-window-header-default-bottom-ml { + background-position: 0 top; +} +.x-window-header-default-bottom-mr { + background-position: right top; +} +.x-window-header-default-bottom-tc { + background-position: 0 0; +} +.x-window-header-default-bottom-bc { + background-position: 0 -2px; +} +.x-window-header-default-bottom-tr, +.x-window-header-default-bottom-br, +.x-window-header-default-bottom-mr { + padding-right: 2px; +} +.x-window-header-default-bottom-tl, +.x-window-header-default-bottom-bl, +.x-window-header-default-bottom-ml { + padding-left: 2px; +} +.x-window-header-default-bottom-tc { + height: 2px; +} +.x-window-header-default-bottom-bc { + height: 2px; +} +.x-window-header-default-bottom-tl, +.x-window-header-default-bottom-bl, +.x-window-header-default-bottom-tr, +.x-window-header-default-bottom-br, +.x-window-header-default-bottom-tc, +.x-window-header-default-bottom-bc, +.x-window-header-default-bottom-ml, +.x-window-header-default-bottom-mr { + background-image: url(images/window-header/window-header-default-bottom-corners.gif); +} +.x-window-header-default-bottom-ml, +.x-window-header-default-bottom-mr { + background-image: url(images/window-header/window-header-default-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-window-header-default-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px 2px 2px 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-window-header-default-left-mc { + background-color: #5fa2dd; +} +.x-nbr .x-window-header-default-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-window-header-default-left-tl { + background-position: 0 -4px; +} +.x-window-header-default-left-tr { + background-position: right -6px; +} +.x-window-header-default-left-bl { + background-position: 0 -8px; +} +.x-window-header-default-left-br { + background-position: right -10px; +} +.x-window-header-default-left-ml { + background-position: 0 top; +} +.x-window-header-default-left-mr { + background-position: right top; +} +.x-window-header-default-left-tc { + background-position: 0 0; +} +.x-window-header-default-left-bc { + background-position: 0 -2px; +} +.x-window-header-default-left-tr, +.x-window-header-default-left-br, +.x-window-header-default-left-mr { + padding-right: 2px; +} +.x-window-header-default-left-tl, +.x-window-header-default-left-bl, +.x-window-header-default-left-ml { + padding-left: 2px; +} +.x-window-header-default-left-tc { + height: 2px; +} +.x-window-header-default-left-bc { + height: 2px; +} +.x-window-header-default-left-tl, +.x-window-header-default-left-bl, +.x-window-header-default-left-tr, +.x-window-header-default-left-br, +.x-window-header-default-left-tc, +.x-window-header-default-left-bc, +.x-window-header-default-left-ml, +.x-window-header-default-left-mr { + background-image: url(images/window-header/window-header-default-left-corners.gif); +} +.x-window-header-default-left-ml, +.x-window-header-default-left-mr { + background-image: url(images/window-header/window-header-default-left-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-left-mc { + padding: 14px 10px 14px 10px; +} +.x-window-header-default-collapsed-top { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-window-header-default-collapsed-top-mc { + background-color: #5fa2dd; +} +.x-nbr .x-window-header-default-collapsed-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-collapsed-top-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-window-header-default-collapsed-top-tl { + background-position: 0 -4px; +} +.x-window-header-default-collapsed-top-tr { + background-position: right -6px; +} +.x-window-header-default-collapsed-top-bl { + background-position: 0 -8px; +} +.x-window-header-default-collapsed-top-br { + background-position: right -10px; +} +.x-window-header-default-collapsed-top-ml { + background-position: 0 top; +} +.x-window-header-default-collapsed-top-mr { + background-position: right top; +} +.x-window-header-default-collapsed-top-tc { + background-position: 0 0; +} +.x-window-header-default-collapsed-top-bc { + background-position: 0 -2px; +} +.x-window-header-default-collapsed-top-tr, +.x-window-header-default-collapsed-top-br, +.x-window-header-default-collapsed-top-mr { + padding-right: 2px; +} +.x-window-header-default-collapsed-top-tl, +.x-window-header-default-collapsed-top-bl, +.x-window-header-default-collapsed-top-ml { + padding-left: 2px; +} +.x-window-header-default-collapsed-top-tc { + height: 2px; +} +.x-window-header-default-collapsed-top-bc { + height: 2px; +} +.x-window-header-default-collapsed-top-tl, +.x-window-header-default-collapsed-top-bl, +.x-window-header-default-collapsed-top-tr, +.x-window-header-default-collapsed-top-br, +.x-window-header-default-collapsed-top-tc, +.x-window-header-default-collapsed-top-bc, +.x-window-header-default-collapsed-top-ml, +.x-window-header-default-collapsed-top-mr { + background-image: url(images/window-header/window-header-default-collapsed-top-corners.gif); +} +.x-window-header-default-collapsed-top-ml, +.x-window-header-default-collapsed-top-mr { + background-image: url(images/window-header/window-header-default-collapsed-top-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-collapsed-top-mc { + padding: 10px 14px 10px 14px; +} +.x-window-header-default-collapsed-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-window-header-default-collapsed-right-mc { + background-color: #5fa2dd; +} +.x-nbr .x-window-header-default-collapsed-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-collapsed-right-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-window-header-default-collapsed-right-tl { + background-position: 0 -4px; +} +.x-window-header-default-collapsed-right-tr { + background-position: right -6px; +} +.x-window-header-default-collapsed-right-bl { + background-position: 0 -8px; +} +.x-window-header-default-collapsed-right-br { + background-position: right -10px; +} +.x-window-header-default-collapsed-right-ml { + background-position: 0 top; +} +.x-window-header-default-collapsed-right-mr { + background-position: right top; +} +.x-window-header-default-collapsed-right-tc { + background-position: 0 0; +} +.x-window-header-default-collapsed-right-bc { + background-position: 0 -2px; +} +.x-window-header-default-collapsed-right-tr, +.x-window-header-default-collapsed-right-br, +.x-window-header-default-collapsed-right-mr { + padding-right: 2px; +} +.x-window-header-default-collapsed-right-tl, +.x-window-header-default-collapsed-right-bl, +.x-window-header-default-collapsed-right-ml { + padding-left: 2px; +} +.x-window-header-default-collapsed-right-tc { + height: 2px; +} +.x-window-header-default-collapsed-right-bc { + height: 2px; +} +.x-window-header-default-collapsed-right-tl, +.x-window-header-default-collapsed-right-bl, +.x-window-header-default-collapsed-right-tr, +.x-window-header-default-collapsed-right-br, +.x-window-header-default-collapsed-right-tc, +.x-window-header-default-collapsed-right-bc, +.x-window-header-default-collapsed-right-ml, +.x-window-header-default-collapsed-right-mr { + background-image: url(images/window-header/window-header-default-collapsed-right-corners.gif); +} +.x-window-header-default-collapsed-right-ml, +.x-window-header-default-collapsed-right-mr { + background-image: url(images/window-header/window-header-default-collapsed-right-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-collapsed-right-mc { + padding: 14px 10px 14px 10px; +} +.x-window-header-default-collapsed-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 10px 14px 10px 14px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-window-header-default-collapsed-bottom-mc { + background-color: #5fa2dd; +} +.x-nbr .x-window-header-default-collapsed-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-collapsed-bottom-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-10-14-10-14; +} +.x-window-header-default-collapsed-bottom-tl { + background-position: 0 -4px; +} +.x-window-header-default-collapsed-bottom-tr { + background-position: right -6px; +} +.x-window-header-default-collapsed-bottom-bl { + background-position: 0 -8px; +} +.x-window-header-default-collapsed-bottom-br { + background-position: right -10px; +} +.x-window-header-default-collapsed-bottom-ml { + background-position: 0 top; +} +.x-window-header-default-collapsed-bottom-mr { + background-position: right top; +} +.x-window-header-default-collapsed-bottom-tc { + background-position: 0 0; +} +.x-window-header-default-collapsed-bottom-bc { + background-position: 0 -2px; +} +.x-window-header-default-collapsed-bottom-tr, +.x-window-header-default-collapsed-bottom-br, +.x-window-header-default-collapsed-bottom-mr { + padding-right: 2px; +} +.x-window-header-default-collapsed-bottom-tl, +.x-window-header-default-collapsed-bottom-bl, +.x-window-header-default-collapsed-bottom-ml { + padding-left: 2px; +} +.x-window-header-default-collapsed-bottom-tc { + height: 2px; +} +.x-window-header-default-collapsed-bottom-bc { + height: 2px; +} +.x-window-header-default-collapsed-bottom-tl, +.x-window-header-default-collapsed-bottom-bl, +.x-window-header-default-collapsed-bottom-tr, +.x-window-header-default-collapsed-bottom-br, +.x-window-header-default-collapsed-bottom-tc, +.x-window-header-default-collapsed-bottom-bc, +.x-window-header-default-collapsed-bottom-ml, +.x-window-header-default-collapsed-bottom-mr { + background-image: url(images/window-header/window-header-default-collapsed-bottom-corners.gif); +} +.x-window-header-default-collapsed-bottom-ml, +.x-window-header-default-collapsed-bottom-mr { + background-image: url(images/window-header/window-header-default-collapsed-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-collapsed-bottom-mc { + padding: 10px 14px 10px 14px; +} +.x-window-header-default-collapsed-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 14px 10px 14px 10px; + border-width: 2px; + border-style: solid; + background-color: #5fa2dd; +} +.x-window-header-default-collapsed-left-mc { + background-color: #5fa2dd; +} +.x-nbr .x-window-header-default-collapsed-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-window-header-default-collapsed-left-frameInfo { + font-family: dh-2-2-2-2-2-2-2-2-14-10-14-10; +} +.x-window-header-default-collapsed-left-tl { + background-position: 0 -4px; +} +.x-window-header-default-collapsed-left-tr { + background-position: right -6px; +} +.x-window-header-default-collapsed-left-bl { + background-position: 0 -8px; +} +.x-window-header-default-collapsed-left-br { + background-position: right -10px; +} +.x-window-header-default-collapsed-left-ml { + background-position: 0 top; +} +.x-window-header-default-collapsed-left-mr { + background-position: right top; +} +.x-window-header-default-collapsed-left-tc { + background-position: 0 0; +} +.x-window-header-default-collapsed-left-bc { + background-position: 0 -2px; +} +.x-window-header-default-collapsed-left-tr, +.x-window-header-default-collapsed-left-br, +.x-window-header-default-collapsed-left-mr { + padding-right: 2px; +} +.x-window-header-default-collapsed-left-tl, +.x-window-header-default-collapsed-left-bl, +.x-window-header-default-collapsed-left-ml { + padding-left: 2px; +} +.x-window-header-default-collapsed-left-tc { + height: 2px; +} +.x-window-header-default-collapsed-left-bc { + height: 2px; +} +.x-window-header-default-collapsed-left-tl, +.x-window-header-default-collapsed-left-bl, +.x-window-header-default-collapsed-left-tr, +.x-window-header-default-collapsed-left-br, +.x-window-header-default-collapsed-left-tc, +.x-window-header-default-collapsed-left-bc, +.x-window-header-default-collapsed-left-ml, +.x-window-header-default-collapsed-left-mr { + background-image: url(images/window-header/window-header-default-collapsed-left-corners.gif); +} +.x-window-header-default-collapsed-left-ml, +.x-window-header-default-collapsed-left-mr { + background-image: url(images/window-header/window-header-default-collapsed-left-sides.gif); + background-repeat: repeat-y; +} +.x-window-header-default-collapsed-left-mc { + padding: 14px 10px 14px 10px; +} +.x-window-header-default .x-window-header-icon { + width: 16px; + height: 16px; + color: #f0f0f0; + font-size: 16px; + line-height: 16px; + background-position: center center; +} +.x-window-header-default .x-window-header-glyph { + color: #f0f0f0; + font-size: 16px; + line-height: 16px; +} +.x-ie8 .x-window-header-default .x-window-header-glyph { + color: #f0f0f0; +} +.x-window-header-default-horizontal .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-window-header-default-horizontal .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-window-header-default-vertical .x-tool-after-title { + margin: 6px 0 0 0; +} +.x-window-header-default-vertical .x-tool-before-title { + margin: 0 0 6px 0; +} +.x-keyboard-mode .x-window-header-default .x-tool-focus { + outline: 1px solid #fff; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus, +.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-window-header-default .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-window-header-default .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-window-header-default .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #fff; + pointer-events: none; +} +.x-window-header-default { + border-width: 2px !important; +} +.x-nbr .x-window-default-collapsed .x-window-header { + border-width: 0 !important; +} +.x-window-default-outer-border-l { + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-b { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-window-default-outer-border-bl { + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-r { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +.x-window-default-outer-border-rl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-rb { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-window-default-outer-border-rbl { + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-t { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; +} +.x-window-default-outer-border-tl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-tb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-window-default-outer-border-tbl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-tr { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; +} +.x-window-default-outer-border-trl { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-left-color: #5fa2dd !important; + border-left-width: 1px !important; +} +.x-window-default-outer-border-trb { + border-top-color: #5fa2dd !important; + border-top-width: 1px !important; + border-right-color: #5fa2dd !important; + border-right-width: 1px !important; + border-bottom-color: #5fa2dd !important; + border-bottom-width: 1px !important; +} +.x-window-default-outer-border-trbl { + border-color: #5fa2dd !important; + border-width: 1px !important; +} +.x-window-body-plain { + background-color: transparent; +} +.x-form-item-label-default { + color: #404040; + font: 300 13px/17px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + min-height: 32px; + padding-top: 8px; + padding-right: 5px; +} +.x-ie8 .x-form-item-label-default { + min-height: 24px; +} +.x-form-item-label-default.x-form-item-label-top { + height: 1px; +} +.x-form-item-label-default.x-form-item-label-top > .x-form-item-label-inner { + padding-top: 8px; + padding-bottom: 5px; +} +.x-form-item-label-default.x-form-item-label-top-side-error:after { + width: 26px; +} +.x-form-item-body-default { + min-height: 32px; +} +.x-form-invalid-icon-default { + width: 16px; + height: 16px; + margin: 0 5px; + background: url(images/form/exclamation.png) no-repeat; +} +.x-form-invalid-under-default { + padding: 2px 2px 2px 20px; + color: #cf4c35; + font: 300 13px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + background: no-repeat 0 2px; + background-image: url(images/form/exclamation.png); +} +.x-form-error-wrap-default.x-form-error-wrap-side { + width: 26px; +} +.x-form-item-default.x-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +.x-autocontainer-form-item, +.x-anchor-form-item, +.x-vbox-form-item, +.x-table-form-item { + margin-bottom: 10px; +} +.x-form-text-field-body-default { + min-width: 170px; + max-width: 170px; +} +.x-form-trigger-wrap-default { + border-width: 1px; + border-style: solid; + border-color: #d0d0d0; +} +.x-form-trigger-wrap-default.x-form-trigger-wrap-focus { + border-color: #77b0e2; +} +.x-form-trigger-wrap-default.x-form-trigger-wrap-invalid { + border-color: #cf4c35; +} +.x-form-text-default { + color: #404040; + padding: 5px 10px 4px; + background-color: #fff; + font: 300 13px/21px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + min-height: 30px; +} +.x-ie8 .x-form-text-default { + min-height: 21px; +} +.x-form-text-default.x-form-textarea { + line-height: 20px; + min-height: 80px; +} +.x-ie8 .x-form-text-default.x-form-textarea { + min-height: 71px; +} +.x-form-text-default.x-form-text-file { + color: grey; +} +.x-form-text-default.x-webkit-border-box-bug { + height: calc(100% + 9px); +} +.x-placeholder-label-default { + padding: 5px 10px 4px; +} +.x-form-empty-field-default + .x-placeholder-label-default { + color: grey; +} +.x-form-text-default:-ms-input-placeholder { + color: grey; +} +.x-form-invalid-field-default { + background-color: #fff; +} +.x-form-trigger-default { + width: 32px; + font: 16px/30px FontAwesome; + background: #fff; + color: #919191; +} +.x-form-trigger-default:before { + content: "\f0d7"; +} +.x-form-trigger-default.x-form-trigger-over { + background-position: -32px center; +} +.x-form-trigger-default.x-form-trigger-over.x-form-trigger-focus { + background-position: -128px center; +} +.x-form-trigger-default.x-form-trigger-focus { + background-position: -96px center; +} +.x-form-trigger.x-form-trigger-default.x-form-trigger-click { + background-position: -64px center; +} +.x-textfield-default-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +.x-form-clear-trigger { + font-size: 16px; + font-family: FontAwesome; +} +.x-form-clear-trigger:before { + content: "\f00d"; +} +.x-form-search-trigger { + font-size: 16px; + font-family: FontAwesome; +} +.x-form-search-trigger:before { + content: "\f002"; +} +.x-message-box .x-window-body { + background-color: #fff; + border-width: 0; +} +.x-message-box-info, +.x-message-box-warning, +.x-message-box-question, +.x-message-box-error { + background-position: left top; + background-repeat: no-repeat; +} +.x-message-box-icon { + height: 44px; + width: 44px; + margin-right: 10px; +} +.x-message-box-info { + font: 44px/1 FontAwesome; + color: grey; +} +.x-message-box-info:before { + content: "\f05a"; +} +.x-message-box-warning { + font: 44px/1 FontAwesome; + color: #f8d400; +} +.x-message-box-warning:before { + content: "\f071"; +} +.x-message-box-question { + font: 44px/1 FontAwesome; + color: grey; +} +.x-message-box-question:before { + content: "\f059"; +} +.x-message-box-error { + font: 44px/1 FontAwesome; + color: #ee611f; +} +.x-message-box-error:before { + content: "\f057"; +} +.x-form-cb-wrap-default { + height: 32px; + min-width: 18px; +} +.x-form-cb-default { + margin-top: 7px; +} +.x-form-checkbox-default, +.x-form-radio-default { + width: 18px; + height: 18px; +} +.x-form-radio-default { + font: 18px/1 FontAwesome; + color: #919191; +} +.x-form-radio-default:before { + content: "\f10c"; +} +.x-form-cb-checked .x-form-radio-default { + font: 18px/1 FontAwesome; +} +.x-form-cb-checked .x-form-radio-default:before { + content: "\f192"; +} +.x-form-checkbox-default { + font: 18px/1 ExtJS; + color: #919191; +} +.x-form-checkbox-default:before { + content: "\e614"; +} +.x-form-cb-checked .x-form-checkbox-default { + font: 18px/1 ExtJS; +} +.x-form-cb-checked .x-form-checkbox-default:before { + content: "\e613"; +} +.x-keyboard-mode .x-form-checkbox-focus.x-form-radio-default { + color: #77b0e2; +} +.x-keyboard-mode .x-form-checkbox-focus.x-form-checkbox-default { + color: #77b0e2; +} +.x-keyboard-mode + .x-form-cb-checked + .x-form-checkbox-focus.x-form-radio-default { + color: #77b0e2; +} +.x-keyboard-mode + .x-form-cb-checked + .x-form-checkbox-focus.x-form-checkbox-default { + color: #77b0e2; +} +.x-form-cb-label-default { + margin-top: 8px; + font: 300 13px/17px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #404040; +} +.x-form-cb-label-default.x-form-cb-label-before { + padding-right: 22px; +} +.x-form-cb-label-default.x-form-cb-label-after { + padding-left: 22px; +} +.x-checkbox-default-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +.x-form-item-body-default.x-form-checkboxgroup-body { + padding: 0 4px; +} +.x-form-invalid .x-form-item-body-default.x-form-checkboxgroup-body { + border-width: 1px; + border-style: solid; + border-color: #cf4c35; +} +.x-fieldset-default { + border: 1px solid #d0d0d0; + padding: 5px 15px 10px 15px; + margin: 0 0 10px; +} +.x-ie8 .x-fieldset-default { + padding-top: 0; +} +.x-ie8 .x-fieldset-body-default { + padding-top: 5px; +} +.x-fieldset-header-default { + padding: 10px 5px; + line-height: 20px; +} +.x-fieldset-header-default > .x-fieldset-header-text { + font: 400 16px/20px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #919191; + padding: 1px 0; +} +.x-fieldset-header-checkbox-default { + margin: 2px 4px 0 0; + line-height: 20px; +} +.x-fieldset-header-tool-default { + margin: 2px 4px 0 0; + padding: 0; +} +.x-fieldset-header-tool-default > .x-tool-img { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=80)"; + opacity: 0.8; + height: 15px; + width: 15px; +} +.x-fieldset-header-tool-default.x-tool-over > .x-tool-img { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=90)"; + opacity: 0.9; +} +.x-fieldset-header-tool-default.x-tool-pressed > .x-tool-img { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +.x-fieldset-header-tool-default > .x-tool-toggle { + font: 14px/1 FontAwesome; + color: #919191; +} +.x-fieldset-header-tool-default > .x-tool-toggle:before { + content: "\f146"; +} +.x-keyboard-mode .x-fieldset-header-tool-default.x-focus { + outline: 1px solid #77b0e2; +} +.x-fieldset-default.x-fieldset-collapsed { + border-width: 1px 1px 0 1px; + border-left-color: transparent; + border-right-color: transparent; +} +.x-fieldset-default.x-fieldset-collapsed .x-tool-toggle { + font: 14px/1 FontAwesome; +} +.x-fieldset-default.x-fieldset-collapsed .x-tool-toggle:before { + content: "\f0fe"; +} +.x-form-trigger-spinner-default { + width: 32px; +} +.x-form-trigger-spinner-default:before { + content: ""; +} +.x-form-spinner-default { + background-color: #fff; + width: 32px; + height: 15px; + color: #919191; +} +.x-form-spinner-up-default { + font: 16px/1 ExtJS; +} +.x-form-spinner-up-default:before { + content: "\e61c"; +} +.x-form-spinner-down-default { + font: 16px/1 ExtJS; +} +.x-form-spinner-down-default:before { + content: "\e61b"; +} +.x-form-spinner-up-default { + background-position: 0 0; +} +.x-form-spinner-up-default.x-form-spinner-over { + background-position: -32px 0; +} +.x-form-spinner-up-default.x-form-spinner-over.x-form-spinner-focus { + background-position: -128px 0; +} +.x-form-spinner-up-default.x-form-spinner-focus { + background-position: -96px 0; +} +.x-form-spinner-up-default.x-form-spinner.x-form-spinner-click { + background-position: -64px 0; +} +.x-form-spinner-down-default { + background-position: 0 -15px; +} +.x-form-spinner-down-default.x-form-spinner-over { + background-position: -32px -15px; +} +.x-form-spinner-down-default.x-form-spinner-over.x-form-spinner-focus { + background-position: -128px -15px; +} +.x-form-spinner-down-default.x-form-spinner-focus { + background-position: -96px -15px; +} +.x-form-spinner-down-default.x-form-spinner.x-form-spinner-click { + background-position: -64px -15px; +} +.x-tbar-page-number { + width: 30px; +} +.x-btn-icon-el.x-tbar-page-first { + font: 16px/16px ExtJS; + color: #919191; +} +.x-btn-icon-el.x-tbar-page-first:before { + content: "\e617"; +} +.x-btn-icon-el.x-tbar-page-prev { + font: 16px/16px ExtJS; + color: #919191; +} +.x-btn-icon-el.x-tbar-page-prev:before { + content: "\e615"; +} +.x-btn-icon-el.x-tbar-page-next { + font: 16px/16px ExtJS; + color: #919191; +} +.x-btn-icon-el.x-tbar-page-next:before { + content: "\e616"; +} +.x-btn-icon-el.x-tbar-page-last { + font: 16px/16px ExtJS; + color: #919191; +} +.x-btn-icon-el.x-tbar-page-last:before { + content: "\e618"; +} +.x-btn-icon-el.x-tbar-loading { + font: 16px/16px FontAwesome; + color: #919191; +} +.x-btn-icon-el.x-tbar-loading:before { + content: "\f021"; +} +.x-boundlist { + border-width: 1px; + border-style: solid; + border-color: #d0d0d0; + background: #fff; +} +.x-boundlist-item { + padding: 0 10px; + font: normal 13px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 30px; + cursor: pointer; + cursor: hand; + position: relative; + border-width: 1px; + border-style: dotted; + border-color: #fff; + color: #404040; +} +.x-boundlist-selected { + color: #fff; + background: #5fa2dd; + border-color: #5fa2dd; +} +.x-boundlist-item-over { + color: #fff; + background: #7fb5e4; + border-color: #7fb5e4; +} +.x-boundlist-floating { + border-top-width: 0; +} +.x-boundlist-above { + border-top-width: 1px; + border-bottom-width: 1px; +} +.x-datepicker { + border-width: 1px; + border-style: solid; + border-color: #d0d0d0; + background-color: #fff; + width: 310px; +} +.x-datepicker-header { + padding: 0; + text-align: center; + background-color: #ececec; +} +.x-datepicker-arrow { + width: 32px; + height: 44px; + top: 0px; + cursor: pointer; + -webkit-touch-callout: none; + color: #919191; + background-color: #ececec; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +div.x-datepicker-arrow:hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +.x-datepicker-next { + right: 0; + font: 16px/1 FontAwesome; +} +.x-datepicker-next:before { + content: "\f101"; +} +.x-datepicker-prev { + left: 0; + font: 16px/1 FontAwesome; +} +.x-datepicker-prev:before { + content: "\f100"; +} +.x-datepicker-month { + background: transparent; +} +.x-datepicker-month .x-btn, +.x-datepicker-month .x-btn .x-btn-tc, +.x-datepicker-month .x-btn .x-btn-tl, +.x-datepicker-month .x-btn .x-btn-tr, +.x-datepicker-month .x-btn .x-btn-mc, +.x-datepicker-month .x-btn .x-btn-ml, +.x-datepicker-month .x-btn .x-btn-mr, +.x-datepicker-month .x-btn .x-btn-bc, +.x-datepicker-month .x-btn .x-btn-bl, +.x-datepicker-month .x-btn .x-btn-br { + background: transparent; + border-width: 0 !important; +} +.x-datepicker-month .x-btn-inner { + color: #404040; +} +.x-datepicker-month .x-btn-split-right:after, +.x-datepicker-month .x-btn-over .x-btn-split-right:after { + content: "\f107"; + font: 16px/1 FontAwesome; + color: #606060; + background: none; + padding: 0; + text-align: right; + width: 16px; +} +.x-datepicker-month .x-btn { + padding: 14px; +} +.x-datepicker-month .x-btn-over { + border-color: transparent; + background: #dfdfdf; +} +.x-datepicker-month .x-btn.x-btn-pressed { + border-color: transparent; + background: #d3d3d3; +} +.x-datepicker-month .x-btn-inner { + font-size: 15px; +} +.x-datepicker-column-header { + width: 44px; + color: #404040; + font: 400 13px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + text-align: right; + background-color: #ececec; +} +.x-datepicker-column-header-inner { + line-height: 36px; + padding: 0 15px 0 0; +} +.x-datepicker-cell { + text-align: right; + border: 0; +} +.x-datepicker-date { + padding: 0 15px 0 0; + font: 300 13px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #404040; + cursor: pointer; + line-height: 36px; +} +div.x-datepicker-date:hover { + color: #404040; + background-color: #ececec; +} +.x-datepicker-selected { + border-style: solid; + border-color: #7fb5e4; +} +.x-datepicker-selected div.x-datepicker-date { + background-color: #5fa2dd; + color: #fff; + font-weight: 300; +} +.x-datepicker-today { + border-color: darkred; + border-style: solid; + background-color: #bfdaf1; +} +.x-datepicker-prevday .x-datepicker-date, +.x-datepicker-nextday .x-datepicker-date { + color: #d0d0d0; +} +.x-datepicker-disabled .x-datepicker-date { + background-color: #eee; + cursor: default; + color: silver; +} +.x-datepicker-disabled div.x-datepicker-date:hover { + background-color: #eee; + color: silver; +} +.x-datepicker-footer, +.x-monthpicker-buttons { + padding: 6px 0; + background-color: #fff; + text-align: center; +} +.x-datepicker-footer .x-btn, +.x-monthpicker-buttons .x-btn { + margin: 0 3px 0 2px; +} +.x-monthpicker { + width: 310px; + border-width: 1px; + border-style: solid; + border-color: #d0d0d0; + background-color: #fff; +} +.x-monthpicker-months { + border-width: 0 1px 0 0; + border-color: #d0d0d0; + border-style: solid; + width: 154px; +} +.x-monthpicker-months .x-monthpicker-item { + width: 76px; +} +.x-monthpicker-years { + width: 154px; +} +.x-monthpicker-years .x-monthpicker-item { + width: 77px; +} +.x-monthpicker-item { + margin: 5px 0 5px; + font: 300 13px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + text-align: center; +} +.x-monthpicker-item-inner { + margin: 0 5px 0 5px; + color: #404040; + border: 0; + line-height: 37px; + cursor: pointer; +} +a.x-monthpicker-item-inner:hover { + color: #404040; + background-color: #ececec; +} +.x-monthpicker-item a.x-monthpicker-selected { + background-color: #5fa2dd; + color: #fff; + border-style: solid; + border-color: #7fb5e4; +} +.x-monthpicker-yearnav { + height: 47px; +} +.x-monthpicker-yearnav-button-ct { + width: 77px; +} +.x-monthpicker-yearnav-button { + height: 16px; + width: 16px; + cursor: pointer; + margin-top: 15px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; + -webkit-touch-callout: none; + color: #919191; + background-color: #fff; +} +a.x-monthpicker-yearnav-button:hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +.x-monthpicker-yearnav-next { + font: 16px/1 FontAwesome; +} +.x-monthpicker-yearnav-next:before { + content: "\f101"; +} +.x-monthpicker-yearnav-prev { + font: 16px/1 FontAwesome; +} +.x-monthpicker-yearnav-prev:before { + content: "\f100"; +} +.x-monthpicker-small .x-monthpicker-item { + margin: 2px 0 2px; +} +.x-monthpicker-small .x-monthpicker-item-inner { + margin: 0 5px 0 5px; +} +.x-monthpicker-small .x-monthpicker-yearnav { + height: 41px; +} +.x-monthpicker-small .x-monthpicker-yearnav-button { + margin-top: 12px; +} +.x-form-field-date .x-form-date-trigger { + font-size: 16px; + font-family: FontAwesome; +} +.x-form-field-date .x-form-date-trigger:before { + content: "\f073"; +} +.x-form-display-field-default { + min-height: 32px; + font: 300 13px/17px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #404040; + margin-top: 8px; +} +.x-keyboard-mode .x-form-display-field-default.x-field-form-focus { + outline: 1px solid #77b0e2; + outline-offset: -1px; +} +.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus, +.x-ie10p .x-keyboard-mode .x-form-display-field-default.x-field-form-focus, +.x-edge .x-keyboard-mode .x-form-display-field-default.x-field-form-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-form-display-field-default.x-field-form-focus:after, +.x-ie10p + .x-keyboard-mode + .x-form-display-field-default.x-field-form-focus:after, +.x-edge + .x-keyboard-mode + .x-form-display-field-default.x-field-form-focus:after { + position: absolute; + content: " "; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + border: 1px solid #77b0e2; + pointer-events: none; +} +.x-ie8 .x-form-display-field-default.x-field-form-focus { + position: relative; +} +.x-tip-default { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #747474; +} +.x-tip-default-mc { + background-color: #747474; +} +.x-nbr .x-tip-default { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tip-default-frameInfo { + font-family: th-2-2-2-2-1-1-1-1-1-1-1-1; +} +.x-tip-default-tl { + background-position: 0 -4px; +} +.x-tip-default-tr { + background-position: right -6px; +} +.x-tip-default-bl { + background-position: 0 -8px; +} +.x-tip-default-br { + background-position: right -10px; +} +.x-tip-default-ml { + background-position: 0 top; +} +.x-tip-default-mr { + background-position: right top; +} +.x-tip-default-tc { + background-position: 0 0; +} +.x-tip-default-bc { + background-position: 0 -2px; +} +.x-tip-default-tr, +.x-tip-default-br, +.x-tip-default-mr { + padding-right: 2px; +} +.x-tip-default-tl, +.x-tip-default-bl, +.x-tip-default-ml { + padding-left: 2px; +} +.x-tip-default-tc { + height: 2px; +} +.x-tip-default-bc { + height: 2px; +} +.x-tip-default-tl, +.x-tip-default-bl, +.x-tip-default-tr, +.x-tip-default-br, +.x-tip-default-tc, +.x-tip-default-bc, +.x-tip-default-ml, +.x-tip-default-mr { + background-image: url(images/tip/tip-default-corners.gif); +} +.x-tip-default-ml, +.x-tip-default-mr { + background-image: url(images/tip/tip-default-sides.gif); + background-repeat: repeat-y; +} +.x-tip-default-mc { + padding: 0px 0px 0px 0px; +} +.x-tip-default { + background-color: #747474; + border-color: #747474; +} +.x-tip-default .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #747474; +} +.x-tip-header-default .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-tip-header-default .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-tip-header-default { + padding: 3px 3px 0 3px; +} +.x-tip-header-title-default { + color: #f0f0f0; + font-size: 13px; + font-weight: bold; +} +.x-tip-body-default { + padding: 6px 8px; + color: #f0f0f0; + font-size: 13px; + font-weight: 300; +} +.x-tip-body-default a { + color: #f0f0f0; +} +.x-tip-default .x-tip-anchor { + border: 10px solid transparent; + _border-color: pink; + _filter: chroma(color=pink); +} +.x-tip-default .x-tip-anchor-top { + border-top-width: 0; + border-bottom: 10px solid #747474; + top: -10px; +} +.x-tip-default .x-tip-anchor-bottom { + border-bottom-width: 0; + border-top: 10px solid #747474; + bottom: -10px; +} +.x-tip-default .x-tip-anchor-left { + border-left-width: 0; + border-right: 10px solid #747474; + left: -10px; +} +.x-tip-default .x-tip-anchor-right { + border-right-width: 0; + border-left: 10px solid #747474; + right: -10px; +} +.x-tip-form-invalid { + -webkit-border-radius: 2px; + -moz-border-radius: 2px; + -ms-border-radius: 2px; + -o-border-radius: 2px; + border-radius: 2px; + padding: 1px 1px 1px 1px; + border-width: 1px; + border-style: solid; + background-color: #747474; +} +.x-tip-form-invalid-mc { + background-color: #747474; +} +.x-nbr .x-tip-form-invalid { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tip-form-invalid-frameInfo { + font-family: th-2-2-2-2-1-1-1-1-1-1-1-1; +} +.x-tip-form-invalid-tl { + background-position: 0 -4px; +} +.x-tip-form-invalid-tr { + background-position: right -6px; +} +.x-tip-form-invalid-bl { + background-position: 0 -8px; +} +.x-tip-form-invalid-br { + background-position: right -10px; +} +.x-tip-form-invalid-ml { + background-position: 0 top; +} +.x-tip-form-invalid-mr { + background-position: right top; +} +.x-tip-form-invalid-tc { + background-position: 0 0; +} +.x-tip-form-invalid-bc { + background-position: 0 -2px; +} +.x-tip-form-invalid-tr, +.x-tip-form-invalid-br, +.x-tip-form-invalid-mr { + padding-right: 2px; +} +.x-tip-form-invalid-tl, +.x-tip-form-invalid-bl, +.x-tip-form-invalid-ml { + padding-left: 2px; +} +.x-tip-form-invalid-tc { + height: 2px; +} +.x-tip-form-invalid-bc { + height: 2px; +} +.x-tip-form-invalid-tl, +.x-tip-form-invalid-bl, +.x-tip-form-invalid-tr, +.x-tip-form-invalid-br, +.x-tip-form-invalid-tc, +.x-tip-form-invalid-bc, +.x-tip-form-invalid-ml, +.x-tip-form-invalid-mr { + background-image: url(images/tip/tip-form-invalid-corners.gif); +} +.x-tip-form-invalid-ml, +.x-tip-form-invalid-mr { + background-image: url(images/tip/tip-form-invalid-sides.gif); + background-repeat: repeat-y; +} +.x-tip-form-invalid-mc { + padding: 0px 0px 0px 0px; +} +.x-tip-form-invalid { + background-color: #747474; + border-color: #747474; +} +.x-tip-form-invalid .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-color: #747474; +} +.x-tip-header-form-invalid .x-tool-after-title { + margin: 0 0 0 6px; +} +.x-tip-header-form-invalid .x-tool-before-title { + margin: 0 6px 0 0; +} +.x-tip-header-form-invalid { + padding: 3px 3px 0 3px; +} +.x-tip-header-title-form-invalid { + color: #f0f0f0; + font-size: 13px; + font-weight: bold; +} +.x-tip-body-form-invalid { + padding: 3px 3px 3px 22px; + color: #f0f0f0; + font-size: 13px; + font-weight: 300; +} +.x-tip-body-form-invalid a { + color: #f0f0f0; +} +.x-tip-form-invalid .x-tip-anchor { + border: 10px solid transparent; + _border-color: pink; + _filter: chroma(color=pink); +} +.x-tip-form-invalid .x-tip-anchor-top { + border-top-width: 0; + border-bottom: 10px solid #747474; + top: -10px; +} +.x-tip-form-invalid .x-tip-anchor-bottom { + border-bottom-width: 0; + border-top: 10px solid #747474; + bottom: -10px; +} +.x-tip-form-invalid .x-tip-anchor-left { + border-left-width: 0; + border-right: 10px solid #747474; + left: -10px; +} +.x-tip-form-invalid .x-tip-anchor-right { + border-right-width: 0; + border-left: 10px solid #747474; + right: -10px; +} +.x-tip-body-form-invalid { + background: 1px 1px no-repeat; + background-image: url(images/form/exclamation.png); +} +.x-tip-body-form-invalid li { + margin-bottom: 4px; +} +.x-tip-body-form-invalid li.last { + margin-bottom: 0; +} +.x-color-picker { + width: 192px; + height: 120px; + background-color: #fff; + border-color: #fff; + border-width: 0; + border-style: solid; +} +.x-color-picker-item { + width: 24px; + height: 24px; + border-width: 1px; + border-color: #fff; + border-style: solid; + background-color: #fff; + cursor: pointer; + padding: 2px; +} +a.x-color-picker-item:hover { + border-color: #8bb8f3; + background-color: #d9d9d9; +} +.x-color-picker-selected { + border-color: #8bb8f3; + background-color: #d9d9d9; +} +.x-color-picker-item-inner { + line-height: 16px; + border-color: #d0d0d0; + border-width: 1px; + border-style: solid; +} +.x-html-editor-tb .x-btn-icon-el { + color: #919191; +} +.x-html-editor-tb .x-edit-bold, +.x-menu-item div.x-edit-bold { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-bold:before, +.x-menu-item div.x-edit-bold:before { + content: "\f032"; +} +.x-html-editor-tb .x-edit-italic, +.x-menu-item div.x-edit-italic { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-italic:before, +.x-menu-item div.x-edit-italic:before { + content: "\f033"; +} +.x-html-editor-tb .x-edit-underline, +.x-menu-item div.x-edit-underline { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-underline:before, +.x-menu-item div.x-edit-underline:before { + content: "\f0cd"; +} +.x-html-editor-tb .x-edit-forecolor, +.x-menu-item div.x-edit-forecolor { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-forecolor:before, +.x-menu-item div.x-edit-forecolor:before { + content: "\e60e"; +} +.x-html-editor-tb .x-edit-backcolor, +.x-menu-item div.x-edit-backcolor { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-backcolor:before, +.x-menu-item div.x-edit-backcolor:before { + content: "\e60d"; +} +.x-html-editor-tb .x-edit-justifyleft, +.x-menu-item div.x-edit-justifyleft { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-justifyleft:before, +.x-menu-item div.x-edit-justifyleft:before { + content: "\f036"; +} +.x-html-editor-tb .x-edit-justifycenter, +.x-menu-item div.x-edit-justifycenter { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-justifycenter:before, +.x-menu-item div.x-edit-justifycenter:before { + content: "\f037"; +} +.x-html-editor-tb .x-edit-justifyright, +.x-menu-item div.x-edit-justifyright { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-justifyright:before, +.x-menu-item div.x-edit-justifyright:before { + content: "\f038"; +} +.x-html-editor-tb .x-edit-insertorderedlist, +.x-menu-item div.x-edit-insertorderedlist { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-insertorderedlist:before, +.x-menu-item div.x-edit-insertorderedlist:before { + content: "\f0cb"; +} +.x-html-editor-tb .x-edit-insertunorderedlist, +.x-menu-item div.x-edit-insertunorderedlist { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-insertunorderedlist:before, +.x-menu-item div.x-edit-insertunorderedlist:before { + content: "\f0ca"; +} +.x-html-editor-tb .x-edit-increasefontsize, +.x-menu-item div.x-edit-increasefontsize { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-increasefontsize:before, +.x-menu-item div.x-edit-increasefontsize:before { + content: "\e610"; +} +.x-html-editor-tb .x-edit-decreasefontsize, +.x-menu-item div.x-edit-decreasefontsize { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-decreasefontsize:before, +.x-menu-item div.x-edit-decreasefontsize:before { + content: "\e60f"; +} +.x-html-editor-tb .x-edit-sourceedit, +.x-menu-item div.x-edit-sourceedit { + font: 16px/1 ExtJS; + background: none; +} +.x-html-editor-tb .x-edit-sourceedit:before, +.x-menu-item div.x-edit-sourceedit:before { + content: "\e604"; +} +.x-html-editor-tb .x-edit-createlink, +.x-menu-item div.x-edit-createlink { + font: 16px/1 FontAwesome; + background: none; +} +.x-html-editor-tb .x-edit-createlink:before, +.x-menu-item div.x-edit-createlink:before { + content: "\f0c1"; +} +.x-html-editor-tip .x-tip-bd .x-tip-bd-inner { + padding: 5px; + padding-bottom: 1px; +} +.x-html-editor-tb .x-font-select { + font-size: 13px; + font-family: inherit; +} +.x-html-editor-wrap textarea { + font: 300 13px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + background-color: #fff; + resize: none; +} +.x-htmleditor-iframe { + background-color: #fff; +} +.x-form-text-default.x-tagfield { + padding: 3px 0 0 4px; +} +.x-form-text-default .x-tagfield-input { + margin: 0 4px 3px 0; +} +.x-form-text-default .x-tagfield-input-field { + height: 24px; + line-height: 24px; +} +.x-form-text-default .x-tagfield-item { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + background-color: #ececec; + border: 1px solid #ececec; + padding: 0 21px 0 5px; + margin: 0 4px 3px 0; + color: #404040; + line-height: 22px; +} +.x-form-text-default .x-tagfield-item:hover { + background-color: #e5e5e5; + border-color: #e5e5e5; + color: #404040; +} +.x-form-text-default .x-tagfield-item.x-tagfield-item-selected { + background-color: #7fb5e4; + border-color: #7fb5e4; + color: #fff; +} +.x-form-text-default .x-tagfield-item-close { + width: 12px; + height: 12px; + top: 5px; + right: 3px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=85)"; + opacity: 0.85; + font: 12px/1 FontAwesome; + color: #919191; +} +.x-form-text-default .x-tagfield-item-close:before { + content: "\f00d"; +} +.x-form-text-default .x-tagfield-item-close:hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=93)"; + opacity: 0.93; + color: #919191; +} +.x-form-text-default .x-tagfield-item-close:active { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close { + color: #fff; +} +.x-form-text-default .x-tagfield-item-selected .x-tagfield-item-close:hover { + color: #fff; +} +.x-grid-view, +.x-tree-view { + z-index: 1; +} +.x-theme-row-height-el { + height: 32px; +} +.x-grid-body { + background: #fff; + border-width: 2px 1px 1px; + border-style: solid; + border-color: #d0d0d0; +} +.x-grid-empty { + padding: 10px; + color: grey; + background-color: #fff; + font: 300 13px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; +} +.x-grid-item { + color: #404040; + font: 300 13px/19px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + background-color: #fff; +} +.x-grid-item-alt { + background-color: #f6f6f6; +} +.x-grid-item-over { + color: #404040; + background-color: #eaeff4; +} +.x-grid-item-focused { + outline: 0; +} +.x-grid-item-focused .x-grid-cell-inner { + z-index: 1; +} +.x-keyboard-mode .x-grid-item-focused { + color: #404040; +} +.x-keyboard-mode .x-grid-item-focused .x-grid-cell-inner:before { + content: ""; + position: absolute; + z-index: -1; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + pointer-events: none; + border: 1px solid #5fa2dd; +} +.x-grid-item-selected { + color: #404040; + background-color: #ffefbb; +} +.x-grid-with-row-lines .x-grid-item { + border-style: solid; + border-width: 1px 0 0; + border-color: #e9e9e9; +} +.x-grid-with-row-lines .x-grid-item:first-child { + border-top-color: #fff; +} +.x-grid-with-row-lines .x-grid-item.x-grid-item-over { + border-style: solid; + border-color: #dee3e8; +} +.x-grid-with-row-lines .x-grid-item-over + .x-grid-item { + border-top-style: solid; + border-top-color: #dee3e8; +} +.x-grid-with-row-lines .x-grid-item.x-grid-item-selected { + border-style: solid; + border-color: #f2e3b2; +} +.x-grid-with-row-lines .x-grid-item-selected + .x-grid-item { + border-top-style: solid; + border-top-color: #f2e3b2; +} +.x-grid-with-row-lines .x-grid-item:last-child { + border-bottom-width: 1px; +} +.x-ie8 .x-grid-with-row-lines .x-grid-item { + border-width: 1px 0; + margin-top: -1px; +} +.x-ie8 .x-grid-with-row-lines .x-grid-item:first-child { + margin-top: 0; +} +.x-grid-cell-inner { + position: relative; + text-overflow: ellipsis; + padding: 7px 10px 6px; +} +.x-grid-cell-special { + border-color: #e9e9e9; + border-style: solid; + border-right-width: 1px; +} +.x-grid-dirty-cell > .x-grid-cell-inner:after { + content: "\e602"; + font: 14px/1 ExtJS; + color: #cf4c35; + position: absolute; + top: 0; + left: 0; +} +.x-grid-row .x-grid-cell-selected { + color: #404040; + background-color: #ffefbb; +} +.x-grid-with-col-lines .x-grid-cell { + border-style: solid; + border-color: #e9e9e9; + border-width: 0 1px 0 0; +} +.x-grid-with-col-lines .x-grid-item-over .x-grid-cell { + border-color: #dee3e8; + border-style: solid; +} +.x-grid-with-col-lines .x-grid-item-selected .x-grid-cell { + border-color: #f2e3b2; + border-style: solid; +} +.x-grid-resize-marker { + width: 1px; + background-color: #0f0f0f; +} +.x-grid-drop-indicator { + position: absolute; + height: 1px; + line-height: 0px; + background-color: #77bc71; + overflow: visible; + pointer-events: none; +} +.x-grid-drop-indicator .x-grid-drop-indicator-left { + position: absolute; + top: -8px; + left: -12px; + background-image: url(images/grid/dd-insert-arrow-right.png); + height: 16px; + width: 16px; +} +.x-grid-drop-indicator .x-grid-drop-indicator-right { + position: absolute; + top: -8px; + right: -11px; + background-image: url(images/grid/dd-insert-arrow-left.png); + height: 16px; + width: 16px; +} +.x-col-move-top, +.x-col-move-bottom { + width: 9px; + height: 9px; +} +.x-col-move-top { + background-image: url(images/grid/col-move-top.png); +} +.x-col-move-bottom { + background-image: url(images/grid/col-move-bottom.png); +} +.x-grid-header-ct { + border: 1px solid #d0d0d0; + border-bottom-color: #fff; + background-color: #fff; +} +.x-accordion-item .x-grid-header-ct { + border-width: 0 0 1px !important; +} +.x-grid-header-ct-hidden { + border-top: 0 !important; + border-bottom: 0 !important; +} +.x-grid-body { + border-top-color: #d0d0d0; +} +.x-hmenu-sort-asc { + font: 16px/24px ExtJS; +} +.x-hmenu-sort-asc:before { + content: "\e61a"; +} +.x-hmenu-sort-desc { + font: 16px/24px ExtJS; +} +.x-hmenu-sort-desc:before { + content: "\e619"; +} +.x-cols-icon { + font: 16px/24px ExtJS; +} +.x-cols-icon:before { + content: "\e601"; +} +.x-column-header { + border-right: 1px solid #d0d0d0; + color: #404040; + font: 400 13px/19px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + outline: 0; + background-color: #fff; +} +.x-group-sub-header { + background: transparent; + border-top: 1px solid #d0d0d0; +} +.x-group-sub-header .x-column-header-inner { + padding: 6px 10px 6px 10px; +} +.x-column-header-inner { + padding: 7px 10px 6px; +} +.x-column-header-inner-empty { + text-overflow: clip; +} +.x-keyboard-mode .x-column-header.x-column-header-focus { + color: #404040; +} +.x-keyboard-mode + .x-column-header.x-column-header-focus + .x-column-header-inner:after { + content: ""; + position: absolute; + z-index: 5; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + border: 1px solid #7fb5e4; + pointer-events: none; +} +.x-keyboard-mode + .x-column-header.x-column-header-focus.x-group-sub-header + .x-column-header-inner:before { + bottom: 0px; +} +.x-column-header-over { + background-image: none; + background-color: #eaeff4; +} +.x-column-header-sort-ASC, +.x-column-header-sort-DESC { + background-image: none; + background-color: #fff; +} +.x-column-header-open { + background-color: #eaeff4; +} +.x-column-header-open .x-column-header-trigger { + background-color: #dee3e8; +} +.x-column-header-over .x-column-header-trigger, +.x-column-header-open .x-column-header-trigger { + width: 24px; + cursor: pointer; + font: 16px/1 FontAwesome; + color: #919191; +} +.x-column-header-over .x-column-header-trigger:before, +.x-column-header-open .x-column-header-trigger:before { + content: "\f0d7"; +} +.x-column-header-over .x-column-header-trigger:before, +.x-column-header-open .x-column-header-trigger:before { + top: 50%; + margin-top: -8px; + text-align: center; + position: relative; + display: block; +} +.x-column-header-align-right .x-column-header-text { + margin-right: 18px; +} +.x-column-header-sort-ASC .x-column-header-text-inner, +.x-column-header-sort-DESC .x-column-header-text-inner { + background-position: right center; +} +.x-column-header-sort-ASC .x-column-header-text-inner:after, +.x-column-header-sort-DESC .x-column-header-text-inner:after { + display: inline-block; + text-align: center; + margin-left: 5px; + width: 14px; +} +.x-column-header-sort-ASC .x-column-header-text-inner:after { + content: "\f176"; + font: 14px/1 FontAwesome; + color: #919191; +} +.x-column-header-sort-DESC .x-column-header-text-inner:after { + content: "\f175"; + font: 14px/1 FontAwesome; + color: #919191; +} +.x-no-header-borders .x-column-header { + border: 0 none; +} +.x-no-header-borders .x-column-header .x-column-header-inner { + padding-top: 7px; +} +.x-grid-cell-inner-action-col { + padding: 7px 4px 7px 4px; +} +.x-action-col-cell .x-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +.x-action-col-icon { + color: #919191; + font-size: 18px; + height: 18px; + width: 18px; + cursor: pointer; +} +.x-column-header-checkbox .x-column-header-inner, +.x-grid-checkcolumn-cell-inner { + padding: 7px 4px 7px 4px; + text-overflow: clip; +} +.x-column-header-checkbox { + border-color: #fff; +} +.x-column-header-checkbox .x-column-header-text { + overflow: visible; +} +.x-column-header-checkbox .x-column-header-checkbox:after, +.x-grid-checkcolumn:after { + content: "\e614"; + font: 18px/1 ExtJS; + color: #919191; +} +.x-item-disabled .x-column-header-checkbox .x-column-header-checkbox, +.x-item-disabled .x-grid-checkcolumn { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +.x-grid-hd-checker-on .x-column-header-checkbox:after, +.x-grid-checkcolumn-checked:after { + content: "\e613"; + font: 18px/1 ExtJS; + color: #919191; +} +.x-grid-item-selected .x-selmodel-column .x-grid-checkcolumn:after { + content: "\e613"; + font: 18px/1 ExtJS; + color: #919191; +} +.x-gecko .x-selmodel-checkbox .x-grid-checkcolumn { + pointer-events: none; +} +.x-grid-cell-row-numberer { + background-color: #fff; +} +.x-grid-cell-inner-row-numberer { + padding: 7px 5px 6px 3px; +} +.x-btn-grid-cell-small { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 7px 7px 7px 7px; + border-width: 1px; + border-style: solid; + background-color: #5fa2dd; +} +.x-btn-grid-cell-small-mc { + background-color: #5fa2dd; +} +.x-nbr .x-btn-grid-cell-small { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-btn-grid-cell-small-frameInfo { + font-family: th-1-1-1-1-1-1-1-1-7-7-7-7; +} +.x-btn-grid-cell-small-tl { + background-position: 0 -2px; +} +.x-btn-grid-cell-small-tr { + background-position: right -3px; +} +.x-btn-grid-cell-small-bl { + background-position: 0 -4px; +} +.x-btn-grid-cell-small-br { + background-position: right -5px; +} +.x-btn-grid-cell-small-ml { + background-position: 0 top; +} +.x-btn-grid-cell-small-mr { + background-position: right top; +} +.x-btn-grid-cell-small-tc { + background-position: 0 0; +} +.x-btn-grid-cell-small-bc { + background-position: 0 -1px; +} +.x-btn-grid-cell-small-tr, +.x-btn-grid-cell-small-br, +.x-btn-grid-cell-small-mr { + padding-right: 1px; +} +.x-btn-grid-cell-small-tl, +.x-btn-grid-cell-small-bl, +.x-btn-grid-cell-small-ml { + padding-left: 1px; +} +.x-btn-grid-cell-small-tc { + height: 1px; +} +.x-btn-grid-cell-small-bc { + height: 1px; +} +.x-btn-grid-cell-small-tl, +.x-btn-grid-cell-small-bl, +.x-btn-grid-cell-small-tr, +.x-btn-grid-cell-small-br, +.x-btn-grid-cell-small-tc, +.x-btn-grid-cell-small-bc, +.x-btn-grid-cell-small-ml, +.x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-corners.gif); +} +.x-btn-grid-cell-small-ml, +.x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-sides.gif); + background-repeat: repeat-y; +} +.x-btn-grid-cell-small-mc { + padding: 7px 7px 7px 7px; +} +.x-btn-grid-cell-small { + border-color: #5897ce; +} +.x-btn-button-grid-cell-small { + min-height: 16px; +} +.x-ie9m .x-btn-button-grid-cell-small { + min-height: auto; + height: 16px; +} +.x-btn-inner-grid-cell-small { + font: 400 12px/16px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + padding: 0 5px; + max-width: 100%; +} +.x-ie9 .x-btn-icon-right > .x-btn-inner-grid-cell-small, +.x-ie9 .x-btn-icon-left > .x-btn-inner-grid-cell-small { + max-width: calc(100% - 16px); +} +.x-safari8m .x-btn-icon-right > .x-btn-inner-grid-cell-small, +.x-safari8m .x-btn-icon-left > .x-btn-inner-grid-cell-small { + max-width: calc(100% - 15px); +} +.x-ie10p .x-btn-inner-grid-cell-small { + max-width: none; +} +.x-btn-icon-el-grid-cell-small { + font-size: 16px; + height: 16px; + color: #f0f0f0; + line-height: 16px; +} +.x-btn-icon-left > .x-btn-icon-el-grid-cell-small, +.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + width: 16px; +} +.x-btn-icon-top > .x-btn-icon-el-grid-cell-small, +.x-btn-icon-bottom > .x-btn-icon-el-grid-cell-small { + min-width: 16px; +} +.x-ie8 .x-btn-icon-el-grid-cell-small.x-btn-glyph { + color: #f0f0f0; +} +.x-btn-text.x-btn-icon-left > .x-btn-icon-el-grid-cell-small { + margin-right: 3px; +} +.x-btn-text.x-btn-icon-right > .x-btn-icon-el-grid-cell-small { + margin-left: 3px; +} +.x-btn-text.x-btn-icon-top > .x-btn-icon-el-grid-cell-small { + margin-bottom: 8px; +} +.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-grid-cell-small { + margin-top: 8px; +} +.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-grid-cell-small { + padding-right: 8px; +} +.x-btn-arrow-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-grid-cell-small { + margin-right: 5px; +} +.x-btn-arrow-bottom > .x-btn-button-grid-cell-small, +.x-btn-split-bottom > .x-btn-button-grid-cell-small { + padding-bottom: 7px; +} +.x-btn-wrap-grid-cell-small.x-btn-arrow-right:after { + width: 8px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-grid-cell-small.x-btn-arrow-bottom:after { + height: 8px; + content: "\f0d7"; + font: 16px/8px FontAwesome; + color: #f0f0f0; +} +.x-btn-wrap-grid-cell-small.x-btn-split-right > .x-btn-button { + padding-right: 7px; +} +.x-btn-wrap-grid-cell-small.x-btn-split-right > .x-btn-button:after { + border-right: 1px solid #f0f0f0; +} +.x-btn-wrap-grid-cell-small.x-btn-split-right:after { + width: 14px; + content: "\f0d7"; + font: 16px/1 FontAwesome; + color: #f0f0f0; + padding-left: 7px; +} +.x-btn-wrap-grid-cell-small.x-btn-split-bottom { + margin-bottom: -7px; +} +.x-btn-wrap-grid-cell-small.x-btn-split-bottom > .x-btn-button:after { + border-bottom: 1px solid #f0f0f0; +} +.x-btn-wrap-grid-cell-small.x-btn-split-bottom:after { + height: 14px; + content: "\f0d7"; + font: 16px/14px FontAwesome; + color: #f0f0f0; +} +.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-grid-cell-small { + padding-right: 8px; +} +.x-btn-split-right + > .x-btn-text.x-btn-icon-right + > .x-btn-icon-el-grid-cell-small { + margin-right: 5px; +} +.x-keyboard-mode .x-btn-focus.x-btn-grid-cell-small { + background-image: none; + background-color: #5fa2dd; +} +.x-btn-grid-cell-small .x-btn-arrow-el { + position: absolute; + top: 0; + right: 0; + height: 100%; + width: 21px; + pointer-events: none; +} +.x-btn-over.x-btn-grid-cell-small { + border-color: #518bbd; + background-image: none; + background-color: #5795cb; +} +.x-btn.x-btn-menu-active.x-btn-grid-cell-small, +.x-btn.x-btn-pressed.x-btn-grid-cell-small { + border-color: #42719a; + background-image: none; + background-color: #477aa6; +} +.x-btn.x-btn-disabled.x-btn-grid-cell-small { + background-image: none; + background-color: #5fa2dd; +} +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-focus-corners.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-focus-sides.gif); +} +.x-keyboard-mode .x-btn-focus .x-btn-grid-cell-small-mc { + background-color: #5fa2dd; +} +.x-btn-over .x-btn-grid-cell-small-tl, +.x-btn-over .x-btn-grid-cell-small-bl, +.x-btn-over .x-btn-grid-cell-small-tr, +.x-btn-over .x-btn-grid-cell-small-br, +.x-btn-over .x-btn-grid-cell-small-tc, +.x-btn-over .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-over-corners.gif); +} +.x-btn-over .x-btn-grid-cell-small-ml, +.x-btn-over .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-over-sides.gif); +} +.x-btn-over .x-btn-grid-cell-small-mc { + background-color: #5795cb; +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-focus-over-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-focus-over-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-grid-cell-small-mc { + background-color: #5795cb; +} +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tl, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-bl, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tr, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-br, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-tc, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-bc, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-tl, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-bl, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-tr, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-br, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-tc, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-pressed-corners.gif); +} +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-ml, +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-mr, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-ml, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-pressed-sides.gif); +} +.x-btn.x-btn-menu-active .x-btn-grid-cell-small-mc, +.x-btn.x-btn-pressed .x-btn-grid-cell-small-mc { + background-color: #477aa6; +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-bc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-bl, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-br, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-tc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-focus-pressed-corners.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-mr, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-ml, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-focus-pressed-sides.gif); +} +.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-grid-cell-small-mc, +.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-grid-cell-small-mc { + background-color: #477aa6; +} +.x-btn.x-btn-disabled .x-btn-grid-cell-small-tl, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-bl, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-tr, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-br, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-tc, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-bc { + background-image: url(images/btn/btn-grid-cell-small-disabled-corners.gif); +} +.x-btn.x-btn-disabled .x-btn-grid-cell-small-ml, +.x-btn.x-btn-disabled .x-btn-grid-cell-small-mr { + background-image: url(images/btn/btn-grid-cell-small-disabled-sides.gif); +} +.x-btn.x-btn-disabled .x-btn-grid-cell-small-mc { + background-color: #5fa2dd; +} +.x-nbr .x-btn-grid-cell-small { + background-image: none; +} +.x-btn-disabled.x-btn-grid-cell-small { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first + .x-btn-grid-cell-small-mc { + padding-right: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-middle { + border-right-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-middle + .x-btn-grid-cell-small-mc { + padding-right: 7px !important; + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-last + .x-btn-grid-cell-small-mc { + padding-left: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first + .x-btn-grid-cell-small-mc { + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-middle { + border-bottom-width: 1px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-middle + .x-btn-grid-cell-small-mc { + padding-top: 7px !important; + padding-bottom: 7px !important; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-last + .x-btn-grid-cell-small-mc { + padding-top: 7px !important; +} +.x-nbr .x-segmented-button-item.x-btn-grid-cell-small:after { + content: " "; + border-style: solid; + border-width: 0; + position: absolute; +} +.x-nbr .x-segmented-button-item-horizontal.x-btn-grid-cell-small:after { + top: 1px; + right: 0; + bottom: 1px; + left: 0; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-first:after { + left: 1px; +} +.x-nbr + .x-segmented-button-item-horizontal.x-btn-grid-cell-small.x-segmented-button-last:after { + right: 1px; +} +.x-nbr .x-segmented-button-item-vertical.x-btn-grid-cell-small:after { + top: 0; + right: 1px; + bottom: 0; + left: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-first:after { + top: 1px; +} +.x-nbr + .x-segmented-button-item-vertical.x-btn-grid-cell-small.x-segmented-button-last:after { + bottom: 1px; +} +.x-button-grid-cell-small-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +.x-button-grid-cell-small-cell > .x-grid-cell-inner > .x-btn-grid-cell-small { + vertical-align: top; +} +.x-grid-widgetcolumn-cell-inner { + text-overflow: clip; +} +.x-grid-group-hd { + border-width: 0 0 1px 0; + border-style: solid; + border-color: #d0d0d0; + padding: 8px 10px; + background: #fff; + cursor: pointer; +} +.x-grid-group-hd-not-collapsible { + cursor: default; +} +.x-grid-group-hd-collapsible .x-grid-group-title { + padding: 0 0 0 24px; +} +.x-grid-group-hd-collapsible .x-grid-group-title:before { + content: "\f146"; + font-size: 14px; + font-family: FontAwesome; + color: #919191; +} +.x-grid-group-title { + color: #606060; + font: 400 13px/15px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; +} +.x-grid-group-hd-collapsed .x-grid-group-title:before { + content: "\f0fe"; + font-size: 14px; + font-family: FontAwesome; + color: #919191; +} +.x-group-by-icon { + font: 16px/24px ExtJS; +} +.x-group-by-icon:before { + content: "\e607"; +} +.x-grid-rowbody { + font: 300 13px/19px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + padding: 5px 10px 5px 10px; +} +.x-docked-summary { + border-width: 1px; + border-color: #d0d0d0; + border-style: solid; + background: #fff !important; +} +.x-docked-summary .x-grid-table { + border: 0 none; +} +.x-grid-row-summary .x-grid-cell, +.x-grid-row-summary .x-grid-rowwrap, +.x-grid-row-summary .x-grid-cell-rowbody { + border-color: #e9e9e9; + background-color: #fff !important; + border-top: 1px solid #e9e9e9; + font: 300 13px/19px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; +} +.x-docked-summary .x-grid-item, +.x-docked-summary .x-grid-row-summary .x-grid-cell { + border-bottom: 0 none; + border-top: 0 none; +} +.x-docked-summary > :first-child { + background-color: #fff; +} +.x-grid-row-summary .x-grid-cell-inner-row-expander { + display: none; +} +.x-menu-default { + border-style: solid; + border-width: 1px; + border-color: #d0d0d0; +} +.x-menu-body-default { + background: #fff; + padding: 0; +} +.x-menu-icon-separator-default { + left: 32px; + border-left: solid 1px #d0d0d0; + background-color: #fff; + width: 1px; +} +.x-menu-item-default { + border-width: 0; + cursor: pointer; +} +.x-menu-item-default.x-menu-item-focus, +.x-menu-item-default.x-menu-item-active { + background-image: none; + background-color: #7fb5e4; +} +.x-nlg .x-menu-item-default.x-menu-item-focus, +.x-nlg .x-menu-item-default.x-menu-item-active { + background: #7fb5e4 repeat-x left top; + background-image: url(images/menu/menu-item-default-active-bg.gif); +} +.x-menu-item-default.x-menu-item-disabled { + cursor: default; +} +.x-menu-item-default.x-menu-item-disabled a { + cursor: default; +} +.x-menu-item-default.x-menu-item-separator { + height: 1px; + border-top: solid 1px #d0d0d0; + background-color: #fff; + margin: 2px 0; + padding: 0; +} +.x-menu-item-default.x-menu-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-icon-ui { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-ie9m .x-menu-item-default.x-menu-item-disabled .x-menu-item-text-default { + background-color: transparent; +} +.x-menu-item-default .x-form-item-label { + font-size: 13px; + color: #000; +} +.x-menu-item-text-default, +.x-menu-item-cmp-default { + margin: 0 8px 0 8px; +} +.x-menu-item-text-default { + font: 300 13px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 31px; + padding-top: 1px; + color: #000; + cursor: pointer; +} +.x-menu-item-focus .x-menu-item-text-default, +.x-menu-item-active .x-menu-item-text-default { + color: #fff; +} +.x-menu-item-text-default.x-menu-item-indent { + margin-left: 41px; +} +.x-menu-item-text-default.x-menu-item-indent-no-separator { + margin-left: 36px; +} +.x-menu-item-text-default.x-menu-item-indent-right-icon { + margin-right: 40px; +} +.x-menu-item-text-default.x-menu-item-indent-right-arrow { + margin-right: 29px; +} +.x-menu-item-disabled .x-menu-item-text-default { + cursor: default; +} +.x-menu-item-indent-default { + margin-left: 41px; +} +.x-menu-item-icon-default { + width: 24px; + height: 24px; + top: 4px; + left: 4px; + line-height: 24px; + font-size: 16px; + color: #919191; + background-position: center center; +} +.x-menu-item-focus .x-menu-item-icon-default, +.x-menu-item-active .x-menu-item-icon-default { + color: #fff; +} +.x-ie8 .x-menu-item-focus .x-menu-item-icon-default, +.x-ie8 .x-menu-item-active .x-menu-item-icon-default { + color: #fff !important; +} +.x-ie8 .x-menu-item-icon-default.x-menu-item-glyph { + color: #919191; +} +.x-menu-item-icon-default.x-menu-item-icon-right { + width: 24px; + height: 24px; + top: 4px; + right: 4px; + left: auto; + background-position: center center; +} +.x-menu-item-icon-default.x-menu-item-checkbox { + color: #919191; +} +.x-menu-item-focus .x-menu-item-icon-default.x-menu-item-checkbox, +.x-menu-item-active .x-menu-item-icon-default.x-menu-item-checkbox { + color: #fff; +} +.x-menu-item-checked .x-menu-item-icon-default.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +.x-menu-item-checked .x-menu-item-icon-default.x-menu-item-checkbox:before { + content: "\f046"; +} +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-item-checkbox:before { + content: "\f096"; +} +.x-menu-item-focus .x-menu-item-icon-default.x-menu-group-icon, +.x-menu-item-active .x-menu-item-icon-default.x-menu-group-icon { + color: #fff; +} +.x-menu-item-checked .x-menu-item-icon-default.x-menu-group-icon { + font: 18px/24px FontAwesome; +} +.x-menu-item-checked .x-menu-item-icon-default.x-menu-group-icon:before { + content: "\f00c"; +} +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-group-icon { + background-image: none; +} +.x-menu-item-unchecked .x-menu-item-icon-default.x-menu-group-icon:before { + content: ""; +} +.x-menu-item-arrow-default { + width: 16px; + height: 16px; + top: 8px; + right: 0; + margin: 0 4px 0; + font: 16px/1 FontAwesome; + color: #919191; +} +.x-menu-item-arrow-default:before { + content: "\f0da"; +} +.x-menu-item-focus .x-menu-item-arrow-default, +.x-menu-item-active .x-menu-item-arrow-default { + color: #fff; +} +.x-menu-item-focus .x-menu-item-arrow-default, +.x-menu-item-active .x-menu-item-arrow-default { + top: 8px; + right: 0; +} +.x-menu-default-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +.x-menu-default-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +.x-box-scroller-menu-default { + cursor: pointer; + color: #919191; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-box-scroller-menu-default.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +.x-box-scroller-menu-default.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +.x-box-scroller-menu-default.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +.x-box-scroller-menu-default.x-box-scroller-top, +.x-box-scroller-menu-default.x-box-scroller-bottom { + height: 16px; + width: 16px; + left: 50%; + margin-left: -8px; +} +.x-box-scroller-menu-default.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +.x-box-scroller-menu-default.x-box-scroller-top:before { + content: "\f077"; +} +.x-box-scroller-menu-default.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +.x-box-scroller-menu-default.x-box-scroller-bottom:before { + content: "\f078"; +} +.x-ie8 .x-box-scroller-menu-default { + background-color: #fff; +} +.x-menu-default-menubar { + border-style: solid; + border-width: 1px; + border-color: #d0d0d0; +} +.x-menu-body-default-menubar { + background: #fff; + padding: 0; +} +.x-menu-icon-separator-default-menubar { + left: 32px; + border-left: solid 1px #d0d0d0; + background-color: #fff; + width: 1px; +} +.x-menu-item-default-menubar { + border-width: 0; + cursor: pointer; +} +.x-menu-item-default-menubar.x-menu-item-focus, +.x-menu-item-default-menubar.x-menu-item-active { + background-image: none; + background-color: #7fb5e4; +} +.x-nlg .x-menu-item-default-menubar.x-menu-item-focus, +.x-nlg .x-menu-item-default-menubar.x-menu-item-active { + background: #7fb5e4 repeat-x left top; + background-image: url(images/menu/menu-item-default-menubar-active-bg.gif); +} +.x-menu-item-default-menubar.x-menu-item-disabled { + cursor: default; +} +.x-menu-item-default-menubar.x-menu-item-disabled a { + cursor: default; +} +.x-menu-item-default-menubar.x-menu-item-separator { + height: 1px; + border-top: solid 1px #d0d0d0; + background-color: #fff; + margin: 2px 0; + padding: 0; +} +.x-menu-item-default-menubar.x-menu-item-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-ie9m .x-menu-item-default-menubar.x-menu-item-disabled .x-menu-item-icon-ui { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-ie9m + .x-menu-item-default-menubar.x-menu-item-disabled + .x-menu-item-text-default-menubar { + background-color: transparent; +} +.x-menu-item-default-menubar .x-form-item-label { + font-size: 13px; + color: #000; +} +.x-menu-item-text-default-menubar, +.x-menu-item-cmp-default-menubar { + margin: 0 8px 0 8px; +} +.x-menu-item-text-default-menubar { + font: 300 13px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + line-height: 31px; + padding-top: 1px; + color: #000; + cursor: pointer; +} +.x-menu-item-focus .x-menu-item-text-default-menubar, +.x-menu-item-active .x-menu-item-text-default-menubar { + color: #fff; +} +.x-menu-item-text-default-menubar.x-menu-item-indent { + margin-left: 41px; +} +.x-menu-item-text-default-menubar.x-menu-item-indent-no-separator { + margin-left: 36px; +} +.x-menu-item-text-default-menubar.x-menu-item-indent-right-icon { + margin-right: 40px; +} +.x-menu-item-text-default-menubar.x-menu-item-indent-right-arrow { + margin-right: 27px; +} +.x-menu-item-disabled .x-menu-item-text-default-menubar { + cursor: default; +} +.x-menu-item-indent-default-menubar { + margin-left: 41px; +} +.x-menu-item-icon-default-menubar { + width: 24px; + height: 24px; + top: 4px; + left: 4px; + line-height: 24px; + font-size: 16px; + color: #919191; + background-position: center center; +} +.x-menu-item-focus .x-menu-item-icon-default-menubar, +.x-menu-item-active .x-menu-item-icon-default-menubar { + color: #fff; +} +.x-ie8 .x-menu-item-focus .x-menu-item-icon-default-menubar, +.x-ie8 .x-menu-item-active .x-menu-item-icon-default-menubar { + color: #fff !important; +} +.x-ie8 .x-menu-item-icon-default-menubar.x-menu-item-glyph { + color: #919191; +} +.x-menu-item-icon-default-menubar.x-menu-item-icon-right { + width: 24px; + height: 24px; + top: 4px; + right: 4px; + left: auto; + background-position: center center; +} +.x-menu-item-icon-default-menubar.x-menu-item-checkbox { + color: #919191; +} +.x-menu-item-focus .x-menu-item-icon-default-menubar.x-menu-item-checkbox, +.x-menu-item-active .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + color: #fff; +} +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +.x-menu-item-checked + .x-menu-item-icon-default-menubar.x-menu-item-checkbox:before { + content: "\f046"; +} +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-item-checkbox { + font: 18px/24px FontAwesome; +} +.x-menu-item-unchecked + .x-menu-item-icon-default-menubar.x-menu-item-checkbox:before { + content: "\f096"; +} +.x-menu-item-focus .x-menu-item-icon-default-menubar.x-menu-group-icon, +.x-menu-item-active .x-menu-item-icon-default-menubar.x-menu-group-icon { + color: #fff; +} +.x-menu-item-checked .x-menu-item-icon-default-menubar.x-menu-group-icon { + font: 18px/24px FontAwesome; +} +.x-menu-item-checked + .x-menu-item-icon-default-menubar.x-menu-group-icon:before { + content: "\f00c"; +} +.x-menu-item-unchecked .x-menu-item-icon-default-menubar.x-menu-group-icon { + background-image: none; +} +.x-menu-item-unchecked + .x-menu-item-icon-default-menubar.x-menu-group-icon:before { + content: ""; +} +.x-menu-item-arrow-default-menubar { + width: 9px; + height: 6px; + top: 9px; + right: 5px; + margin: 0 4px 0; + font: 16px/1 FontAwesome; + color: #919191; +} +.x-menu-item-arrow-default-menubar:before { + content: "\f0d7"; +} +.x-menu-item-focus .x-menu-item-arrow-default-menubar, +.x-menu-item-active .x-menu-item-arrow-default-menubar { + color: #fff; +} +.x-menu-item-focus .x-menu-item-arrow-default-menubar, +.x-menu-item-active .x-menu-item-arrow-default-menubar { + top: 9px; + right: 5px; +} +.x-menu-default-menubar-scroller .x-box-scroller-body-horizontal { + margin-left: 16px; +} +.x-menu-default-menubar-vertical-scroller .x-box-scroller-body-vertical { + margin-top: 24px; +} +.x-box-scroller-menu-default-menubar { + cursor: pointer; + color: #919191; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-hover { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=60)"; + opacity: 0.6; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-pressed { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=70)"; + opacity: 0.7; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-disabled { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=25)"; + opacity: 0.25; + cursor: default; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-top, +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom { + height: 16px; + width: 16px; + left: 50%; + margin-left: -8px; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-top { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-top:before { + content: "\f077"; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom { + margin-top: 4px; + margin-right: 0; + margin-bottom: 4px; + font: 16px/16px FontAwesome; +} +.x-box-scroller-menu-default-menubar.x-box-scroller-bottom:before { + content: "\f078"; +} +.x-ie8 .x-box-scroller-menu-default-menubar { + background-color: #fff; +} +.x-grid-filters-filtered-column { + font-style: italic; + font-weight: 600; + text-decoration: underline; +} +.x-grid-filters-icon { + background-repeat: no-repeat; + background-position: center center; + color: #919191; + text-align: center; +} +.x-grid-filters-find .x-form-item-label-inner { + font: 16px/1 FontAwesome; +} +.x-grid-filters-find .x-form-item-label-inner:before { + content: "\f002"; +} +.x-grid-filters-gt .x-form-item-label-inner { + font: 16px/1 FontAwesome; +} +.x-grid-filters-gt .x-form-item-label-inner:before { + content: "\f054"; +} +.x-grid-filters-lt .x-form-item-label-inner { + font: 16px/1 FontAwesome; +} +.x-grid-filters-lt .x-form-item-label-inner:before { + content: "\f053"; +} +.x-grid-filters-eq .x-form-item-label-inner { + font: 16px/1 ExtJS; +} +.x-grid-filters-eq .x-form-item-label-inner:before { + content: "\e605"; +} +.x-grid-locked .x-grid-inner-locked { + border-width: 0 2px 0 0; + border-style: solid; +} +.x-grid-locked-split .x-grid-inner-normal { + border-width: 0 0 0 2px; + border-style: solid; + border-left-color: #d0d0d0; +} +.x-grid-locking-body { + border-width: 1px; +} +.x-grid-locking-body > .x-splitter { + background-color: #ececec; +} +.x-grid-locking-body > .x-splitter-active { + background-color: #b4b4b4; +} +.x-grid-inner-locked { + border-right-color: #d0d0d0; +} +.x-grid-inner-locked .x-column-header-last, +.x-grid-inner-locked .x-grid-cell-last { + border-right-width: 0 !important; +} +.x-hmenu-lock { + font: 16px/24px FontAwesome; +} +.x-hmenu-lock:before { + content: "\f023"; +} +.x-hmenu-unlock { + font: 16px/24px FontAwesome; +} +.x-hmenu-unlock:before { + content: "\f09c"; +} +.x-grid-scrollbar-clipper > .x-grid-view, +.x-grid-scrollbar-clipper > .x-tree-view { + background-color: #fff; +} +.x-grid-scrollbar-clipper-locked, +.x-grid-scrollbar-locked { + border-width: 0 2px 0 0; + border-style: solid; + border-color: #d0d0d0; +} +.x-grid-scroll-container { + background-color: #fff; +} +.x-grid-editor .x-form-display-field { + text-overflow: ellipsis; +} +.x-grid-editor .x-form-action-col-field { + padding: 7px 4px 7px 4px; +} +.x-grid-editor .x-form-text { + padding-left: 9px; + padding-right: 9px; +} +.x-tree-cell-editor .x-form-text { + padding-left: 5px; + padding-right: 5px; +} +.x-grid-row-editor .x-field { + margin: 0 3px 0 2px; +} +.x-grid-row-editor .x-form-display-field { + padding: 7px 8px 6px 8px; + line-height: 19px; +} +.x-ie9m .x-grid-row-editor .x-form-display-field { + min-height: 19px; +} +.x-grid-row-editor .x-form-action-col-field { + padding: 7px 1px 7px 2px; +} +.x-grid-row-editor .x-form-text { + padding: 5px 6px 4px 7px; +} +.x-gecko .x-grid-row-editor .x-form-text { + padding-left: 6px; + padding-right: 5px; +} +.x-grid-row-editor .x-panel-body { + border-top: 1px solid #d0d0d0 !important; + border-bottom: 1px solid #d0d0d0 !important; + padding: 5px 0 5px 0; + background-color: #e5edf4; +} +.x-grid-with-col-lines .x-grid-row-editor .x-form-cb { + margin-right: 1px; +} +.x-grid-row-editor-buttons-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 5px; + -webkit-border-bottom-right-radius: 5px; + border-bottom-right-radius: 5px; + -moz-border-radius-bottomleft: 5px; + -webkit-border-bottom-left-radius: 5px; + border-bottom-left-radius: 5px; + padding: 5px 5px 5px 5px; + border-width: 0 1px 1px 1px; + border-style: solid; + background-color: #e5edf4; +} +.x-grid-row-editor-buttons-default-bottom-mc { + background-color: #e5edf4; +} +.x-nbr .x-grid-row-editor-buttons-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-grid-row-editor-buttons-default-bottom-frameInfo { + font-family: th-0-5-5-5-0-1-1-1-5-5-5-5; +} +.x-grid-row-editor-buttons-default-bottom-tl { + background-position: 0 -10px; +} +.x-grid-row-editor-buttons-default-bottom-tr { + background-position: right -15px; +} +.x-grid-row-editor-buttons-default-bottom-bl { + background-position: 0 -20px; +} +.x-grid-row-editor-buttons-default-bottom-br { + background-position: right -25px; +} +.x-grid-row-editor-buttons-default-bottom-ml { + background-position: 0 top; +} +.x-grid-row-editor-buttons-default-bottom-mr { + background-position: right top; +} +.x-grid-row-editor-buttons-default-bottom-tc { + background-position: 0 0; +} +.x-grid-row-editor-buttons-default-bottom-bc { + background-position: 0 -5px; +} +.x-grid-row-editor-buttons-default-bottom-tr, +.x-grid-row-editor-buttons-default-bottom-br, +.x-grid-row-editor-buttons-default-bottom-mr { + padding-right: 5px; +} +.x-grid-row-editor-buttons-default-bottom-tl, +.x-grid-row-editor-buttons-default-bottom-bl, +.x-grid-row-editor-buttons-default-bottom-ml { + padding-left: 5px; +} +.x-grid-row-editor-buttons-default-bottom-tc { + height: 0; +} +.x-grid-row-editor-buttons-default-bottom-bc { + height: 5px; +} +.x-grid-row-editor-buttons-default-bottom-tl, +.x-grid-row-editor-buttons-default-bottom-bl, +.x-grid-row-editor-buttons-default-bottom-tr, +.x-grid-row-editor-buttons-default-bottom-br, +.x-grid-row-editor-buttons-default-bottom-tc, +.x-grid-row-editor-buttons-default-bottom-bc, +.x-grid-row-editor-buttons-default-bottom-ml, +.x-grid-row-editor-buttons-default-bottom-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-corners.gif); +} +.x-grid-row-editor-buttons-default-bottom-ml, +.x-grid-row-editor-buttons-default-bottom-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-bottom-sides.gif); + background-repeat: repeat-y; +} +.x-grid-row-editor-buttons-default-bottom-mc { + padding: 5px 1px 1px 1px; +} +.x-grid-row-editor-buttons-default-top { + -moz-border-radius-topleft: 5px; + -webkit-border-top-left-radius: 5px; + border-top-left-radius: 5px; + -moz-border-radius-topright: 5px; + -webkit-border-top-right-radius: 5px; + border-top-right-radius: 5px; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 5px 5px 5px 5px; + border-width: 1px 1px 0 1px; + border-style: solid; + background-color: #e5edf4; +} +.x-grid-row-editor-buttons-default-top-mc { + background-color: #e5edf4; +} +.x-nbr .x-grid-row-editor-buttons-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-grid-row-editor-buttons-default-top-frameInfo { + font-family: th-5-5-0-5-1-1-0-1-5-5-5-5; +} +.x-grid-row-editor-buttons-default-top-tl { + background-position: 0 -10px; +} +.x-grid-row-editor-buttons-default-top-tr { + background-position: right -15px; +} +.x-grid-row-editor-buttons-default-top-bl { + background-position: 0 -20px; +} +.x-grid-row-editor-buttons-default-top-br { + background-position: right -25px; +} +.x-grid-row-editor-buttons-default-top-ml { + background-position: 0 top; +} +.x-grid-row-editor-buttons-default-top-mr { + background-position: right top; +} +.x-grid-row-editor-buttons-default-top-tc { + background-position: 0 0; +} +.x-grid-row-editor-buttons-default-top-bc { + background-position: 0 -5px; +} +.x-grid-row-editor-buttons-default-top-tr, +.x-grid-row-editor-buttons-default-top-br, +.x-grid-row-editor-buttons-default-top-mr { + padding-right: 5px; +} +.x-grid-row-editor-buttons-default-top-tl, +.x-grid-row-editor-buttons-default-top-bl, +.x-grid-row-editor-buttons-default-top-ml { + padding-left: 5px; +} +.x-grid-row-editor-buttons-default-top-tc { + height: 5px; +} +.x-grid-row-editor-buttons-default-top-bc { + height: 0; +} +.x-grid-row-editor-buttons-default-top-tl, +.x-grid-row-editor-buttons-default-top-bl, +.x-grid-row-editor-buttons-default-top-tr, +.x-grid-row-editor-buttons-default-top-br, +.x-grid-row-editor-buttons-default-top-tc, +.x-grid-row-editor-buttons-default-top-bc, +.x-grid-row-editor-buttons-default-top-ml, +.x-grid-row-editor-buttons-default-top-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-corners.gif); +} +.x-grid-row-editor-buttons-default-top-ml, +.x-grid-row-editor-buttons-default-top-mr { + background-image: url(images/grid-row-editor-buttons/grid-row-editor-buttons-default-top-sides.gif); + background-repeat: repeat-y; +} +.x-grid-row-editor-buttons-default-top-mc { + padding: 1px 1px 5px 1px; +} +.x-grid-row-editor-buttons { + border-color: #d0d0d0; +} +.x-row-editor-update-button { + margin-right: 3px; +} +.x-row-editor-cancel-button { + margin-left: 2px; +} +.x-grid-row-editor-errors .x-tip-body { + padding: 5px; +} +.x-grid-row-editor-errors-item { + list-style: disc; + margin-left: 15px; +} +.x-grid-cell-inner-row-expander { + padding: 8px 8px 8px 8px; +} +.x-grid-row-expander { + width: 16px; + height: 16px; + cursor: pointer; + color: #919191; + font: 14px/1 FontAwesome; +} +.x-grid-row-expander:before { + content: "\f146"; +} +.x-grid-row-collapsed .x-grid-row-expander { + font: 14px/1 FontAwesome; +} +.x-grid-row-collapsed .x-grid-row-expander:before { + content: "\f0fe"; +} +.x-ssm-row-numberer-hd { + cursor: se-resize !important; +} +.x-ssm-row-numberer-cell { + cursor: e-resize; +} +.x-ssm-column-select .x-column-header { + cursor: s-resize; +} +.x-ssm-extender-drag-handle { + height: 7px; + width: 7px; + background-color: #5fa2dd; +} +.x-ssm-extender-mask { + border: 1px dotted #5fa2dd; +} +.x-accordion-layout-ct { + background-color: #fff; + padding: 5px 5px 0; +} +.x-accordion-hd .x-panel-header-title { + color: #404040; + font-weight: 300; + font-family: "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + text-transform: none; +} +.x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus, +.x-edge .x-keyboard-mode .x-accordion-hd .x-panel-header-title.x-title-focus { + outline: none; +} +.x-ie + .x-keyboard-mode + .x-accordion-hd + .x-panel-header-title.x-title-focus:after, +.x-ie10p + .x-keyboard-mode + .x-accordion-hd + .x-panel-header-title.x-title-focus:after, +.x-edge + .x-keyboard-mode + .x-accordion-hd + .x-panel-header-title.x-title-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +.x-accordion-item { + margin: 0 0 5px; +} +.x-accordion-item .x-accordion-hd { + background: #ececec; + border-width: 0; + border-color: #5fa2dd; + padding: 12px 10px; +} +.x-accordion-item .x-accordion-hd-over { + background-color: #f6f6f6; +} +.x-accordion-item .x-accordion-hd-over .x-tool-tool-el { + background-color: #f6f6f6; +} +.x-accordion-item .x-accordion-hd-sibling-expanded { + border-top-color: #5fa2dd; + border-top-width: 0; +} +.x-accordion-item .x-accordion-hd-last-collapsed { + border-bottom-color: #ececec; +} +.x-accordion-item .x-accordion-body { + border-width: 0; +} +.x-accordion-hd .x-tool-tool-el { + background-color: #ececec; + color: #5fa2dd; +} +.x-accordion-hd .x-tool-img { + background-image: url(images/tools/tool-sprites-dark.png); + background-image: none; +} +.x-accordion-hd .x-tool-collapse-top, +.x-accordion-hd .x-tool-collapse-bottom { + font: 16px/1 FontAwesome; + background-image: none; +} +.x-accordion-hd .x-tool-collapse-top:before, +.x-accordion-hd .x-tool-collapse-bottom:before { + content: "\f068"; +} +.x-accordion-hd .x-tool-expand-top, +.x-accordion-hd .x-tool-expand-bottom { + font: 16px/1 FontAwesome; + background-image: none; +} +.x-accordion-hd .x-tool-expand-top:before, +.x-accordion-hd .x-tool-expand-bottom:before { + content: "\f067"; +} +.x-keyboard-mode .x-accordion-hd .x-tool-focus { + outline: 1px solid #5fa2dd; + outline-offset: 2px; +} +.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus, +.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus { + outline: none; +} +.x-ie .x-keyboard-mode .x-accordion-hd .x-tool-focus:after, +.x-ie10p .x-keyboard-mode .x-accordion-hd .x-tool-focus:after, +.x-edge .x-keyboard-mode .x-accordion-hd .x-tool-focus:after { + position: absolute; + content: " "; + top: -3px; + right: -3px; + bottom: -3px; + left: -3px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +body.x-border-layout-ct, +div.x-border-layout-ct { + background-color: #f6f6f6; +} +.x-form-layout-wrap { + border-spacing: 10px; +} +.x-resizable-handle { + position: absolute; + z-index: 100; + font-size: 1px; + line-height: 10px; + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; + background-color: #ececec; + color: #919191; + text-align: center; +} +.x-collapsed .x-resizable-handle { + display: none; +} +.x-resizable-handle-southeast { + cursor: se-resize; +} +.x-resizable-handle-southeast:before { + position: absolute; + bottom: 0; + right: 0; +} +.x-resizable-handle-northwest { + cursor: nw-resize; +} +.x-resizable-handle-northwest:before { + position: absolute; + top: 0; + left: 0; +} +.x-resizable-handle-northeast { + cursor: ne-resize; +} +.x-resizable-handle-northeast:before { + position: absolute; + top: 0; + right: 0; +} +.x-resizable-handle-southwest { + cursor: sw-resize; +} +.x-resizable-handle-southwest:before { + position: absolute; + bottom: 0; + left: 0; +} +.x-resizable-handle-east:before, +.x-resizable-handle-west:before { + display: block; + position: absolute; + top: 50%; + margin-top: -0.5em; + width: 100%; +} +.x-resizable-handle-east { + cursor: e-resize; + width: 10px; + right: 0; + top: 0; + bottom: 0; +} +.x-resizable-handle-south { + cursor: s-resize; + height: 10px; + left: 0; + right: 0; + bottom: 0; +} +.x-resizable-handle-west { + cursor: w-resize; + width: 10px; + left: 0; + top: 0; + bottom: 0; +} +.x-resizable-handle-north { + cursor: n-resize; + height: 10px; + left: 0; + right: 0; + top: 0; +} +.x-resizable-handle-southeast { + width: 10px; + height: 10px; + right: 0; + bottom: 0; + z-index: 101; +} +.x-resizable-handle-northwest { + width: 10px; + height: 10px; + left: 0; + top: 0; + z-index: 101; +} +.x-resizable-handle-northeast { + width: 10px; + height: 10px; + right: 0; + top: 0; + z-index: 101; +} +.x-resizable-handle-southwest { + width: 10px; + height: 10px; + left: 0; + bottom: 0; + z-index: 101; +} +.x-tablet .x-resizable-handle-north, +.x-tablet .x-resizable-handle-south { + height: 20px; +} +.x-tablet .x-resizable-handle-east, +.x-tablet .x-resizable-handle-west { + width: 20px; +} +.x-tablet .x-resizable-handle-northwest, +.x-tablet .x-resizable-handle-northeast, +.x-tablet .x-resizable-handle-southwest, +.x-tablet .x-resizable-handle-southeast { + width: 20px; + height: 20px; +} +.x-window .x-window-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; + opacity: 0; +} +.x-window-collapsed .x-window-handle { + display: none; +} +.x-resizable-proxy { + border: 1px dashed #3b5a82; + position: absolute; + overflow: hidden; + z-index: 50000; +} +.x-resizable-handle-over, +.x-resizable-pinned .x-resizable-handle { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=100)"; + opacity: 1; +} +.x-resizable-handle-east-over, +.x-resizable-handle-west-over, +.x-resizable-pinned > .x-resizable-handle-east, +.x-resizable-pinned > .x-resizable-handle-west { + font: 16px/1 FontAwesome; +} +.x-resizable-handle-east-over:before, +.x-resizable-handle-west-over:before, +.x-resizable-pinned > .x-resizable-handle-east:before, +.x-resizable-pinned > .x-resizable-handle-west:before { + content: "\f142"; +} +.x-resizable-handle-south-over, +.x-resizable-handle-north-over, +.x-resizable-pinned > .x-resizable-handle-south, +.x-resizable-pinned > .x-resizable-handle-north { + font: 16px/10px FontAwesome; +} +.x-resizable-handle-south-over:before, +.x-resizable-handle-north-over:before, +.x-resizable-pinned > .x-resizable-handle-south:before, +.x-resizable-pinned > .x-resizable-handle-north:before { + content: "\f141"; +} +.x-resizable-handle-southeast-over, +.x-resizable-pinned > .x-resizable-handle-southeast { + font: 16px/1 ExtJS; +} +.x-resizable-handle-southeast-over:before, +.x-resizable-pinned > .x-resizable-handle-southeast:before { + content: "\e60c"; +} +.x-resizable-handle-northwest-over, +.x-resizable-pinned > .x-resizable-handle-northwest { + font: 16px/1 ExtJS; +} +.x-resizable-handle-northwest-over:before, +.x-resizable-pinned > .x-resizable-handle-northwest:before { + content: "\e609"; +} +.x-resizable-handle-northeast-over, +.x-resizable-pinned > .x-resizable-handle-northeast { + font: 16px/1 ExtJS; +} +.x-resizable-handle-northeast-over:before, +.x-resizable-pinned > .x-resizable-handle-northeast:before { + content: "\e60a"; +} +.x-resizable-handle-southwest-over, +.x-resizable-pinned > .x-resizable-handle-southwest { + font: 16px/1 ExtJS; +} +.x-resizable-handle-southwest-over:before, +.x-resizable-pinned > .x-resizable-handle-southwest:before { + content: "\e60b"; +} +.x-slider:before { + border: 1px solid #d0d0d0; + content: ""; + position: absolute; + border-radius: 2px; + background-color: #eee; + box-sizing: border-box; + -moz-box-sizing: border-box; + -ms-box-sizing: border-box; + -webkit-box-sizing: border-box; +} +.x-slider-thumb { + background-color: #f6f6f6; + border: 1px solid #d0d0d0; + border-radius: 2px; +} +.x-slider-thumb:before { + color: #d0d0d0; +} +.x-slider-thumb-over { + background-color: #fcfcfc; + border-color: #c8cdd2; +} +.x-slider-thumb-over:before { + color: #d0d0d0; +} +.x-keyboard-mode .x-slider-focus .x-slider-thumb { + background-color: #f6f6f6; + border-color: #5fa2dd; +} +.x-keyboard-mode .x-slider-focus .x-slider-thumb:before { + color: #a6c7e5; +} +.x-keyboard-mode .x-slider-focus .x-slider-thumb-over { + background-color: #fcfcfc; +} +.x-slider-thumb-drag { + background-color: #f1f1f1; + border-color: #c0c8cf; +} +.x-slider-thumb-drag:before { + color: #d0d0d0; +} +.x-keyboard-mode .x-slider-focus .x-slider-thumb-drag { + background-color: #f1f1f1; +} +.x-slider-horz { + padding-left: 10px; + background: no-repeat 0 -20px; + margin: 6px 0 6px; +} +.x-slider-horz .x-slider-end { + padding-right: 10px; + background: no-repeat right -40px; +} +.x-slider-horz .x-slider-inner { + height: 20px; +} +.x-slider-horz:before { + height: 10px; + width: 100%; + top: 50%; + left: 0; + margin-top: -5px; +} +.x-slider-horz .x-slider-thumb { + width: 20px; + height: 20px; + margin-left: -10px; + font: 12px/1 ExtJS; +} +.x-slider-horz .x-slider-thumb:before { + content: "\e612"; +} +.x-slider-ct-vert { + height: 100%; +} +.x-slider-vert { + padding-top: 10px; + height: 100%; +} +.x-slider-vert > .x-slider-end { + height: 100%; +} +.x-slider-vert > .x-slider-end > .x-slider-inner { + height: 100%; +} +.x-slider-vert:before { + width: 10px; + height: 100%; + left: 10px; + top: 0; + margin-left: -5px; +} +.x-slider-vert .x-slider-end { + padding-bottom: 10px; + background: no-repeat -20px bottom; + width: 20px; +} +.x-slider-vert .x-slider-inner { + width: 20px; +} +.x-slider-vert .x-slider-thumb { + width: 20px; + height: 20px; + margin-bottom: -10px; + font: 12px/1 ExtJS; +} +.x-slider-vert .x-slider-thumb:before { + content: "\e605"; +} +.x-slider-default-cell > .x-grid-cell-inner, +.x-sliderwidget-default-cell > .x-grid-cell-inner { + padding-top: 0px; + padding-bottom: 0px; +} +.x-tab-default-top { + -webkit-border-radius: 0; + -moz-border-radius: 0; + -ms-border-radius: 0; + -o-border-radius: 0; + border-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0; + border-style: solid; + background-color: transparent; +} +.x-tab-default-top-mc { + background-color: transparent; +} +.x-nbr .x-tab-default-top { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tab-default-top-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +.x-tab-default-top-tl { + background-position: 0 0; +} +.x-tab-default-top-tr { + background-position: right 0; +} +.x-tab-default-top-bl { + background-position: 0 0; +} +.x-tab-default-top-br { + background-position: right 0; +} +.x-tab-default-top-ml { + background-position: 0 top; +} +.x-tab-default-top-mr { + background-position: right top; +} +.x-tab-default-top-tc { + background-position: 0 0; +} +.x-tab-default-top-bc { + background-position: 0 0; +} +.x-tab-default-top-tr, +.x-tab-default-top-br, +.x-tab-default-top-mr { + padding-right: 0; +} +.x-tab-default-top-tl, +.x-tab-default-top-bl, +.x-tab-default-top-ml { + padding-left: 0; +} +.x-tab-default-top-tc { + height: 0; +} +.x-tab-default-top-bc { + height: 0; +} +.x-tab-default-top-mc { + padding: 8px 10px 8px 10px; +} +.x-tab-default-bottom { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0 0 0 0; + border-style: solid; + background-color: transparent; +} +.x-tab-default-bottom-mc { + background-color: transparent; +} +.x-nbr .x-tab-default-bottom { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tab-default-bottom-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +.x-tab-default-bottom-tl { + background-position: 0 0; +} +.x-tab-default-bottom-tr { + background-position: right 0; +} +.x-tab-default-bottom-bl { + background-position: 0 0; +} +.x-tab-default-bottom-br { + background-position: right 0; +} +.x-tab-default-bottom-ml { + background-position: 0 bottom; +} +.x-tab-default-bottom-mr { + background-position: right bottom; +} +.x-tab-default-bottom-tc { + background-position: 0 0; +} +.x-tab-default-bottom-bc { + background-position: 0 0; +} +.x-tab-default-bottom-tr, +.x-tab-default-bottom-br, +.x-tab-default-bottom-mr { + padding-right: 0; +} +.x-tab-default-bottom-tl, +.x-tab-default-bottom-bl, +.x-tab-default-bottom-ml { + padding-left: 0; +} +.x-tab-default-bottom-tc { + height: 0; +} +.x-tab-default-bottom-bc { + height: 0; +} +.x-tab-default-bottom-mc { + padding: 8px 10px 8px 10px; +} +.x-tab-default-left { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0 0 0 0; + border-style: solid; + background-color: transparent; +} +.x-tab-default-left-mc { + background-color: transparent; +} +.x-nbr .x-tab-default-left { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tab-default-left-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +.x-tab-default-left-tl { + background-position: 0 0; +} +.x-tab-default-left-tr { + background-position: right 0; +} +.x-tab-default-left-bl { + background-position: 0 0; +} +.x-tab-default-left-br { + background-position: right 0; +} +.x-tab-default-left-ml { + background-position: 0 top; +} +.x-tab-default-left-mr { + background-position: right top; +} +.x-tab-default-left-tc { + background-position: 0 0; +} +.x-tab-default-left-bc { + background-position: 0 0; +} +.x-tab-default-left-tr, +.x-tab-default-left-br, +.x-tab-default-left-mr { + padding-right: 0; +} +.x-tab-default-left-tl, +.x-tab-default-left-bl, +.x-tab-default-left-ml { + padding-left: 0; +} +.x-tab-default-left-tc { + height: 0; +} +.x-tab-default-left-bc { + height: 0; +} +.x-tab-default-left-mc { + padding: 8px 10px 8px 10px; +} +.x-tab-default-right { + -moz-border-radius-topleft: 0; + -webkit-border-top-left-radius: 0; + border-top-left-radius: 0; + -moz-border-radius-topright: 0; + -webkit-border-top-right-radius: 0; + border-top-right-radius: 0; + -moz-border-radius-bottomright: 0; + -webkit-border-bottom-right-radius: 0; + border-bottom-right-radius: 0; + -moz-border-radius-bottomleft: 0; + -webkit-border-bottom-left-radius: 0; + border-bottom-left-radius: 0; + padding: 8px 10px 8px 10px; + border-width: 0 0 0 0; + border-style: solid; + background-color: transparent; +} +.x-tab-default-right-mc { + background-color: transparent; +} +.x-nbr .x-tab-default-right { + padding: 0 !important; + border-width: 0 !important; + -webkit-border-radius: 0px; + -moz-border-radius: 0px; + -ms-border-radius: 0px; + -o-border-radius: 0px; + border-radius: 0px; + background-color: transparent !important; + box-shadow: none !important; +} +.x-tab-default-right-frameInfo { + font-family: th-0-0-0-0-0-0-0-0-8-10-8-10; +} +.x-tab-default-right-tl { + background-position: 0 0; +} +.x-tab-default-right-tr { + background-position: right 0; +} +.x-tab-default-right-bl { + background-position: 0 0; +} +.x-tab-default-right-br { + background-position: right 0; +} +.x-tab-default-right-ml { + background-position: 0 top; +} +.x-tab-default-right-mr { + background-position: right top; +} +.x-tab-default-right-tc { + background-position: 0 0; +} +.x-tab-default-right-bc { + background-position: 0 0; +} +.x-tab-default-right-tr, +.x-tab-default-right-br, +.x-tab-default-right-mr { + padding-right: 0; +} +.x-tab-default-right-tl, +.x-tab-default-right-bl, +.x-tab-default-right-ml { + padding-left: 0; +} +.x-tab-default-right-tc { + height: 0; +} +.x-tab-default-right-bc { + height: 0; +} +.x-tab-default-right-mc { + padding: 8px 10px 8px 10px; +} +.x-tab-default { + border-color: transparent; + cursor: pointer; +} +.x-tab-default-top { + margin: 0 4px 0 0; +} +.x-tab-default-top.x-tab-rotate-left { + margin: 0 0 0 4px; +} +.x-keyboard-mode .x-tab-default-top.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-top.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-tab-default-right { + margin: 0 0 4px 0; +} +.x-tab-default-right.x-tab-rotate-right { + margin: 4px 0 0 0; +} +.x-keyboard-mode .x-tab-default-right.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-right.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-tab-default-bottom { + margin: 0 4px 0 0; +} +.x-tab-default-bottom.x-tab-rotate-left { + margin: 0 0 0 4px; +} +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-bottom.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-tab-default-left { + margin: 0 0 4px 0; +} +.x-tab-default-left.x-tab-rotate-right { + margin: 4px 0 0 0; +} +.x-keyboard-mode .x-tab-default-left.x-tab-focus { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-over { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-keyboard-mode .x-tab-default-left.x-tab-focus.x-tab-active { + -webkit-box-shadow: none; + -moz-box-shadow: none; + box-shadow: none; +} +.x-tab-button-default { + height: 20px; +} +.x-tab-inner-default { + font: 400 13px/20px "Open Sans", "Helvetica Neue", helvetica, arial, verdana, + sans-serif; + color: #f0f0f0; + max-width: 100%; +} +.x-tab-bar-plain .x-tab-inner-default { + color: #606060; +} +.x-tab-icon-right > .x-tab-inner-default, +.x-tab-icon-left > .x-tab-inner-default { + max-width: calc(100% - 20px); +} +.x-tab-icon-el-default { + min-height: 20px; + background-position: center center; + font-size: 20px; + line-height: 20px; + color: #f0f0f0; +} +.x-tab-icon-left > .x-tab-icon-el-default, +.x-tab-icon-right > .x-tab-icon-el-default { + width: 20px; +} +.x-tab-icon-top > .x-tab-icon-el-default, +.x-tab-icon-bottom > .x-tab-icon-el-default { + min-width: 20px; +} +.x-tab-bar-plain .x-tab-icon-el-default { + color: #606060; +} +.x-tab-icon-el-default.x-tab-glyph { + opacity: 0.7; +} +.x-tab-text.x-tab-icon-left > .x-tab-icon-el-default { + margin-right: 6px; +} +.x-tab-text.x-tab-icon-right > .x-tab-icon-el-default { + margin-left: 6px; +} +.x-tab-text.x-tab-icon-top > .x-tab-icon-el-default { + margin-bottom: 6px; +} +.x-tab-text.x-tab-icon-bottom > .x-tab-icon-el-default { + margin-top: 6px; +} +.x-keyboard-mode .x-tab-focus.x-tab-default { + border-color: transparent; + background-color: transparent; + outline: 1px solid #5fa2dd; + outline-offset: -3px; +} +.x-ie .x-keyboard-mode .x-tab-focus.x-tab-default, +.x-ie10p .x-keyboard-mode .x-tab-focus.x-tab-default, +.x-edge .x-keyboard-mode .x-tab-focus.x-tab-default { + outline: none; +} +.x-ie .x-keyboard-mode .x-tab-focus.x-tab-default:after, +.x-ie10p .x-keyboard-mode .x-tab-focus.x-tab-default:after, +.x-edge .x-keyboard-mode .x-tab-focus.x-tab-default:after { + position: absolute; + content: " "; + top: 2px; + right: 2px; + bottom: 2px; + left: 2px; + border: 1px solid #5fa2dd; + pointer-events: none; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-default + .x-tab-inner-default { + color: #606060; +} +.x-keyboard-mode .x-tab-bar-plain .x-tab-focus.x-tab-default .x-tab-icon-el { + color: #606060; +} +.x-tab-over.x-tab-default { + border-color: #000; + background-image: none; + background-color: rgba(0, 0, 0, 0.08); +} +.x-ie8 .x-tab-over.x-tab-default { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#14000000, endColorstr=#14000000)"; + zoom: 1; +} +.x-ie8 .x-tab-over.x-tab-default.x-tab-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +.x-ie8 .x-tab-over.x-tab-default.x-tab-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +.x-tab-bar-plain .x-tab-over.x-tab-default .x-tab-inner-default { + color: #606060; +} +.x-tab-bar-plain .x-tab-over.x-tab-default .x-tab-icon-el { + color: #606060; +} +.x-keyboard-mode .x-tab-focus.x-tab-over.x-tab-default { + border-color: #000; + background-image: none; + background-color: rgba(0, 0, 0, 0.08); +} +.x-ie8 .x-keyboard-mode .x-tab-focus.x-tab-over.x-tab-default { + -ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#14000000, endColorstr=#14000000)"; + zoom: 1; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-over.x-tab-default + .x-tab-inner-default { + color: #606060; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-over.x-tab-default + .x-tab-icon-el { + color: #606060; +} +.x-keyboard-mode.x-ie8 .x-tab-focus.x-tab-over.x-tab-default.x-tab-rotate-left { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=3)"; +} +.x-keyboard-mode.x-ie8 + .x-tab-focus.x-tab-over.x-tab-default.x-tab-rotate-right { + -ms-filter: "progid:DXImageTransform.Microsoft.BasicImage(rotation=1)"; +} +.x-tab.x-tab-active.x-tab-default { + border-color: #fff; + background-color: #fff; +} +.x-tab.x-tab-active.x-tab-default .x-tab-inner-default { + color: #4c82b1; +} +.x-tab-bar-plain .x-tab.x-tab-active.x-tab-default .x-tab-inner-default { + color: #404040; +} +.x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #4c82b1; +} +.x-ie8 .x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #82a7c8; +} +.x-tab-bar-plain .x-tab.x-tab-active.x-tab-default .x-tab-icon-el { + color: #404040; +} +.x-keyboard-mode .x-tab-focus.x-tab-active.x-tab-default { + border-color: #fff; + background-color: #fff; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-active.x-tab-default + .x-tab-inner-default { + color: #404040; +} +.x-keyboard-mode + .x-tab-bar-plain + .x-tab-focus.x-tab-active.x-tab-default + .x-tab-icon-el { + color: #404040; +} +.x-tab.x-tab-disabled.x-tab-default { + border-color: transparent; + background-color: transparent; + cursor: default; +} +.x-tab.x-tab-disabled.x-tab-default .x-tab-inner-default { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=30)"; + opacity: 0.3; +} +.x-tab-bar-plain .x-tab.x-tab-disabled.x-tab-default .x-tab-inner-default { + color: #606060; +} +.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el-default { + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=50)"; + opacity: 0.5; +} +.x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el { + color: #f0f0f0; + opacity: 0.3; + filter: none; +} +.x-tab-bar-plain .x-tab.x-tab-disabled.x-tab-default .x-tab-icon-el { + color: #606060; +} +.x-nbr .x-tab-default { + background-image: none; +} +.x-tab-over .x-tab-default-top-tl, +.x-tab-over .x-tab-default-top-bl, +.x-tab-over .x-tab-default-top-tr, +.x-tab-over .x-tab-default-top-br, +.x-tab-over .x-tab-default-top-tc, +.x-tab-over .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-over-corners.gif); +} +.x-tab-over .x-tab-default-top-ml, +.x-tab-over .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-over-sides.gif); +} +.x-tab-over .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-over-fbg.gif); +} +.x-tab-focus .x-tab-default-top-tl, +.x-tab-focus .x-tab-default-top-bl, +.x-tab-focus .x-tab-default-top-tr, +.x-tab-focus .x-tab-default-top-br, +.x-tab-focus .x-tab-default-top-tc, +.x-tab-focus .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-corners.gif); +} +.x-tab-focus .x-tab-default-top-ml, +.x-tab-focus .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-sides.gif); +} +.x-tab-focus .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-fbg.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-top-tl, +.x-tab-focus.x-tab-over .x-tab-default-top-bl, +.x-tab-focus.x-tab-over .x-tab-default-top-tr, +.x-tab-focus.x-tab-over .x-tab-default-top-br, +.x-tab-focus.x-tab-over .x-tab-default-top-tc, +.x-tab-focus.x-tab-over .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-over-corners.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-top-ml, +.x-tab-focus.x-tab-over .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-over-sides.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-over-fbg.gif); +} +.x-tab.x-tab-active .x-tab-default-top-tl, +.x-tab.x-tab-active .x-tab-default-top-bl, +.x-tab.x-tab-active .x-tab-default-top-tr, +.x-tab.x-tab-active .x-tab-default-top-br, +.x-tab.x-tab-active .x-tab-default-top-tc, +.x-tab.x-tab-active .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-active-corners.gif); +} +.x-tab.x-tab-active .x-tab-default-top-ml, +.x-tab.x-tab-active .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-active-sides.gif); +} +.x-tab.x-tab-active .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-active-fbg.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-top-tl, +.x-tab-focus.x-tab-active .x-tab-default-top-bl, +.x-tab-focus.x-tab-active .x-tab-default-top-tr, +.x-tab-focus.x-tab-active .x-tab-default-top-br, +.x-tab-focus.x-tab-active .x-tab-default-top-tc, +.x-tab-focus.x-tab-active .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-focus-active-corners.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-top-ml, +.x-tab-focus.x-tab-active .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-focus-active-sides.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-focus-active-fbg.gif); +} +.x-tab.x-tab-disabled .x-tab-default-top-tl, +.x-tab.x-tab-disabled .x-tab-default-top-bl, +.x-tab.x-tab-disabled .x-tab-default-top-tr, +.x-tab.x-tab-disabled .x-tab-default-top-br, +.x-tab.x-tab-disabled .x-tab-default-top-tc, +.x-tab.x-tab-disabled .x-tab-default-top-bc { + background-image: url(images/tab/tab-default-top-disabled-corners.gif); +} +.x-tab.x-tab-disabled .x-tab-default-top-ml, +.x-tab.x-tab-disabled .x-tab-default-top-mr { + background-image: url(images/tab/tab-default-top-disabled-sides.gif); +} +.x-tab.x-tab-disabled .x-tab-default-top-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-top-disabled-fbg.gif); +} +.x-tab-over .x-tab-default-right-tl, +.x-tab-over .x-tab-default-right-bl, +.x-tab-over .x-tab-default-right-tr, +.x-tab-over .x-tab-default-right-br, +.x-tab-over .x-tab-default-right-tc, +.x-tab-over .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-over-corners.gif); +} +.x-tab-over .x-tab-default-right-ml, +.x-tab-over .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-over-sides.gif); +} +.x-tab-over .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-over-fbg.gif); +} +.x-tab-focus .x-tab-default-right-tl, +.x-tab-focus .x-tab-default-right-bl, +.x-tab-focus .x-tab-default-right-tr, +.x-tab-focus .x-tab-default-right-br, +.x-tab-focus .x-tab-default-right-tc, +.x-tab-focus .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-corners.gif); +} +.x-tab-focus .x-tab-default-right-ml, +.x-tab-focus .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-sides.gif); +} +.x-tab-focus .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-fbg.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-right-tl, +.x-tab-focus.x-tab-over .x-tab-default-right-bl, +.x-tab-focus.x-tab-over .x-tab-default-right-tr, +.x-tab-focus.x-tab-over .x-tab-default-right-br, +.x-tab-focus.x-tab-over .x-tab-default-right-tc, +.x-tab-focus.x-tab-over .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-over-corners.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-right-ml, +.x-tab-focus.x-tab-over .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-over-sides.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-over-fbg.gif); +} +.x-tab.x-tab-active .x-tab-default-right-tl, +.x-tab.x-tab-active .x-tab-default-right-bl, +.x-tab.x-tab-active .x-tab-default-right-tr, +.x-tab.x-tab-active .x-tab-default-right-br, +.x-tab.x-tab-active .x-tab-default-right-tc, +.x-tab.x-tab-active .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-active-corners.gif); +} +.x-tab.x-tab-active .x-tab-default-right-ml, +.x-tab.x-tab-active .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-active-sides.gif); +} +.x-tab.x-tab-active .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-active-fbg.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-right-tl, +.x-tab-focus.x-tab-active .x-tab-default-right-bl, +.x-tab-focus.x-tab-active .x-tab-default-right-tr, +.x-tab-focus.x-tab-active .x-tab-default-right-br, +.x-tab-focus.x-tab-active .x-tab-default-right-tc, +.x-tab-focus.x-tab-active .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-focus-active-corners.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-right-ml, +.x-tab-focus.x-tab-active .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-focus-active-sides.gif); +} +.x-tab-focus.x-tab-active .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-focus-active-fbg.gif); +} +.x-tab.x-tab-disabled .x-tab-default-right-tl, +.x-tab.x-tab-disabled .x-tab-default-right-bl, +.x-tab.x-tab-disabled .x-tab-default-right-tr, +.x-tab.x-tab-disabled .x-tab-default-right-br, +.x-tab.x-tab-disabled .x-tab-default-right-tc, +.x-tab.x-tab-disabled .x-tab-default-right-bc { + background-image: url(images/tab/tab-default-right-disabled-corners.gif); +} +.x-tab.x-tab-disabled .x-tab-default-right-ml, +.x-tab.x-tab-disabled .x-tab-default-right-mr { + background-image: url(images/tab/tab-default-right-disabled-sides.gif); +} +.x-tab.x-tab-disabled .x-tab-default-right-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-right-disabled-fbg.gif); +} +.x-tab-over .x-tab-default-bottom-tl, +.x-tab-over .x-tab-default-bottom-bl, +.x-tab-over .x-tab-default-bottom-tr, +.x-tab-over .x-tab-default-bottom-br, +.x-tab-over .x-tab-default-bottom-tc, +.x-tab-over .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-over-corners.gif); +} +.x-tab-over .x-tab-default-bottom-ml, +.x-tab-over .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-over-sides.gif); +} +.x-tab-over .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-over-fbg.gif); +} +.x-tab-focus .x-tab-default-bottom-tl, +.x-tab-focus .x-tab-default-bottom-bl, +.x-tab-focus .x-tab-default-bottom-tr, +.x-tab-focus .x-tab-default-bottom-br, +.x-tab-focus .x-tab-default-bottom-tc, +.x-tab-focus .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-corners.gif); +} +.x-tab-focus .x-tab-default-bottom-ml, +.x-tab-focus .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-sides.gif); +} +.x-tab-focus .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-fbg.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-bottom-tl, +.x-tab-focus.x-tab-over .x-tab-default-bottom-bl, +.x-tab-focus.x-tab-over .x-tab-default-bottom-tr, +.x-tab-focus.x-tab-over .x-tab-default-bottom-br, +.x-tab-focus.x-tab-over .x-tab-default-bottom-tc, +.x-tab-focus.x-tab-over .x-tab-default-bottom-bc { + background-image: url(images/tab/tab-default-bottom-focus-over-corners.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-bottom-ml, +.x-tab-focus.x-tab-over .x-tab-default-bottom-mr { + background-image: url(images/tab/tab-default-bottom-focus-over-sides.gif); +} +.x-tab-focus.x-tab-over .x-tab-default-bottom-mc { + background-repeat: repeat-x; + background-image: url(images/tab/tab-default-bottom-focus-over-fbg.gif); +} diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all_2.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all_2.css new file mode 100644 index 0000000..b97e215 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/theme-triton-all_2.css @@ -0,0 +1 @@ +.x-tab.x-tab-active .x-tab-default-bottom-tl,.x-tab.x-tab-active .x-tab-default-bottom-bl,.x-tab.x-tab-active .x-tab-default-bottom-tr,.x-tab.x-tab-active .x-tab-default-bottom-br,.x-tab.x-tab-active .x-tab-default-bottom-tc,.x-tab.x-tab-active .x-tab-default-bottom-bc{background-image:url(images/tab/tab-default-bottom-active-corners.gif)}.x-tab.x-tab-active .x-tab-default-bottom-ml,.x-tab.x-tab-active .x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-active-sides.gif)}.x-tab.x-tab-active .x-tab-default-bottom-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-bottom-active-fbg.gif)}.x-tab-focus.x-tab-active .x-tab-default-bottom-tl,.x-tab-focus.x-tab-active .x-tab-default-bottom-bl,.x-tab-focus.x-tab-active .x-tab-default-bottom-tr,.x-tab-focus.x-tab-active .x-tab-default-bottom-br,.x-tab-focus.x-tab-active .x-tab-default-bottom-tc,.x-tab-focus.x-tab-active .x-tab-default-bottom-bc{background-image:url(images/tab/tab-default-bottom-focus-active-corners.gif)}.x-tab-focus.x-tab-active .x-tab-default-bottom-ml,.x-tab-focus.x-tab-active .x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-focus-active-sides.gif)}.x-tab-focus.x-tab-active .x-tab-default-bottom-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-bottom-focus-active-fbg.gif)}.x-tab.x-tab-disabled .x-tab-default-bottom-tl,.x-tab.x-tab-disabled .x-tab-default-bottom-bl,.x-tab.x-tab-disabled .x-tab-default-bottom-tr,.x-tab.x-tab-disabled .x-tab-default-bottom-br,.x-tab.x-tab-disabled .x-tab-default-bottom-tc,.x-tab.x-tab-disabled .x-tab-default-bottom-bc{background-image:url(images/tab/tab-default-bottom-disabled-corners.gif)}.x-tab.x-tab-disabled .x-tab-default-bottom-ml,.x-tab.x-tab-disabled .x-tab-default-bottom-mr{background-image:url(images/tab/tab-default-bottom-disabled-sides.gif)}.x-tab.x-tab-disabled .x-tab-default-bottom-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-bottom-disabled-fbg.gif)}.x-tab-over .x-tab-default-left-tl,.x-tab-over .x-tab-default-left-bl,.x-tab-over .x-tab-default-left-tr,.x-tab-over .x-tab-default-left-br,.x-tab-over .x-tab-default-left-tc,.x-tab-over .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-over-corners.gif)}.x-tab-over .x-tab-default-left-ml,.x-tab-over .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-over-sides.gif)}.x-tab-over .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-over-fbg.gif)}.x-tab-focus .x-tab-default-left-tl,.x-tab-focus .x-tab-default-left-bl,.x-tab-focus .x-tab-default-left-tr,.x-tab-focus .x-tab-default-left-br,.x-tab-focus .x-tab-default-left-tc,.x-tab-focus .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-focus-corners.gif)}.x-tab-focus .x-tab-default-left-ml,.x-tab-focus .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-focus-sides.gif)}.x-tab-focus .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-focus-fbg.gif)}.x-tab-focus.x-tab-over .x-tab-default-left-tl,.x-tab-focus.x-tab-over .x-tab-default-left-bl,.x-tab-focus.x-tab-over .x-tab-default-left-tr,.x-tab-focus.x-tab-over .x-tab-default-left-br,.x-tab-focus.x-tab-over .x-tab-default-left-tc,.x-tab-focus.x-tab-over .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-focus-over-corners.gif)}.x-tab-focus.x-tab-over .x-tab-default-left-ml,.x-tab-focus.x-tab-over .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-focus-over-sides.gif)}.x-tab-focus.x-tab-over .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-focus-over-fbg.gif)}.x-tab.x-tab-active .x-tab-default-left-tl,.x-tab.x-tab-active .x-tab-default-left-bl,.x-tab.x-tab-active .x-tab-default-left-tr,.x-tab.x-tab-active .x-tab-default-left-br,.x-tab.x-tab-active .x-tab-default-left-tc,.x-tab.x-tab-active .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-active-corners.gif)}.x-tab.x-tab-active .x-tab-default-left-ml,.x-tab.x-tab-active .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-active-sides.gif)}.x-tab.x-tab-active .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-active-fbg.gif)}.x-tab-focus.x-tab-active .x-tab-default-left-tl,.x-tab-focus.x-tab-active .x-tab-default-left-bl,.x-tab-focus.x-tab-active .x-tab-default-left-tr,.x-tab-focus.x-tab-active .x-tab-default-left-br,.x-tab-focus.x-tab-active .x-tab-default-left-tc,.x-tab-focus.x-tab-active .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-focus-active-corners.gif)}.x-tab-focus.x-tab-active .x-tab-default-left-ml,.x-tab-focus.x-tab-active .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-focus-active-sides.gif)}.x-tab-focus.x-tab-active .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-focus-active-fbg.gif)}.x-tab.x-tab-disabled .x-tab-default-left-tl,.x-tab.x-tab-disabled .x-tab-default-left-bl,.x-tab.x-tab-disabled .x-tab-default-left-tr,.x-tab.x-tab-disabled .x-tab-default-left-br,.x-tab.x-tab-disabled .x-tab-default-left-tc,.x-tab.x-tab-disabled .x-tab-default-left-bc{background-image:url(images/tab/tab-default-left-disabled-corners.gif)}.x-tab.x-tab-disabled .x-tab-default-left-ml,.x-tab.x-tab-disabled .x-tab-default-left-mr{background-image:url(images/tab/tab-default-left-disabled-sides.gif)}.x-tab.x-tab-disabled .x-tab-default-left-mc{background-repeat:repeat-x;background-image:url(images/tab/tab-default-left-disabled-fbg.gif)}.x-tab-default-tl,.x-tab-default-bl,.x-tab-default-tr,.x-tab-default-br{-ms-filter:"progid:DXImageTransform.Microsoft.gradient(startColorstr=#00FFFFFF,endColorstr=#00FFFFFF)"}.x-tab-default .x-tab-close-btn{top:0;right:0;width:16px;height:16px;font:12px/1 FontAwesome;color:#fff}.x-tab-default .x-tab-close-btn:before{content:"\f00d"}.x-tab-bar-plain .x-tab-default .x-tab-close-btn{color:#919191}.x-tab-default .x-tab-close-btn-over{background-position:-16px 0}.x-tab-default .x-tab-close-btn-pressed{background-position:-32px 0}.x-keyboard-mode .x-tab-default.x-tab-focus .x-tab-close-btn{color:#fff}.x-keyboard-mode .x-tab-bar-plain .x-tab-default.x-tab-focus .x-tab-close-btn{color:#919191}.x-tab-default.x-tab-over .x-tab-close-btn{color:#fff}.x-tab-bar-plain .x-tab-default.x-tab-over .x-tab-close-btn{color:#919191}.x-keyboard-mode .x-tab-default.x-tab-focus.x-tab-over .x-tab-close-btn{color:#fff}.x-keyboard-mode .x-tab-bar-plain .x-tab-default.x-tab-focus.x-tab-over .x-tab-close-btn{color:#919191}.x-tab-default.x-tab-active .x-tab-close-btn{color:#919191}.x-keyboard-mode .x-tab-default.x-tab-focus.x-tab-active .x-tab-close-btn{color:#919191}.x-tab-default.x-tab-disabled .x-tab-close-btn{color:#fff;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=30)";opacity:0.3;background-position:0 0}.x-tab-bar-plain .x-tab-default.x-tab-disabled .x-tab-close-btn{color:#919191}.x-tab-closable.x-tab-default .x-tab-button{padding-right:16px}.x-tab-bar-default{background-color:#5fa2dd}.x-tab-bar-default-top > .x-tab-bar-body-default{padding:8px 4px 0 8px}.x-tab-bar-default-bottom > .x-tab-bar-body-default{padding:0 4px 8px 8px}.x-tab-bar-default-left > .x-tab-bar-body-default{padding:4px 0 8px 8px}.x-tab-bar-default-right > .x-tab-bar-body-default{padding:8px 8px 4px 0}.x-tab-bar-plain.x-tab-bar-default-top > .x-tab-bar-body-default{padding:8px 0 0}.x-tab-bar-plain.x-tab-bar-default-bottom > .x-tab-bar-body-default{padding:0 0 8px 0}.x-tab-bar-plain.x-tab-bar-default-left > .x-tab-bar-body-default{padding:0 0 0 8px}.x-tab-bar-plain.x-tab-bar-default-right > .x-tab-bar-body-default{padding:0 8px 0 0}.x-tab-bar-plain.x-tab-bar-default-horizontal{border-top-color:transparent;border-bottom-color:transparent;border-left-width:0;border-right-width:0}.x-tab-bar-plain.x-tab-bar-default-vertical{border-right-color:transparent;border-left-color:transparent;border-top-width:0;border-bottom-width:0}.x-tab-bar-horizontal > .x-tab-bar-body-default{min-height:44px}.x-ie8m .x-tab-bar-horizontal > .x-tab-bar-body-default{min-height:36px}.x-tab-bar-vertical > .x-tab-bar-body-default{min-width:44px}.x-ie8m .x-tab-bar-vertical > .x-tab-bar-body-default{min-width:36px}.x-tab-bar-default-scroller .x-box-scroller-body-horizontal{margin-left:16px}.x-tab-bar-default-vertical-scroller .x-box-scroller-body-vertical{margin-top:16px}.x-box-scroller-tab-bar-default{cursor:pointer;color:#fff;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-box-scroller-tab-bar-default.x-box-scroller-hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-box-scroller-tab-bar-default.x-box-scroller-pressed{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=70)";opacity:0.7}.x-box-scroller-tab-bar-default.x-box-scroller-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=25)";opacity:0.25;cursor:default}.x-box-scroller-tab-bar-default.x-box-scroller-left,.x-box-scroller-tab-bar-default.x-box-scroller-right{width:24px;height:24px;top:50%;margin-top:-12px}.x-box-scroller-tab-bar-default.x-box-scroller-left{margin-left:0;margin-right:0;margin-bottom:0;font:16px/24px FontAwesome}.x-box-scroller-tab-bar-default.x-box-scroller-left:before{content:"\f053"}.x-box-scroller-tab-bar-default.x-box-scroller-right{margin-left:0;margin-right:0;margin-bottom:0;font:16px/24px FontAwesome}.x-box-scroller-tab-bar-default.x-box-scroller-right:before{content:"\f054"}.x-box-scroller-tab-bar-default.x-box-scroller-top,.x-box-scroller-tab-bar-default.x-box-scroller-bottom{height:24px;width:24px;left:50%;margin-left:-12px}.x-box-scroller-tab-bar-default.x-box-scroller-top{margin-top:0;margin-right:0;margin-bottom:0;font:16px/24px FontAwesome}.x-box-scroller-tab-bar-default.x-box-scroller-top:before{content:"\f077"}.x-box-scroller-tab-bar-default.x-box-scroller-bottom{margin-top:0;margin-right:0;margin-bottom:0;font:16px/24px FontAwesome}.x-box-scroller-tab-bar-default.x-box-scroller-bottom:before{content:"\f078"}.x-tab-bar-more-icon{font:16px/1 FontAwesome;color:#f0f0f0}.x-tab-bar-more-icon:before{content:"\f0c9"}.x-tab-bar-plain.x-tab-bar-default-scroller .x-box-scroller-body-horizontal{margin-left:24px}.x-tab-bar-plain.x-tab-bar-default-vertical-scroller .x-box-scroller-body-vertical{margin-top:16px}.x-tab-bar-plain .x-box-scroller-tab-bar-default{color:#919191}.x-tab-bar-default-top .x-box-scroller-tab-bar-default{margin-top:-8px}.x-tab-bar-default-right .x-box-scroller-tab-bar-default{margin-left:-16px}.x-tab-bar-default-bottom .x-box-scroller-tab-bar-default{margin-top:-16px}.x-tab-bar-default-left .x-box-scroller-tab-bar-default{margin-left:-8px}.x-box-scroller-tab-bar-default{background-color:#5fa2dd}.x-box-scroller-tab-bar-default .x-ie8 .x-box-scroller-plain{background-color:#fff}.x-breadcrumb-btn-default{margin:0 0 0 0px}.x-breadcrumb-icon-folder-default{font:16px/1 FontAwesome;color:#919191}.x-breadcrumb-icon-folder-default:before{content:"\f114"}.x-btn-menu-active .x-breadcrumb-icon-folder-default{font:16px/1 FontAwesome;color:#919191}.x-btn-menu-active .x-breadcrumb-icon-folder-default:before{content:"\f115"}.x-breadcrumb-icon-leaf-default{font:16px/1 FontAwesome;color:#919191}.x-breadcrumb-icon-leaf-default:before{content:"\f016"}.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-arrow:after{width:20px;background-image:url(images/breadcrumb/default-arrow.png)}.x-btn-menu-active.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-arrow:after{background-image:url(images/breadcrumb/default-arrow-open.png)}.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after{width:20px;content:"\f105";font:16px/1 FontAwesome;color:#919191;background:none !important}.x-btn-menu-active.x-breadcrumb-btn .x-btn-wrap-plain-toolbar-small.x-btn-split:after{content:"\f107";font:16px/1 FontAwesome;color:#919191;background:none !important}.x-breadcrumb-default-scroller .x-box-scroller-body-horizontal{margin-left:32px}.x-breadcrumb-default-vertical-scroller .x-box-scroller-body-vertical{margin-top:24px}.x-box-scroller-breadcrumb-default{cursor:pointer;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=60)";opacity:0.6}.x-box-scroller-breadcrumb-default.x-box-scroller-hover{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=80)";opacity:0.8}.x-box-scroller-breadcrumb-default.x-box-scroller-pressed{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";opacity:1}.x-box-scroller-breadcrumb-default.x-box-scroller-disabled{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=25)";opacity:0.25;cursor:default}.x-box-scroller-breadcrumb-default.x-box-scroller-left,.x-box-scroller-breadcrumb-default.x-box-scroller-right{width:24px;height:24px;top:50%;margin-top:-12px}.x-box-scroller-breadcrumb-default.x-box-scroller-left{margin-left:4px;margin-right:4px;margin-bottom:0;background-image:url(images/breadcrumb/default-scroll-left.png)}.x-box-scroller-breadcrumb-default.x-box-scroller-right{margin-left:4px;margin-right:4px;margin-bottom:0;background-image:url(images/breadcrumb/default-scroll-right.png)}.x-tree-expander{cursor:pointer}.x-tree-arrows .x-tree-expander{font-size:16px;font-family:FontAwesome;color:#5fa2dd}.x-tree-arrows .x-tree-expander:before{content:"\f0da"}.x-tree-arrows .x-grid-tree-node-expanded .x-tree-expander{font-size:16px;font-family:FontAwesome;color:#5fa2dd}.x-tree-arrows .x-grid-tree-node-expanded .x-tree-expander:before{content:"\f0d7"}.x-tree-elbow-plus,.x-tree-elbow-end-plus{font-size:14px;font-family:FontAwesome;color:#5fa2dd}.x-tree-elbow-plus:before,.x-tree-elbow-end-plus:before{content:"\f0fe"}.x-grid-tree-node-expanded .x-tree-elbow-plus,.x-grid-tree-node-expanded .x-tree-elbow-end-plus{font-size:14px;font-family:FontAwesome;color:#5fa2dd}.x-grid-tree-node-expanded .x-tree-elbow-plus:before,.x-grid-tree-node-expanded .x-tree-elbow-end-plus:before{content:"\f146"}.x-tree-icon{width:16px;height:32px;line-height:32px;color:#5fa2dd;font-size:16px}.x-tree-elbow-img{width:18px;height:32px;line-height:32px;margin-right:4px}.x-tree-icon,.x-tree-elbow-img,.x-tree-checkbox{margin-top:-7px;margin-bottom:-6px}.x-tree-icon-leaf{font-size:16px;font-family:FontAwesome;color:#5fa2dd}.x-tree-icon-leaf:before{content:"\f016"}.x-tree-icon-parent{font-size:16px;font-family:FontAwesome;color:#5fa2dd}.x-tree-icon-parent:before{content:"\f114"}.x-tree-icon-parent-expanded{font-size:16px;font-family:FontAwesome;color:#5fa2dd}.x-tree-icon-parent-expanded:before{content:"\f115"}.x-tree-icon-custom{background-image:none}.x-tree-icon-custom:before{content:''}.x-tree-checkbox{margin-right:6px;top:7px;width:18px;height:18px;font:18px/1 ExtJS;color:#5fa2dd}.x-tree-checkbox:before{content:"\e614"}.x-tree-checkbox-checked{font:18px/1 ExtJS}.x-tree-checkbox-checked:before{content:"\e613"}.x-grid-tree-loading .x-tree-icon{background-image:url(images/tree/loading.gif)}.x-tree-node-text{padding-left:6px}.x-grid-cell-inner-treecolumn{padding:7px 10px 6px 6px}.x-tree-drop-ok-append .x-dd-drop-icon,.x-tree-drop-ok-above .x-dd-drop-icon,.x-tree-drop-ok-below .x-dd-drop-icon,.x-tree-drop-ok-between .x-dd-drop-icon{font:16px/1 FontAwesome;color:#a4cf6d}.x-tree-drop-ok-append .x-dd-drop-icon:before,.x-tree-drop-ok-above .x-dd-drop-icon:before,.x-tree-drop-ok-below .x-dd-drop-icon:before,.x-tree-drop-ok-between .x-dd-drop-icon:before{content:"\f055"}.x-tree-ddindicator{height:1px;border-width:1px 0px 0px;border-style:dotted;border-color:green}.x-multiselector-remove{font-size:110%;color:#d0d0d0;cursor:pointer}.x-multiselector-remove .x-grid-cell-inner{padding:7px 4px 6px 4px}.x-grid-item-over .x-multiselector-remove{color:red}.x-multiselector-search-input .x-form-text::-ms-clear{display:none}.x-toast-icon-information{background-image:url(images/window/toast/icon16_info.png)}.x-toast-icon-error{background-image:url(images/window/toast/icon16_error.png)}.x-toast-window .x-window-body{padding:15px 5px 15px 5px}.x-toast-light .x-window-header{background-color:#7fb5e4}.x-toast-light .x-tool-img{background-color:#7fb5e4}.x-toast-light{background-image:url(images/window/toast/fader.png)}.x-toast-light .x-window-body{padding:15px 5px 20px 5px;background-color:transparent;border:0px solid white}.x-btn-plain-toolbar-small{-webkit-border-radius:0;-moz-border-radius:0;-ms-border-radius:0;-o-border-radius:0;border-radius:0;padding:7px 7px 7px 7px;border-width:1px;border-style:solid;background-color:transparent}.x-btn-plain-toolbar-small-mc{background-color:transparent}.x-nbr .x-btn-plain-toolbar-small{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-btn-plain-toolbar-small-frameInfo{font-family:th-1-1-1-1-1-1-1-1-7-7-7-7}.x-btn-plain-toolbar-small-tl{background-position:0 -2px}.x-btn-plain-toolbar-small-tr{background-position:right -3px}.x-btn-plain-toolbar-small-bl{background-position:0 -4px}.x-btn-plain-toolbar-small-br{background-position:right -5px}.x-btn-plain-toolbar-small-ml{background-position:0 top}.x-btn-plain-toolbar-small-mr{background-position:right top}.x-btn-plain-toolbar-small-tc{background-position:0 0}.x-btn-plain-toolbar-small-bc{background-position:0 -1px}.x-btn-plain-toolbar-small-tr,.x-btn-plain-toolbar-small-br,.x-btn-plain-toolbar-small-mr{padding-right:1px}.x-btn-plain-toolbar-small-tl,.x-btn-plain-toolbar-small-bl,.x-btn-plain-toolbar-small-ml{padding-left:1px}.x-btn-plain-toolbar-small-tc{height:1px}.x-btn-plain-toolbar-small-bc{height:1px}.x-btn-plain-toolbar-small-mc{padding:7px 7px 7px 7px}.x-btn-plain-toolbar-small{border-color:transparent}.x-btn-button-plain-toolbar-small{min-height:16px}.x-ie9m .x-btn-button-plain-toolbar-small{min-height:auto;height:16px}.x-btn-inner-plain-toolbar-small{font:400 12px/16px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif;color:#606060;padding:0 5px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-small,.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-small{max-width:calc(100% - 16px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-small,.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-small{max-width:calc(100% - 15px)}.x-ie10p .x-btn-inner-plain-toolbar-small{max-width:none}.x-btn-icon-el-plain-toolbar-small{font-size:16px;height:16px;color:#919191;line-height:16px}.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small,.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small{width:16px}.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small,.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small{min-width:16px}.x-ie8 .x-btn-icon-el-plain-toolbar-small.x-btn-glyph{color:#919191}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-small{margin-right:3px}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small{margin-left:3px}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-small{margin-bottom:8px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-small{margin-top:8px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small{padding-right:8px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small{margin-right:5px}.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-small,.x-btn-split-bottom > .x-btn-button-plain-toolbar-small{padding-bottom:7px}.x-btn-wrap-plain-toolbar-small.x-btn-arrow-right:after{width:18px;content:"\f0d7";font:16px/1 FontAwesome;color:#606060}.x-btn-wrap-plain-toolbar-small.x-btn-arrow-bottom:after{height:12px;content:"\f0d7";font:16px/12px FontAwesome;color:#606060}.x-btn-wrap-plain-toolbar-small.x-btn-split-right > .x-btn-button{padding-right:7px}.x-btn-wrap-plain-toolbar-small.x-btn-split-right > .x-btn-button:after{border-right:1px solid #e4e4e4}.x-btn-wrap-plain-toolbar-small.x-btn-split-right:after{width:20px;content:"\f0d7";font:16px/1 FontAwesome;color:#606060;padding-left:7px}.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom{margin-bottom:-7px}.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom > .x-btn-button:after{border-bottom:1px solid #e4e4e4}.x-btn-wrap-plain-toolbar-small.x-btn-split-bottom:after{height:20px;content:"\f0d7";font:16px/20px FontAwesome;color:#606060}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-small{padding-right:8px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-small{margin-right:5px}.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-small{background-image:none;background-color:transparent;-webkit-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;-moz-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset}.x-btn-plain-toolbar-small .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:27px;pointer-events:none}.x-keyboard-mode .x-btn-plain-toolbar-small.x-arrow-focus .x-btn-arrow-el{border:1px solid #5fa2dd}.x-btn-over.x-btn-plain-toolbar-small{border-color:#dbdbdb;background-image:none;background-color:#ececec}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-small{-webkit-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;-moz-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-plain-toolbar-small,.x-btn.x-btn-pressed.x-btn-plain-toolbar-small{border-color:#d2d2d2;background-image:none;background-color:#e2e2e2}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small{-webkit-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;-moz-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-plain-toolbar-small{background-image:none;background-color:transparent}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tr,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-br,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-tc,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-ml,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-small-mc{background-color:transparent}.x-btn-over .x-btn-plain-toolbar-small-tl,.x-btn-over .x-btn-plain-toolbar-small-bl,.x-btn-over .x-btn-plain-toolbar-small-tr,.x-btn-over .x-btn-plain-toolbar-small-br,.x-btn-over .x-btn-plain-toolbar-small-tc,.x-btn-over .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-over-corners.gif)}.x-btn-over .x-btn-plain-toolbar-small-ml,.x-btn-over .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-over-sides.gif)}.x-btn-over .x-btn-plain-toolbar-small-mc{background-color:#ececec}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-small-mc{background-color:#ececec}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tr,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-br,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-tc,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-bc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-br,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-tc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-ml,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-ml,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-small-mc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-small-mc{background-color:#e2e2e2}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-small-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-small-mc{background-color:#e2e2e2}.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tr,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-br,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-tc,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-bc{background-image:url(images/btn/btn-plain-toolbar-small-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-ml,.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mr{background-image:url(images/btn/btn-plain-toolbar-small-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-small-mc{background-color:transparent}.x-nbr .x-btn-plain-toolbar-small{background-image:none}.x-btn-disabled.x-btn-plain-toolbar-small{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first .x-btn-plain-toolbar-small-mc{padding-right:7px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-middle .x-btn-plain-toolbar-small-mc{padding-right:7px !important;padding-left:7px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last .x-btn-plain-toolbar-small-mc{padding-left:7px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first .x-btn-plain-toolbar-small-mc{padding-bottom:7px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-middle .x-btn-plain-toolbar-small-mc{padding-top:7px !important;padding-bottom:7px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last .x-btn-plain-toolbar-small-mc{padding-top:7px !important}.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-small:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-small.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-small.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-small:after{border-width:1px;border-color:#5fa2dd}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-small:after{border-width:1px;border-color:#5fa2dd}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-small:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-small:after{border-width:1px;border-color:#5fa2dd}.x-button-plain-toolbar-small-cell > .x-grid-cell-inner{padding-top:0px;padding-bottom:0px}.x-button-plain-toolbar-small-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-small{vertical-align:top}.x-btn-plain-toolbar-medium{-webkit-border-radius:0;-moz-border-radius:0;-ms-border-radius:0;-o-border-radius:0;border-radius:0;padding:8px 8px 8px 8px;border-width:1px;border-style:solid;background-color:transparent}.x-btn-plain-toolbar-medium-mc{background-color:transparent}.x-nbr .x-btn-plain-toolbar-medium{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-btn-plain-toolbar-medium-frameInfo{font-family:th-1-1-1-1-1-1-1-1-8-8-8-8}.x-btn-plain-toolbar-medium-tl{background-position:0 -2px}.x-btn-plain-toolbar-medium-tr{background-position:right -3px}.x-btn-plain-toolbar-medium-bl{background-position:0 -4px}.x-btn-plain-toolbar-medium-br{background-position:right -5px}.x-btn-plain-toolbar-medium-ml{background-position:0 top}.x-btn-plain-toolbar-medium-mr{background-position:right top}.x-btn-plain-toolbar-medium-tc{background-position:0 0}.x-btn-plain-toolbar-medium-bc{background-position:0 -1px}.x-btn-plain-toolbar-medium-tr,.x-btn-plain-toolbar-medium-br,.x-btn-plain-toolbar-medium-mr{padding-right:1px}.x-btn-plain-toolbar-medium-tl,.x-btn-plain-toolbar-medium-bl,.x-btn-plain-toolbar-medium-ml{padding-left:1px}.x-btn-plain-toolbar-medium-tc{height:1px}.x-btn-plain-toolbar-medium-bc{height:1px}.x-btn-plain-toolbar-medium-mc{padding:8px 8px 8px 8px}.x-btn-plain-toolbar-medium{border-color:transparent}.x-btn-button-plain-toolbar-medium{min-height:20px}.x-ie9m .x-btn-button-plain-toolbar-medium{min-height:auto;height:20px}.x-btn-inner-plain-toolbar-medium{font:400 14px/18px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif;color:#606060;padding:0 8px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium,.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium{max-width:calc(100% - 20px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-medium,.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-medium{max-width:calc(100% - 19px)}.x-ie10p .x-btn-inner-plain-toolbar-medium{max-width:none}.x-btn-icon-el-plain-toolbar-medium{font-size:20px;height:20px;color:#919191;line-height:20px}.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium,.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium{width:20px}.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium,.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium{min-width:20px}.x-ie8 .x-btn-icon-el-plain-toolbar-medium.x-btn-glyph{color:#919191}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-medium{margin-right:0px}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium{margin-left:0px}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-medium{margin-bottom:8px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-medium{margin-top:8px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium{padding-right:8px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium{margin-right:8px}.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-medium,.x-btn-split-bottom > .x-btn-button-plain-toolbar-medium{padding-bottom:8px}.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-right:after{width:20px;content:"\f0d7";font:20px/1 FontAwesome;color:#606060}.x-btn-wrap-plain-toolbar-medium.x-btn-arrow-bottom:after{height:14px;content:"\f0d7";font:20px/14px FontAwesome;color:#606060}.x-btn-wrap-plain-toolbar-medium.x-btn-split-right > .x-btn-button{padding-right:8px}.x-btn-wrap-plain-toolbar-medium.x-btn-split-right > .x-btn-button:after{border-right:1px solid #e4e4e4}.x-btn-wrap-plain-toolbar-medium.x-btn-split-right:after{width:26px;content:"\f0d7";font:20px/1 FontAwesome;color:#606060;padding-left:8px}.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom{margin-bottom:-8px}.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom > .x-btn-button:after{border-bottom:1px solid #e4e4e4}.x-btn-wrap-plain-toolbar-medium.x-btn-split-bottom:after{height:24px;content:"\f0d7";font:20px/24px FontAwesome;color:#606060}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-medium{padding-right:8px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-medium{margin-right:8px}.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-medium{background-image:none;background-color:transparent;-webkit-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;-moz-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset}.x-btn-plain-toolbar-medium .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:34px;pointer-events:none}.x-keyboard-mode .x-btn-plain-toolbar-medium.x-arrow-focus .x-btn-arrow-el{border:1px solid #5fa2dd}.x-btn-over.x-btn-plain-toolbar-medium{border-color:#dbdbdb;background-image:none;background-color:#ececec}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium{-webkit-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;-moz-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-plain-toolbar-medium,.x-btn.x-btn-pressed.x-btn-plain-toolbar-medium{border-color:#d2d2d2;background-image:none;background-color:#e2e2e2}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium{-webkit-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;-moz-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-plain-toolbar-medium{background-image:none;background-color:transparent}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-br,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-medium-mc{background-color:transparent}.x-btn-over .x-btn-plain-toolbar-medium-tl,.x-btn-over .x-btn-plain-toolbar-medium-bl,.x-btn-over .x-btn-plain-toolbar-medium-tr,.x-btn-over .x-btn-plain-toolbar-medium-br,.x-btn-over .x-btn-plain-toolbar-medium-tc,.x-btn-over .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-over-corners.gif)}.x-btn-over .x-btn-plain-toolbar-medium-ml,.x-btn-over .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-over-sides.gif)}.x-btn-over .x-btn-plain-toolbar-medium-mc{background-color:#ececec}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-medium-mc{background-color:#ececec}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tr,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-br,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-tc,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-bc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-br,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-tc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-ml,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-ml,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-medium-mc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-medium-mc{background-color:#e2e2e2}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-medium-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-medium-mc{background-color:#e2e2e2}.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tr,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-br,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-tc,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-bc{background-image:url(images/btn/btn-plain-toolbar-medium-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-ml,.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mr{background-image:url(images/btn/btn-plain-toolbar-medium-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-medium-mc{background-color:transparent}.x-nbr .x-btn-plain-toolbar-medium{background-image:none}.x-btn-disabled.x-btn-plain-toolbar-medium{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first .x-btn-plain-toolbar-medium-mc{padding-right:8px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-middle .x-btn-plain-toolbar-medium-mc{padding-right:8px !important;padding-left:8px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last .x-btn-plain-toolbar-medium-mc{padding-left:8px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first .x-btn-plain-toolbar-medium-mc{padding-bottom:8px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-middle .x-btn-plain-toolbar-medium-mc{padding-top:8px !important;padding-bottom:8px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last .x-btn-plain-toolbar-medium-mc{padding-top:8px !important}.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-medium:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-medium.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-medium.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-medium:after{border-width:1px;border-color:#5fa2dd}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-medium:after{border-width:1px;border-color:#5fa2dd}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-medium:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-medium:after{border-width:1px;border-color:#5fa2dd}.x-button-plain-toolbar-medium-cell > .x-grid-cell-inner{padding-top:0;padding-bottom:0}.x-button-plain-toolbar-medium-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-medium{vertical-align:top}.x-btn-plain-toolbar-large{-webkit-border-radius:0;-moz-border-radius:0;-ms-border-radius:0;-o-border-radius:0;border-radius:0;padding:9px 9px 9px 9px;border-width:1px;border-style:solid;background-color:transparent}.x-btn-plain-toolbar-large-mc{background-color:transparent}.x-nbr .x-btn-plain-toolbar-large{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-btn-plain-toolbar-large-frameInfo{font-family:th-1-1-1-1-1-1-1-1-9-9-9-9}.x-btn-plain-toolbar-large-tl{background-position:0 -2px}.x-btn-plain-toolbar-large-tr{background-position:right -3px}.x-btn-plain-toolbar-large-bl{background-position:0 -4px}.x-btn-plain-toolbar-large-br{background-position:right -5px}.x-btn-plain-toolbar-large-ml{background-position:0 top}.x-btn-plain-toolbar-large-mr{background-position:right top}.x-btn-plain-toolbar-large-tc{background-position:0 0}.x-btn-plain-toolbar-large-bc{background-position:0 -1px}.x-btn-plain-toolbar-large-tr,.x-btn-plain-toolbar-large-br,.x-btn-plain-toolbar-large-mr{padding-right:1px}.x-btn-plain-toolbar-large-tl,.x-btn-plain-toolbar-large-bl,.x-btn-plain-toolbar-large-ml{padding-left:1px}.x-btn-plain-toolbar-large-tc{height:1px}.x-btn-plain-toolbar-large-bc{height:1px}.x-btn-plain-toolbar-large-mc{padding:9px 9px 9px 9px}.x-btn-plain-toolbar-large{border-color:transparent}.x-btn-button-plain-toolbar-large{min-height:24px}.x-ie9m .x-btn-button-plain-toolbar-large{min-height:auto;height:24px}.x-btn-inner-plain-toolbar-large{font:400 16px/20px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif;color:#606060;padding:0 10px;max-width:100%}.x-ie9 .x-btn-icon-right > .x-btn-inner-plain-toolbar-large,.x-ie9 .x-btn-icon-left > .x-btn-inner-plain-toolbar-large{max-width:calc(100% - 24px)}.x-safari8m .x-btn-icon-right > .x-btn-inner-plain-toolbar-large,.x-safari8m .x-btn-icon-left > .x-btn-inner-plain-toolbar-large{max-width:calc(100% - 23px)}.x-ie10p .x-btn-inner-plain-toolbar-large{max-width:none}.x-btn-icon-el-plain-toolbar-large{font-size:24px;height:24px;color:#919191;line-height:24px}.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large,.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large{width:24px}.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large,.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large{min-width:24px}.x-ie8 .x-btn-icon-el-plain-toolbar-large.x-btn-glyph{color:#919191}.x-btn-text.x-btn-icon-left > .x-btn-icon-el-plain-toolbar-large{margin-right:0}.x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large{margin-left:0}.x-btn-text.x-btn-icon-top > .x-btn-icon-el-plain-toolbar-large{margin-bottom:8px}.x-btn-text.x-btn-icon-bottom > .x-btn-icon-el-plain-toolbar-large{margin-top:8px}.x-btn-arrow-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large{padding-right:8px}.x-btn-arrow-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large{margin-right:10px}.x-btn-arrow-bottom > .x-btn-button-plain-toolbar-large,.x-btn-split-bottom > .x-btn-button-plain-toolbar-large{padding-bottom:9px}.x-btn-wrap-plain-toolbar-large.x-btn-arrow-right:after{width:22px;content:"\f0d7";font:24px/1 FontAwesome;color:#606060}.x-btn-wrap-plain-toolbar-large.x-btn-arrow-bottom:after{height:16px;content:"\f0d7";font:24px/16px FontAwesome;color:#606060}.x-btn-wrap-plain-toolbar-large.x-btn-split-right > .x-btn-button{padding-right:9px}.x-btn-wrap-plain-toolbar-large.x-btn-split-right > .x-btn-button:after{border-right:1px solid #e4e4e4}.x-btn-wrap-plain-toolbar-large.x-btn-split-right:after{width:32px;content:"\f0d7";font:24px/1 FontAwesome;color:#606060;padding-left:9px}.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom{margin-bottom:-9px}.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom > .x-btn-button:after{border-bottom:1px solid #e4e4e4}.x-btn-wrap-plain-toolbar-large.x-btn-split-bottom:after{height:28px;content:"\f0d7";font:24px/28px FontAwesome;color:#606060}.x-btn-split-right > .x-btn-icon.x-btn-no-text.x-btn-button-plain-toolbar-large{padding-right:8px}.x-btn-split-right > .x-btn-text.x-btn-icon-right > .x-btn-icon-el-plain-toolbar-large{margin-right:10px}.x-keyboard-mode .x-btn-focus.x-btn-plain-toolbar-large{background-image:none;background-color:transparent;-webkit-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;-moz-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset}.x-btn-plain-toolbar-large .x-btn-arrow-el{position:absolute;top:0;right:0;height:100%;width:41px;pointer-events:none}.x-keyboard-mode .x-btn-plain-toolbar-large.x-arrow-focus .x-btn-arrow-el{border:1px solid #5fa2dd}.x-btn-over.x-btn-plain-toolbar-large{border-color:#dbdbdb;background-image:none;background-color:#ececec}.x-keyboard-mode .x-btn-focus.x-btn-over.x-btn-plain-toolbar-large{-webkit-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;-moz-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset}.x-btn.x-btn-menu-active.x-btn-plain-toolbar-large,.x-btn.x-btn-pressed.x-btn-plain-toolbar-large{border-color:#d2d2d2;background-image:none;background-color:#e2e2e2}.x-keyboard-mode .x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large,.x-keyboard-mode .x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large{-webkit-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;-moz-box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset;box-shadow:#5fa2dd 0 1px 0px 0 inset, #5fa2dd 0 -1px 0px 0 inset, #5fa2dd -1px 0 0px 0 inset, #5fa2dd 1px 0 0px 0 inset}.x-btn.x-btn-disabled.x-btn-plain-toolbar-large{background-image:none;background-color:transparent}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bl,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tr,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-br,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-tc,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-focus-corners.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-ml,.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-focus-sides.gif)}.x-keyboard-mode .x-btn-focus .x-btn-plain-toolbar-large-mc{background-color:transparent}.x-btn-over .x-btn-plain-toolbar-large-tl,.x-btn-over .x-btn-plain-toolbar-large-bl,.x-btn-over .x-btn-plain-toolbar-large-tr,.x-btn-over .x-btn-plain-toolbar-large-br,.x-btn-over .x-btn-plain-toolbar-large-tc,.x-btn-over .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-over-corners.gif)}.x-btn-over .x-btn-plain-toolbar-large-ml,.x-btn-over .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-over-sides.gif)}.x-btn-over .x-btn-plain-toolbar-large-mc{background-color:#ececec}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-br,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-focus-over-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-focus-over-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-over .x-btn-plain-toolbar-large-mc{background-color:#ececec}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bl,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tr,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-br,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-tc,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-bc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bl,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-br,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-tc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-pressed-corners.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-ml,.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mr,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-ml,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-pressed-sides.gif)}.x-btn.x-btn-menu-active .x-btn-plain-toolbar-large-mc,.x-btn.x-btn-pressed .x-btn-plain-toolbar-large-mc{background-color:#e2e2e2}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-br,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-bc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bl,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-br,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-tc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-focus-pressed-corners.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mr,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-ml,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-focus-pressed-sides.gif)}.x-keyboard-mode .x-btn-focus.x-btn-menu-active .x-btn-plain-toolbar-large-mc,.x-keyboard-mode .x-btn-focus.x-btn-pressed .x-btn-plain-toolbar-large-mc{background-color:#e2e2e2}.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bl,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tr,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-br,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-tc,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-bc{background-image:url(images/btn/btn-plain-toolbar-large-disabled-corners.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-ml,.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mr{background-image:url(images/btn/btn-plain-toolbar-large-disabled-sides.gif)}.x-btn.x-btn-disabled .x-btn-plain-toolbar-large-mc{background-color:transparent}.x-nbr .x-btn-plain-toolbar-large{background-image:none}.x-btn-disabled.x-btn-plain-toolbar-large{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first .x-btn-plain-toolbar-large-mc{padding-right:9px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle{border-right-width:1px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-middle .x-btn-plain-toolbar-large-mc{padding-right:9px !important;padding-left:9px !important}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last .x-btn-plain-toolbar-large-mc{padding-left:9px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first .x-btn-plain-toolbar-large-mc{padding-bottom:9px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle{border-bottom-width:1px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-middle .x-btn-plain-toolbar-large-mc{padding-top:9px !important;padding-bottom:9px !important}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last .x-btn-plain-toolbar-large-mc{padding-top:9px !important}.x-nbr .x-segmented-button-item.x-btn-plain-toolbar-large:after{content:' ';border-style:solid;border-width:0;position:absolute}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large:after{top:1px;right:0;bottom:1px;left:0}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-first:after{left:1px}.x-nbr .x-segmented-button-item-horizontal.x-btn-plain-toolbar-large.x-segmented-button-last:after{right:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large:after{top:0;right:1px;bottom:0;left:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-first:after{top:1px}.x-nbr .x-segmented-button-item-vertical.x-btn-plain-toolbar-large.x-segmented-button-last:after{bottom:1px}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-plain-toolbar-large:after{border-width:1px;border-color:#5fa2dd}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-over.x-btn-plain-toolbar-large:after{border-width:1px;border-color:#5fa2dd}.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-menu-active.x-btn-plain-toolbar-large:after,.x-keyboard-mode .x-nbr .x-segmented-button-item.x-btn-focus.x-btn-pressed.x-btn-plain-toolbar-large:after{border-width:1px;border-color:#5fa2dd}.x-button-plain-toolbar-large-cell > .x-grid-cell-inner{padding-top:0;padding-bottom:0}.x-button-plain-toolbar-large-cell > .x-grid-cell-inner >.x-btn-plain-toolbar-large{vertical-align:top}.x-btn-plain-toolbar-small-disabled .x-btn-icon-el,.x-btn-plain-toolbar-medium-disabled .x-btn-icon-el,.x-btn-plain-toolbar-large-disabled .x-btn-icon-el{background-color:#fff}.x-ie8 .x-btn-plain-toolbar-small-disabled .x-btn-icon-el,.x-ie8 .x-btn-plain-toolbar-medium-disabled .x-btn-icon-el,.x-ie8 .x-btn-plain-toolbar-large-disabled .x-btn-icon-el{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=50)";opacity:0.5}.x-panel-light{border-color:#d0d0d0;padding:0}.x-panel-light.x-masked{border-color:#e8e8e8}.x-panel-header-light{font-size:16px;border:1px solid #d0d0d0}.x-panel-header-light .x-tool-tool-el{color:#919191}.x-panel-header-light .x-tool-tool-el{background-color:#fff}.x-panel-header-light-horizontal{padding:11px 15px 12px}.x-panel-header-light-horizontal .x-panel-header-light-tab-bar{margin-top:-11px;margin-bottom:-12px}.x-panel-header-light-horizontal.x-header-noborder{padding:12px 16px 12px 16px}.x-panel-header-light-horizontal.x-header-noborder .x-panel-header-light-tab-bar{margin-top:-12px;margin-bottom:-12px}.x-panel-header-light-vertical{padding:15px 11px 15px 12px}.x-panel-header-light-vertical .x-panel-header-light-tab-bar{margin-right:-11px;margin-left:-12px}.x-panel-header-light-vertical.x-header-noborder{padding:16px 12px 16px 12px}.x-panel-header-light-vertical.x-header-noborder .x-panel-header-light-tab-bar{margin-right:-12px;margin-left:-12px}.x-panel-header-title-light{color:#606060;font-size:16px;font-weight:400;font-family:'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif;line-height:20px}.x-keyboard-mode .x-panel-header-title-light.x-title-focus{outline:1px solid #5fa2dd;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus,.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus,.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after,.x-edge .x-keyboard-mode .x-panel-header-title-light.x-title-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #5fa2dd;pointer-events:none}.x-panel-header-title-light > .x-title-text-light{text-transform:none;padding:0}.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-top{height:24px;padding-bottom:8px}.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-right{width:24px;padding-left:8px}.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-bottom{height:24px;padding-top:8px}.x-panel-header-title-light > .x-title-icon-wrap-light.x-title-icon-left{width:24px;padding-right:8px}.x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light{width:16px;height:16px;font-size:16px;color:#606060;background-position:center center}.x-ie8 .x-panel-header-title-light > .x-title-icon-wrap-light > .x-title-icon-light.x-title-glyph{color:#606060}.x-panel-body-light{background:#fff;border-color:#d0d0d0;color:#404040;font-size:13px;font-weight:300;font-family:'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif;border-width:1px;border-style:solid}.x-panel-header-light{background-image:none;background-color:#fff}.x-panel-header-light-vertical{background-image:none;background-color:#fff}.x-panel .x-panel-header-light-collapsed-border-top{border-bottom-width:1px !important}.x-panel .x-panel-header-light-collapsed-border-right{border-left-width:1px !important}.x-panel .x-panel-header-light-collapsed-border-bottom{border-top-width:1px !important}.x-panel .x-panel-header-light-collapsed-border-left{border-right-width:1px !important}.x-panel-header-light-horizontal .x-tool-after-title{margin:0 0 0 6px}.x-panel-header-light-horizontal .x-tool-before-title{margin:0 6px 0 0}.x-panel-header-light-vertical .x-tool-after-title{margin:6px 0 0 0}.x-panel-header-light-vertical .x-tool-before-title{margin:0 0 6px 0}.x-keyboard-mode .x-panel-header-light .x-tool-focus{outline:1px solid #5fa2dd;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus,.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus,.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-light .x-tool-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-light .x-tool-focus:after,.x-edge .x-keyboard-mode .x-panel-header-light .x-tool-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #5fa2dd;pointer-events:none}.x-panel-light-resizable .x-panel-handle{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-panel-light-outer-border-l{border-left-color:#d0d0d0 !important;border-left-width:1px !important}.x-panel-light-outer-border-b{border-bottom-color:#d0d0d0 !important;border-bottom-width:1px !important}.x-panel-light-outer-border-bl{border-bottom-color:#d0d0d0 !important;border-bottom-width:1px !important;border-left-color:#d0d0d0 !important;border-left-width:1px !important}.x-panel-light-outer-border-r{border-right-color:#d0d0d0 !important;border-right-width:1px !important}.x-panel-light-outer-border-rl{border-right-color:#d0d0d0 !important;border-right-width:1px !important;border-left-color:#d0d0d0 !important;border-left-width:1px !important}.x-panel-light-outer-border-rb{border-right-color:#d0d0d0 !important;border-right-width:1px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:1px !important}.x-panel-light-outer-border-rbl{border-right-color:#d0d0d0 !important;border-right-width:1px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:1px !important;border-left-color:#d0d0d0 !important;border-left-width:1px !important}.x-panel-light-outer-border-t{border-top-color:#d0d0d0 !important;border-top-width:1px !important}.x-panel-light-outer-border-tl{border-top-color:#d0d0d0 !important;border-top-width:1px !important;border-left-color:#d0d0d0 !important;border-left-width:1px !important}.x-panel-light-outer-border-tb{border-top-color:#d0d0d0 !important;border-top-width:1px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:1px !important}.x-panel-light-outer-border-tbl{border-top-color:#d0d0d0 !important;border-top-width:1px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:1px !important;border-left-color:#d0d0d0 !important;border-left-width:1px !important}.x-panel-light-outer-border-tr{border-top-color:#d0d0d0 !important;border-top-width:1px !important;border-right-color:#d0d0d0 !important;border-right-width:1px !important}.x-panel-light-outer-border-trl{border-top-color:#d0d0d0 !important;border-top-width:1px !important;border-right-color:#d0d0d0 !important;border-right-width:1px !important;border-left-color:#d0d0d0 !important;border-left-width:1px !important}.x-panel-light-outer-border-trb{border-top-color:#d0d0d0 !important;border-top-width:1px !important;border-right-color:#d0d0d0 !important;border-right-width:1px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:1px !important}.x-panel-light-outer-border-trbl{border-color:#d0d0d0 !important;border-width:1px !important}.x-panel-light-framed{border-color:#d0d0d0;padding:0}.x-panel-light-framed.x-masked{border-color:#e8e8e8}.x-panel-header-light-framed{font-size:16px;border:2px solid #d0d0d0}.x-panel-header-light-framed .x-tool-tool-el{color:#919191}.x-panel-header-light-framed .x-tool-tool-el{background-color:#fff}.x-panel-header-light-framed-horizontal{padding:10px 14px 10px 14px}.x-panel-header-light-framed-horizontal .x-panel-header-light-framed-tab-bar{margin-top:-10px;margin-bottom:-10px}.x-panel-header-light-framed-horizontal.x-header-noborder{padding:12px 16px 10px 16px}.x-panel-header-light-framed-horizontal.x-header-noborder .x-panel-header-light-framed-tab-bar{margin-top:-12px;margin-bottom:-10px}.x-panel-header-light-framed-vertical{padding:14px 10px 14px 10px}.x-panel-header-light-framed-vertical .x-panel-header-light-framed-tab-bar{margin-right:-10px;margin-left:-10px}.x-panel-header-light-framed-vertical.x-header-noborder{padding:16px 12px 16px 10px}.x-panel-header-light-framed-vertical.x-header-noborder .x-panel-header-light-framed-tab-bar{margin-right:-12px;margin-left:-10px}.x-panel-header-title-light-framed{color:#606060;font-size:16px;font-weight:400;font-family:'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif;line-height:20px}.x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus{outline:1px solid #5fa2dd;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus,.x-ie10p .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus,.x-edge .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after,.x-edge .x-keyboard-mode .x-panel-header-title-light-framed.x-title-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #5fa2dd;pointer-events:none}.x-panel-header-title-light-framed > .x-title-text-light-framed{text-transform:none;padding:0}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-top{height:24px;padding-bottom:8px}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-right{width:24px;padding-left:8px}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-bottom{height:24px;padding-top:8px}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed.x-title-icon-left{width:24px;padding-right:8px}.x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed{width:16px;height:16px;font-size:16px;color:#606060;background-position:center center}.x-ie8 .x-panel-header-title-light-framed > .x-title-icon-wrap-light-framed > .x-title-icon-light-framed.x-title-glyph{color:#606060}.x-panel-body-light-framed{background:#fff;border-color:#d0d0d0;color:#404040;font-size:13px;font-weight:300;font-family:'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif;border-width:1px;border-style:solid}.x-panel-light-framed{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:0 0 0 0;border-width:2px;border-style:solid;background-color:#fff}.x-panel-light-framed-mc{background-color:#fff}.x-nbr .x-panel-light-framed{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-light-framed-frameInfo{font-family:dh-2-2-2-2-2-2-2-2-0px-0px-0px-0px}.x-panel-light-framed-tl{background-position:0 -4px}.x-panel-light-framed-tr{background-position:right -6px}.x-panel-light-framed-bl{background-position:0 -8px}.x-panel-light-framed-br{background-position:right -10px}.x-panel-light-framed-ml{background-position:0 top}.x-panel-light-framed-mr{background-position:right top}.x-panel-light-framed-tc{background-position:0 0}.x-panel-light-framed-bc{background-position:0 -2px}.x-panel-light-framed-tr,.x-panel-light-framed-br,.x-panel-light-framed-mr{padding-right:2px}.x-panel-light-framed-tl,.x-panel-light-framed-bl,.x-panel-light-framed-ml{padding-left:2px}.x-panel-light-framed-tc{height:2px}.x-panel-light-framed-bc{height:2px}.x-panel-light-framed-tl,.x-panel-light-framed-bl,.x-panel-light-framed-tr,.x-panel-light-framed-br,.x-panel-light-framed-tc,.x-panel-light-framed-bc,.x-panel-light-framed-ml,.x-panel-light-framed-mr{background-image:url(images/panel/panel-light-framed-corners.gif)}.x-panel-light-framed-ml,.x-panel-light-framed-mr{background-image:url(images/panel/panel-light-framed-sides.gif);background-repeat:repeat-y}.x-panel-light-framed-mc{padding:0px 0px 0px 0px}.x-panel-header-light-framed-top{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:10px 14px 10px 14px;border-width:2px 2px 0 2px;border-style:solid;background-color:#fff}.x-panel-header-light-framed-top-mc{background-color:#fff}.x-nbr .x-panel-header-light-framed-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-top-frameInfo{font-family:dh-2-2-0-2-2-2-0-2-10-14-10-14}.x-panel-header-light-framed-top-tl{background-position:0 -4px}.x-panel-header-light-framed-top-tr{background-position:right -6px}.x-panel-header-light-framed-top-bl{background-position:0 -8px}.x-panel-header-light-framed-top-br{background-position:right -10px}.x-panel-header-light-framed-top-ml{background-position:0 top}.x-panel-header-light-framed-top-mr{background-position:right top}.x-panel-header-light-framed-top-tc{background-position:0 0}.x-panel-header-light-framed-top-bc{background-position:0 -2px}.x-panel-header-light-framed-top-tr,.x-panel-header-light-framed-top-br,.x-panel-header-light-framed-top-mr{padding-right:2px}.x-panel-header-light-framed-top-tl,.x-panel-header-light-framed-top-bl,.x-panel-header-light-framed-top-ml{padding-left:2px}.x-panel-header-light-framed-top-tc{height:2px}.x-panel-header-light-framed-top-bc{height:0}.x-panel-header-light-framed-top-tl,.x-panel-header-light-framed-top-bl,.x-panel-header-light-framed-top-tr,.x-panel-header-light-framed-top-br,.x-panel-header-light-framed-top-tc,.x-panel-header-light-framed-top-bc,.x-panel-header-light-framed-top-ml,.x-panel-header-light-framed-top-mr{background-image:url(images/panel-header/panel-header-light-framed-top-corners.gif)}.x-panel-header-light-framed-top-ml,.x-panel-header-light-framed-top-mr{background-image:url(images/panel-header/panel-header-light-framed-top-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-top-mc{padding:10px 14px 10px 14px}.x-panel-header-light-framed-right{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:14px 10px 14px 10px;border-width:2px 2px 2px 0;border-style:solid;background-color:#fff}.x-panel-header-light-framed-right-mc{background-color:#fff}.x-nbr .x-panel-header-light-framed-right{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-right-frameInfo{font-family:dh-2-2-2-0-2-2-2-0-14-10-14-10}.x-panel-header-light-framed-right-tl{background-position:0 -4px}.x-panel-header-light-framed-right-tr{background-position:right -6px}.x-panel-header-light-framed-right-bl{background-position:0 -8px}.x-panel-header-light-framed-right-br{background-position:right -10px}.x-panel-header-light-framed-right-ml{background-position:right 0}.x-panel-header-light-framed-right-mr{background-position:right 0}.x-panel-header-light-framed-right-tc{background-position:0 0}.x-panel-header-light-framed-right-bc{background-position:0 -2px}.x-panel-header-light-framed-right-tr,.x-panel-header-light-framed-right-br,.x-panel-header-light-framed-right-mr{padding-right:2px}.x-panel-header-light-framed-right-tl,.x-panel-header-light-framed-right-bl,.x-panel-header-light-framed-right-ml{padding-left:0}.x-panel-header-light-framed-right-tc{height:2px}.x-panel-header-light-framed-right-bc{height:2px}.x-panel-header-light-framed-right-tl,.x-panel-header-light-framed-right-bl,.x-panel-header-light-framed-right-tr,.x-panel-header-light-framed-right-br,.x-panel-header-light-framed-right-tc,.x-panel-header-light-framed-right-bc,.x-panel-header-light-framed-right-ml,.x-panel-header-light-framed-right-mr{background-image:url(images/panel-header/panel-header-light-framed-right-corners.gif)}.x-panel-header-light-framed-right-ml,.x-panel-header-light-framed-right-mr{background-image:url(images/panel-header/panel-header-light-framed-right-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-right-mc{padding:14px 10px 14px 10px}.x-panel-header-light-framed-bottom{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:10px 14px 10px 14px;border-width:0 2px 2px 2px;border-style:solid;background-color:#fff}.x-panel-header-light-framed-bottom-mc{background-color:#fff}.x-nbr .x-panel-header-light-framed-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-bottom-frameInfo{font-family:dh-0-2-2-2-0-2-2-2-10-14-10-14}.x-panel-header-light-framed-bottom-tl{background-position:0 -4px}.x-panel-header-light-framed-bottom-tr{background-position:right -6px}.x-panel-header-light-framed-bottom-bl{background-position:0 -8px}.x-panel-header-light-framed-bottom-br{background-position:right -10px}.x-panel-header-light-framed-bottom-ml{background-position:0 bottom}.x-panel-header-light-framed-bottom-mr{background-position:right bottom}.x-panel-header-light-framed-bottom-tc{background-position:0 0}.x-panel-header-light-framed-bottom-bc{background-position:0 -2px}.x-panel-header-light-framed-bottom-tr,.x-panel-header-light-framed-bottom-br,.x-panel-header-light-framed-bottom-mr{padding-right:2px}.x-panel-header-light-framed-bottom-tl,.x-panel-header-light-framed-bottom-bl,.x-panel-header-light-framed-bottom-ml{padding-left:2px}.x-panel-header-light-framed-bottom-tc{height:0}.x-panel-header-light-framed-bottom-bc{height:2px}.x-panel-header-light-framed-bottom-tl,.x-panel-header-light-framed-bottom-bl,.x-panel-header-light-framed-bottom-tr,.x-panel-header-light-framed-bottom-br,.x-panel-header-light-framed-bottom-tc,.x-panel-header-light-framed-bottom-bc,.x-panel-header-light-framed-bottom-ml,.x-panel-header-light-framed-bottom-mr{background-image:url(images/panel-header/panel-header-light-framed-bottom-corners.gif)}.x-panel-header-light-framed-bottom-ml,.x-panel-header-light-framed-bottom-mr{background-image:url(images/panel-header/panel-header-light-framed-bottom-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-bottom-mc{padding:10px 14px 10px 14px}.x-panel-header-light-framed-left{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:14px 10px 14px 10px;border-width:2px 0 2px 2px;border-style:solid;background-color:#fff}.x-panel-header-light-framed-left-mc{background-color:#fff}.x-nbr .x-panel-header-light-framed-left{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-left-frameInfo{font-family:dh-2-0-2-2-2-0-2-2-14-10-14-10}.x-panel-header-light-framed-left-tl{background-position:0 -4px}.x-panel-header-light-framed-left-tr{background-position:right -6px}.x-panel-header-light-framed-left-bl{background-position:0 -8px}.x-panel-header-light-framed-left-br{background-position:right -10px}.x-panel-header-light-framed-left-ml{background-position:left 0}.x-panel-header-light-framed-left-mr{background-position:left 0}.x-panel-header-light-framed-left-tc{background-position:0 0}.x-panel-header-light-framed-left-bc{background-position:0 -2px}.x-panel-header-light-framed-left-tr,.x-panel-header-light-framed-left-br,.x-panel-header-light-framed-left-mr{padding-right:0}.x-panel-header-light-framed-left-tl,.x-panel-header-light-framed-left-bl,.x-panel-header-light-framed-left-ml{padding-left:2px}.x-panel-header-light-framed-left-tc{height:2px}.x-panel-header-light-framed-left-bc{height:2px}.x-panel-header-light-framed-left-tl,.x-panel-header-light-framed-left-bl,.x-panel-header-light-framed-left-tr,.x-panel-header-light-framed-left-br,.x-panel-header-light-framed-left-tc,.x-panel-header-light-framed-left-bc,.x-panel-header-light-framed-left-ml,.x-panel-header-light-framed-left-mr{background-image:url(images/panel-header/panel-header-light-framed-left-corners.gif)}.x-panel-header-light-framed-left-ml,.x-panel-header-light-framed-left-mr{background-image:url(images/panel-header/panel-header-light-framed-left-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-left-mc{padding:14px 10px 14px 10px}.x-panel-header-light-framed-collapsed-top{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:10px 14px 10px 14px;border-width:2px;border-style:solid;background-color:#fff}.x-panel-header-light-framed-collapsed-top-mc{background-color:#fff}.x-nbr .x-panel-header-light-framed-collapsed-top{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-collapsed-top-frameInfo{font-family:dh-2-2-2-2-2-2-2-2-10-14-10-14}.x-panel-header-light-framed-collapsed-top-tl{background-position:0 -4px}.x-panel-header-light-framed-collapsed-top-tr{background-position:right -6px}.x-panel-header-light-framed-collapsed-top-bl{background-position:0 -8px}.x-panel-header-light-framed-collapsed-top-br{background-position:right -10px}.x-panel-header-light-framed-collapsed-top-ml{background-position:0 top}.x-panel-header-light-framed-collapsed-top-mr{background-position:right top}.x-panel-header-light-framed-collapsed-top-tc{background-position:0 0}.x-panel-header-light-framed-collapsed-top-bc{background-position:0 -2px}.x-panel-header-light-framed-collapsed-top-tr,.x-panel-header-light-framed-collapsed-top-br,.x-panel-header-light-framed-collapsed-top-mr{padding-right:2px}.x-panel-header-light-framed-collapsed-top-tl,.x-panel-header-light-framed-collapsed-top-bl,.x-panel-header-light-framed-collapsed-top-ml{padding-left:2px}.x-panel-header-light-framed-collapsed-top-tc{height:2px}.x-panel-header-light-framed-collapsed-top-bc{height:2px}.x-panel-header-light-framed-collapsed-top-tl,.x-panel-header-light-framed-collapsed-top-bl,.x-panel-header-light-framed-collapsed-top-tr,.x-panel-header-light-framed-collapsed-top-br,.x-panel-header-light-framed-collapsed-top-tc,.x-panel-header-light-framed-collapsed-top-bc,.x-panel-header-light-framed-collapsed-top-ml,.x-panel-header-light-framed-collapsed-top-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-top-corners.gif)}.x-panel-header-light-framed-collapsed-top-ml,.x-panel-header-light-framed-collapsed-top-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-top-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-collapsed-top-mc{padding:10px 14px 10px 14px}.x-panel-header-light-framed-collapsed-right{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:14px 10px 14px 10px;border-width:2px;border-style:solid;background-color:#fff}.x-panel-header-light-framed-collapsed-right-mc{background-color:#fff}.x-nbr .x-panel-header-light-framed-collapsed-right{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-collapsed-right-frameInfo{font-family:dh-2-2-2-2-2-2-2-2-14-10-14-10}.x-panel-header-light-framed-collapsed-right-tl{background-position:0 -4px}.x-panel-header-light-framed-collapsed-right-tr{background-position:right -6px}.x-panel-header-light-framed-collapsed-right-bl{background-position:0 -8px}.x-panel-header-light-framed-collapsed-right-br{background-position:right -10px}.x-panel-header-light-framed-collapsed-right-ml{background-position:right 0}.x-panel-header-light-framed-collapsed-right-mr{background-position:right 0}.x-panel-header-light-framed-collapsed-right-tc{background-position:0 0}.x-panel-header-light-framed-collapsed-right-bc{background-position:0 -2px}.x-panel-header-light-framed-collapsed-right-tr,.x-panel-header-light-framed-collapsed-right-br,.x-panel-header-light-framed-collapsed-right-mr{padding-right:2px}.x-panel-header-light-framed-collapsed-right-tl,.x-panel-header-light-framed-collapsed-right-bl,.x-panel-header-light-framed-collapsed-right-ml{padding-left:2px}.x-panel-header-light-framed-collapsed-right-tc{height:2px}.x-panel-header-light-framed-collapsed-right-bc{height:2px}.x-panel-header-light-framed-collapsed-right-tl,.x-panel-header-light-framed-collapsed-right-bl,.x-panel-header-light-framed-collapsed-right-tr,.x-panel-header-light-framed-collapsed-right-br,.x-panel-header-light-framed-collapsed-right-tc,.x-panel-header-light-framed-collapsed-right-bc,.x-panel-header-light-framed-collapsed-right-ml,.x-panel-header-light-framed-collapsed-right-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-right-corners.gif)}.x-panel-header-light-framed-collapsed-right-ml,.x-panel-header-light-framed-collapsed-right-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-right-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-collapsed-right-mc{padding:14px 10px 14px 10px}.x-panel-header-light-framed-collapsed-bottom{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:10px 14px 10px 14px;border-width:2px;border-style:solid;background-color:#fff}.x-panel-header-light-framed-collapsed-bottom-mc{background-color:#fff}.x-nbr .x-panel-header-light-framed-collapsed-bottom{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-collapsed-bottom-frameInfo{font-family:dh-2-2-2-2-2-2-2-2-10-14-10-14}.x-panel-header-light-framed-collapsed-bottom-tl{background-position:0 -4px}.x-panel-header-light-framed-collapsed-bottom-tr{background-position:right -6px}.x-panel-header-light-framed-collapsed-bottom-bl{background-position:0 -8px}.x-panel-header-light-framed-collapsed-bottom-br{background-position:right -10px}.x-panel-header-light-framed-collapsed-bottom-ml{background-position:0 bottom}.x-panel-header-light-framed-collapsed-bottom-mr{background-position:right bottom}.x-panel-header-light-framed-collapsed-bottom-tc{background-position:0 0}.x-panel-header-light-framed-collapsed-bottom-bc{background-position:0 -2px}.x-panel-header-light-framed-collapsed-bottom-tr,.x-panel-header-light-framed-collapsed-bottom-br,.x-panel-header-light-framed-collapsed-bottom-mr{padding-right:2px}.x-panel-header-light-framed-collapsed-bottom-tl,.x-panel-header-light-framed-collapsed-bottom-bl,.x-panel-header-light-framed-collapsed-bottom-ml{padding-left:2px}.x-panel-header-light-framed-collapsed-bottom-tc{height:2px}.x-panel-header-light-framed-collapsed-bottom-bc{height:2px}.x-panel-header-light-framed-collapsed-bottom-tl,.x-panel-header-light-framed-collapsed-bottom-bl,.x-panel-header-light-framed-collapsed-bottom-tr,.x-panel-header-light-framed-collapsed-bottom-br,.x-panel-header-light-framed-collapsed-bottom-tc,.x-panel-header-light-framed-collapsed-bottom-bc,.x-panel-header-light-framed-collapsed-bottom-ml,.x-panel-header-light-framed-collapsed-bottom-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-bottom-corners.gif)}.x-panel-header-light-framed-collapsed-bottom-ml,.x-panel-header-light-framed-collapsed-bottom-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-bottom-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-collapsed-bottom-mc{padding:10px 14px 10px 14px}.x-panel-header-light-framed-collapsed-left{-moz-border-radius-topleft:0;-webkit-border-top-left-radius:0;border-top-left-radius:0;-moz-border-radius-topright:0;-webkit-border-top-right-radius:0;border-top-right-radius:0;-moz-border-radius-bottomright:0;-webkit-border-bottom-right-radius:0;border-bottom-right-radius:0;-moz-border-radius-bottomleft:0;-webkit-border-bottom-left-radius:0;border-bottom-left-radius:0;padding:14px 10px 14px 10px;border-width:2px;border-style:solid;background-color:#fff}.x-panel-header-light-framed-collapsed-left-mc{background-color:#fff}.x-nbr .x-panel-header-light-framed-collapsed-left{padding:0 !important;border-width:0 !important;-webkit-border-radius:0px;-moz-border-radius:0px;-ms-border-radius:0px;-o-border-radius:0px;border-radius:0px;background-color:transparent !important;box-shadow:none !important}.x-panel-header-light-framed-collapsed-left-frameInfo{font-family:dh-2-2-2-2-2-2-2-2-14-10-14-10}.x-panel-header-light-framed-collapsed-left-tl{background-position:0 -4px}.x-panel-header-light-framed-collapsed-left-tr{background-position:right -6px}.x-panel-header-light-framed-collapsed-left-bl{background-position:0 -8px}.x-panel-header-light-framed-collapsed-left-br{background-position:right -10px}.x-panel-header-light-framed-collapsed-left-ml{background-position:left 0}.x-panel-header-light-framed-collapsed-left-mr{background-position:left 0}.x-panel-header-light-framed-collapsed-left-tc{background-position:0 0}.x-panel-header-light-framed-collapsed-left-bc{background-position:0 -2px}.x-panel-header-light-framed-collapsed-left-tr,.x-panel-header-light-framed-collapsed-left-br,.x-panel-header-light-framed-collapsed-left-mr{padding-right:2px}.x-panel-header-light-framed-collapsed-left-tl,.x-panel-header-light-framed-collapsed-left-bl,.x-panel-header-light-framed-collapsed-left-ml{padding-left:2px}.x-panel-header-light-framed-collapsed-left-tc{height:2px}.x-panel-header-light-framed-collapsed-left-bc{height:2px}.x-panel-header-light-framed-collapsed-left-tl,.x-panel-header-light-framed-collapsed-left-bl,.x-panel-header-light-framed-collapsed-left-tr,.x-panel-header-light-framed-collapsed-left-br,.x-panel-header-light-framed-collapsed-left-tc,.x-panel-header-light-framed-collapsed-left-bc,.x-panel-header-light-framed-collapsed-left-ml,.x-panel-header-light-framed-collapsed-left-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-left-corners.gif)}.x-panel-header-light-framed-collapsed-left-ml,.x-panel-header-light-framed-collapsed-left-mr{background-image:url(images/panel-header/panel-header-light-framed-collapsed-left-sides.gif);background-repeat:repeat-y}.x-panel-header-light-framed-collapsed-left-mc{padding:14px 10px 14px 10px}.x-panel .x-panel-header-light-framed-top{border-bottom-width:2px !important}.x-panel .x-panel-header-light-framed-right{border-left-width:2px !important}.x-panel .x-panel-header-light-framed-bottom{border-top-width:2px !important}.x-panel .x-panel-header-light-framed-left{border-right-width:2px !important}.x-nbr .x-panel-header-light-framed-collapsed-top{border-bottom-width:0 !important}.x-nbr .x-panel-header-light-framed-collapsed-right{border-left-width:0 !important}.x-nbr .x-panel-header-light-framed-collapsed-bottom{border-top-width:0 !important}.x-nbr .x-panel-header-light-framed-collapsed-left{border-right-width:0 !important}.x-panel-header-light-framed-horizontal .x-tool-after-title{margin:0 0 0 6px}.x-panel-header-light-framed-horizontal .x-tool-before-title{margin:0 6px 0 0}.x-panel-header-light-framed-vertical .x-tool-after-title{margin:6px 0 0 0}.x-panel-header-light-framed-vertical .x-tool-before-title{margin:0 0 6px 0}.x-keyboard-mode .x-panel-header-light-framed .x-tool-focus{outline:1px solid #5fa2dd;outline-offset:2px}.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus,.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus,.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus{outline:none}.x-ie .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after,.x-ie10p .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after,.x-edge .x-keyboard-mode .x-panel-header-light-framed .x-tool-focus:after{position:absolute;content:' ';top:-3px;right:-3px;bottom:-3px;left:-3px;border:1px solid #5fa2dd;pointer-events:none}.x-panel-light-framed-resizable .x-panel-handle{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";opacity:0}.x-panel-light-framed-outer-border-l{border-left-color:#d0d0d0 !important;border-left-width:2px !important}.x-panel-light-framed-outer-border-b{border-bottom-color:#d0d0d0 !important;border-bottom-width:2px !important}.x-panel-light-framed-outer-border-bl{border-bottom-color:#d0d0d0 !important;border-bottom-width:2px !important;border-left-color:#d0d0d0 !important;border-left-width:2px !important}.x-panel-light-framed-outer-border-r{border-right-color:#d0d0d0 !important;border-right-width:2px !important}.x-panel-light-framed-outer-border-rl{border-right-color:#d0d0d0 !important;border-right-width:2px !important;border-left-color:#d0d0d0 !important;border-left-width:2px !important}.x-panel-light-framed-outer-border-rb{border-right-color:#d0d0d0 !important;border-right-width:2px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:2px !important}.x-panel-light-framed-outer-border-rbl{border-right-color:#d0d0d0 !important;border-right-width:2px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:2px !important;border-left-color:#d0d0d0 !important;border-left-width:2px !important}.x-panel-light-framed-outer-border-t{border-top-color:#d0d0d0 !important;border-top-width:2px !important}.x-panel-light-framed-outer-border-tl{border-top-color:#d0d0d0 !important;border-top-width:2px !important;border-left-color:#d0d0d0 !important;border-left-width:2px !important}.x-panel-light-framed-outer-border-tb{border-top-color:#d0d0d0 !important;border-top-width:2px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:2px !important}.x-panel-light-framed-outer-border-tbl{border-top-color:#d0d0d0 !important;border-top-width:2px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:2px !important;border-left-color:#d0d0d0 !important;border-left-width:2px !important}.x-panel-light-framed-outer-border-tr{border-top-color:#d0d0d0 !important;border-top-width:2px !important;border-right-color:#d0d0d0 !important;border-right-width:2px !important}.x-panel-light-framed-outer-border-trl{border-top-color:#d0d0d0 !important;border-top-width:2px !important;border-right-color:#d0d0d0 !important;border-right-width:2px !important;border-left-color:#d0d0d0 !important;border-left-width:2px !important}.x-panel-light-framed-outer-border-trb{border-top-color:#d0d0d0 !important;border-top-width:2px !important;border-right-color:#d0d0d0 !important;border-right-width:2px !important;border-bottom-color:#d0d0d0 !important;border-bottom-width:2px !important}.x-panel-light-framed-outer-border-trbl{border-color:#d0d0d0 !important;border-width:2px !important}.x-form-file-wrap .x-form-trigger-wrap{border:0}.x-form-file-wrap .x-form-trigger-wrap .x-form-text{border:1px solid;border-color:#d0d0d0;height:32px}.x-form-file-wrap .x-form-trigger-wrap .x-form-text.x-form-invalid-field{border-color:#cf4c35}.x-html-editor-container{border:1px solid;border-color:#d0d0d0}.x-grid-header-ct{border:1px solid #d0d0d0}.x-column-header-trigger{background-color:#eaeff4;border-left:1px solid #d0d0d0}.x-column-header-last{border-right-width:0}.x-column-header-last .x-column-header-over .x-column-header-trigger{border-right:1px solid #d0d0d0}.x-resizable-handle{background-repeat:no-repeat}.x-resizable-handle-east-over,.x-resizable-handle-west-over{background-position:center}.x-resizable-handle-south-over,.x-resizable-handle-north-over{background-position:center}.x-resizable-handle-southeast-over{background-position:-2px -2px}.x-resizable-handle-northwest-over{background-position:2px 2px}.x-resizable-handle-northeast-over{background-position:-2px 2px}.x-resizable-handle-southwest-over{background-position:2px -2px}.x-resizable-pinned .x-resizable-handle-east,.x-resizable-pinned .x-resizable-handle-west{background-position:center}.x-resizable-pinned .x-resizable-handle-south,.x-resizable-pinned .x-resizable-handle-north{background-position:center}.x-resizable-pinned .x-resizable-handle-southeast{background-position:-2px -2px}.x-resizable-pinned .x-resizable-handle-northwest{background-position:2px 2px}.x-resizable-pinned .x-resizable-handle-northeast{background-position:-2px 2px}.x-resizable-pinned .x-resizable-handle-southwest{background-position:2px -2px}@font-face{font-family:'FontAwesome';src:url('font-awesome/fonts/fontawesome-webfont.eot?v=4.7.0');src:url('font-awesome/fonts/fontawesome-webfont.eot?#iefix&v=4.7.0') format('embedded-opentype'), url('font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0') format('woff2'), url('font-awesome/fonts/fontawesome-webfont.woff?v=4.7.0') format('woff'), url('font-awesome/fonts/fontawesome-webfont.ttf?v=4.7.0') format('truetype'), url('font-awesome/fonts/fontawesome-webfont.svg?v=4.7.0#fontawesomeregular') format('svg');font-weight:normal;font-style:normal}.fa{display:inline-block;font:normal normal normal 14px/1 FontAwesome;font-size:inherit;text-rendering:auto;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.fa-lg{font-size:1.33333em;line-height:0.75em;vertical-align:-15%}.fa-2x{font-size:2em}.fa-3x{font-size:3em}.fa-4x{font-size:4em}.fa-5x{font-size:5em}.fa-fw{width:1.28571em;text-align:center}.fa-ul{padding-left:0;margin-left:2.14286em;list-style-type:none}.fa-ul > li{position:relative}.fa-li{position:absolute;left:-2.14286em;width:2.14286em;top:0.14286em;text-align:center}.fa-li.fa-lg{left:-1.85714em}.fa-border{padding:0.2em 0.25em 0.15em;border:solid 0.08em #eee;border-radius:0.1em}.fa-pull-left{float:left}.fa-pull-right{float:right}.fa.fa-pull-left{margin-right:0.3em}.fa.fa-pull-right{margin-left:0.3em}.pull-right{float:right}.pull-left{float:left}.fa.pull-left{margin-right:0.3em}.fa.pull-right{margin-left:0.3em}.fa-spin{-webkit-animation:fa-spin 2s infinite linear;animation:fa-spin 2s infinite linear}.fa-pulse{-webkit-animation:fa-spin 1s infinite steps(8);animation:fa-spin 1s infinite steps(8)}@-webkit-keyframes fa-spin{0%{-webkit-transform:rotate(0deg);transform:rotate(0deg)}100%{-webkit-transform:rotate(359deg);transform:rotate(359deg)}}@keyframes fa-spin{0%{-webkit-transform:rotate(0deg);transform:rotate(0deg)}100%{-webkit-transform:rotate(359deg);transform:rotate(359deg)}}.fa-rotate-90{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=1)";-webkit-transform:rotate(90deg);-ms-transform:rotate(90deg);transform:rotate(90deg)}.fa-rotate-180{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=2)";-webkit-transform:rotate(180deg);-ms-transform:rotate(180deg);transform:rotate(180deg)}.fa-rotate-270{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=3)";-webkit-transform:rotate(270deg);-ms-transform:rotate(270deg);transform:rotate(270deg)}.fa-flip-horizontal{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=0, mirror=1)";-webkit-transform:scale(-1,1);-ms-transform:scale(-1,1);transform:scale(-1,1)}.fa-flip-vertical{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1)";-webkit-transform:scale(1,-1);-ms-transform:scale(1,-1);transform:scale(1,-1)}:root .fa-rotate-90,:root .fa-rotate-180,:root .fa-rotate-270,:root .fa-flip-horizontal,:root .fa-flip-vertical{filter:none}.fa-stack{position:relative;display:inline-block;width:2em;height:2em;line-height:2em;vertical-align:middle}.fa-stack-1x,.fa-stack-2x{position:absolute;left:0;width:100%;text-align:center}.fa-stack-1x{line-height:inherit}.fa-stack-2x{font-size:2em}.fa-inverse{color:#fff}.fa-glass:before{content:"\f000" !important}.fa-music:before{content:"\f001" !important}.fa-search:before{content:"\f002" !important}.fa-envelope-o:before{content:"\f003" !important}.fa-heart:before{content:"\f004" !important}.fa-star:before{content:"\f005" !important}.fa-star-o:before{content:"\f006" !important}.fa-user:before{content:"\f007" !important}.fa-film:before{content:"\f008" !important}.fa-th-large:before{content:"\f009" !important}.fa-th:before{content:"\f00a" !important}.fa-th-list:before{content:"\f00b" !important}.fa-check:before{content:"\f00c" !important}.fa-remove:before,.fa-close:before,.fa-times:before{content:"\f00d" !important}.fa-search-plus:before{content:"\f00e" !important}.fa-search-minus:before{content:"\f010" !important}.fa-power-off:before{content:"\f011" !important}.fa-signal:before{content:"\f012" !important}.fa-gear:before,.fa-cog:before{content:"\f013" !important}.fa-trash-o:before{content:"\f014" !important}.fa-home:before{content:"\f015" !important}.fa-file-o:before{content:"\f016" !important}.fa-clock-o:before{content:"\f017" !important}.fa-road:before{content:"\f018" !important}.fa-download:before{content:"\f019" !important}.fa-arrow-circle-o-down:before{content:"\f01a" !important}.fa-arrow-circle-o-up:before{content:"\f01b" !important}.fa-inbox:before{content:"\f01c" !important}.fa-play-circle-o:before{content:"\f01d" !important}.fa-rotate-right:before,.fa-repeat:before{content:"\f01e" !important}.fa-refresh:before{content:"\f021" !important}.fa-list-alt:before{content:"\f022" !important}.fa-lock:before{content:"\f023" !important}.fa-flag:before{content:"\f024" !important}.fa-headphones:before{content:"\f025" !important}.fa-volume-off:before{content:"\f026" !important}.fa-volume-down:before{content:"\f027" !important}.fa-volume-up:before{content:"\f028" !important}.fa-qrcode:before{content:"\f029" !important}.fa-barcode:before{content:"\f02a" !important}.fa-tag:before{content:"\f02b" !important}.fa-tags:before{content:"\f02c" !important}.fa-book:before{content:"\f02d" !important}.fa-bookmark:before{content:"\f02e" !important}.fa-print:before{content:"\f02f" !important}.fa-camera:before{content:"\f030" !important}.fa-font:before{content:"\f031" !important}.fa-bold:before{content:"\f032" !important}.fa-italic:before{content:"\f033" !important}.fa-text-height:before{content:"\f034" !important}.fa-text-width:before{content:"\f035" !important}.fa-align-left:before{content:"\f036" !important}.fa-align-center:before{content:"\f037" !important}.fa-align-right:before{content:"\f038" !important}.fa-align-justify:before{content:"\f039" !important}.fa-list:before{content:"\f03a" !important}.fa-dedent:before,.fa-outdent:before{content:"\f03b" !important}.fa-indent:before{content:"\f03c" !important}.fa-video-camera:before{content:"\f03d" !important}.fa-photo:before,.fa-image:before,.fa-picture-o:before{content:"\f03e" !important}.fa-pencil:before{content:"\f040" !important}.fa-map-marker:before{content:"\f041" !important}.fa-adjust:before{content:"\f042" !important}.fa-tint:before{content:"\f043" !important}.fa-edit:before,.fa-pencil-square-o:before{content:"\f044" !important}.fa-share-square-o:before{content:"\f045" !important}.fa-check-square-o:before{content:"\f046" !important}.fa-arrows:before{content:"\f047" !important}.fa-step-backward:before{content:"\f048" !important}.fa-fast-backward:before{content:"\f049" !important}.fa-backward:before{content:"\f04a" !important}.fa-play:before{content:"\f04b" !important}.fa-pause:before{content:"\f04c" !important}.fa-stop:before{content:"\f04d" !important}.fa-forward:before{content:"\f04e" !important}.fa-fast-forward:before{content:"\f050" !important}.fa-step-forward:before{content:"\f051" !important}.fa-eject:before{content:"\f052" !important}.fa-chevron-left:before{content:"\f053" !important}.fa-chevron-right:before{content:"\f054" !important}.fa-plus-circle:before{content:"\f055" !important}.fa-minus-circle:before{content:"\f056" !important}.fa-times-circle:before{content:"\f057" !important}.fa-check-circle:before{content:"\f058" !important}.fa-question-circle:before{content:"\f059" !important}.fa-info-circle:before{content:"\f05a" !important}.fa-crosshairs:before{content:"\f05b" !important}.fa-times-circle-o:before{content:"\f05c" !important}.fa-check-circle-o:before{content:"\f05d" !important}.fa-ban:before{content:"\f05e" !important}.fa-arrow-left:before{content:"\f060" !important}.fa-arrow-right:before{content:"\f061" !important}.fa-arrow-up:before{content:"\f062" !important}.fa-arrow-down:before{content:"\f063" !important}.fa-mail-forward:before,.fa-share:before{content:"\f064" !important}.fa-expand:before{content:"\f065" !important}.fa-compress:before{content:"\f066" !important}.fa-plus:before{content:"\f067" !important}.fa-minus:before{content:"\f068" !important}.fa-asterisk:before{content:"\f069" !important}.fa-exclamation-circle:before{content:"\f06a" !important}.fa-gift:before{content:"\f06b" !important}.fa-leaf:before{content:"\f06c" !important}.fa-fire:before{content:"\f06d" !important}.fa-eye:before{content:"\f06e" !important}.fa-eye-slash:before{content:"\f070" !important}.fa-warning:before,.fa-exclamation-triangle:before{content:"\f071" !important}.fa-plane:before{content:"\f072" !important}.fa-calendar:before{content:"\f073" !important}.fa-random:before{content:"\f074" !important}.fa-comment:before{content:"\f075" !important}.fa-magnet:before{content:"\f076" !important}.fa-chevron-up:before{content:"\f077" !important}.fa-chevron-down:before{content:"\f078" !important}.fa-retweet:before{content:"\f079" !important}.fa-shopping-cart:before{content:"\f07a" !important}.fa-folder:before{content:"\f07b" !important}.fa-folder-open:before{content:"\f07c" !important}.fa-arrows-v:before{content:"\f07d" !important}.fa-arrows-h:before{content:"\f07e" !important}.fa-bar-chart-o:before,.fa-bar-chart:before{content:"\f080" !important}.fa-twitter-square:before{content:"\f081" !important}.fa-facebook-square:before{content:"\f082" !important}.fa-camera-retro:before{content:"\f083" !important}.fa-key:before{content:"\f084" !important}.fa-gears:before,.fa-cogs:before{content:"\f085" !important}.fa-comments:before{content:"\f086" !important}.fa-thumbs-o-up:before{content:"\f087" !important}.fa-thumbs-o-down:before{content:"\f088" !important}.fa-star-half:before{content:"\f089" !important}.fa-heart-o:before{content:"\f08a" !important}.fa-sign-out:before{content:"\f08b" !important}.fa-linkedin-square:before{content:"\f08c" !important}.fa-thumb-tack:before{content:"\f08d" !important}.fa-external-link:before{content:"\f08e" !important}.fa-sign-in:before{content:"\f090" !important}.fa-trophy:before{content:"\f091" !important}.fa-github-square:before{content:"\f092" !important}.fa-upload:before{content:"\f093" !important}.fa-lemon-o:before{content:"\f094" !important}.fa-phone:before{content:"\f095" !important}.fa-square-o:before{content:"\f096" !important}.fa-bookmark-o:before{content:"\f097" !important}.fa-phone-square:before{content:"\f098" !important}.fa-twitter:before{content:"\f099" !important}.fa-facebook-f:before,.fa-facebook:before{content:"\f09a" !important}.fa-github:before{content:"\f09b" !important}.fa-unlock:before{content:"\f09c" !important}.fa-credit-card:before{content:"\f09d" !important}.fa-feed:before,.fa-rss:before{content:"\f09e" !important}.fa-hdd-o:before{content:"\f0a0" !important}.fa-bullhorn:before{content:"\f0a1" !important}.fa-bell:before{content:"\f0f3" !important}.fa-certificate:before{content:"\f0a3" !important}.fa-hand-o-right:before{content:"\f0a4" !important}.fa-hand-o-left:before{content:"\f0a5" !important}.fa-hand-o-up:before{content:"\f0a6" !important}.fa-hand-o-down:before{content:"\f0a7" !important}.fa-arrow-circle-left:before{content:"\f0a8" !important}.fa-arrow-circle-right:before{content:"\f0a9" !important}.fa-arrow-circle-up:before{content:"\f0aa" !important}.fa-arrow-circle-down:before{content:"\f0ab" !important}.fa-globe:before{content:"\f0ac" !important}.fa-wrench:before{content:"\f0ad" !important}.fa-tasks:before{content:"\f0ae" !important}.fa-filter:before{content:"\f0b0" !important}.fa-briefcase:before{content:"\f0b1" !important}.fa-arrows-alt:before{content:"\f0b2" !important}.fa-group:before,.fa-users:before{content:"\f0c0" !important}.fa-chain:before,.fa-link:before{content:"\f0c1" !important}.fa-cloud:before{content:"\f0c2" !important}.fa-flask:before{content:"\f0c3" !important}.fa-cut:before,.fa-scissors:before{content:"\f0c4" !important}.fa-copy:before,.fa-files-o:before{content:"\f0c5" !important}.fa-paperclip:before{content:"\f0c6" !important}.fa-save:before,.fa-floppy-o:before{content:"\f0c7" !important}.fa-square:before{content:"\f0c8" !important}.fa-navicon:before,.fa-reorder:before,.fa-bars:before{content:"\f0c9" !important}.fa-list-ul:before{content:"\f0ca" !important}.fa-list-ol:before{content:"\f0cb" !important}.fa-strikethrough:before{content:"\f0cc" !important}.fa-underline:before{content:"\f0cd" !important}.fa-table:before{content:"\f0ce" !important}.fa-magic:before{content:"\f0d0" !important}.fa-truck:before{content:"\f0d1" !important}.fa-pinterest:before{content:"\f0d2" !important}.fa-pinterest-square:before{content:"\f0d3" !important}.fa-google-plus-square:before{content:"\f0d4" !important}.fa-google-plus:before{content:"\f0d5" !important}.fa-money:before{content:"\f0d6" !important}.fa-caret-down:before{content:"\f0d7" !important}.fa-caret-up:before{content:"\f0d8" !important}.fa-caret-left:before{content:"\f0d9" !important}.fa-caret-right:before{content:"\f0da" !important}.fa-columns:before{content:"\f0db" !important}.fa-unsorted:before,.fa-sort:before{content:"\f0dc" !important}.fa-sort-down:before,.fa-sort-desc:before{content:"\f0dd" !important}.fa-sort-up:before,.fa-sort-asc:before{content:"\f0de" !important}.fa-envelope:before{content:"\f0e0" !important}.fa-linkedin:before{content:"\f0e1" !important}.fa-rotate-left:before,.fa-undo:before{content:"\f0e2" !important}.fa-legal:before,.fa-gavel:before{content:"\f0e3" !important}.fa-dashboard:before,.fa-tachometer:before{content:"\f0e4" !important}.fa-comment-o:before{content:"\f0e5" !important}.fa-comments-o:before{content:"\f0e6" !important}.fa-flash:before,.fa-bolt:before{content:"\f0e7" !important}.fa-sitemap:before{content:"\f0e8" !important}.fa-umbrella:before{content:"\f0e9" !important}.fa-paste:before,.fa-clipboard:before{content:"\f0ea" !important}.fa-lightbulb-o:before{content:"\f0eb" !important}.fa-exchange:before{content:"\f0ec" !important}.fa-cloud-download:before{content:"\f0ed" !important}.fa-cloud-upload:before{content:"\f0ee" !important}.fa-user-md:before{content:"\f0f0" !important}.fa-stethoscope:before{content:"\f0f1" !important}.fa-suitcase:before{content:"\f0f2" !important}.fa-bell-o:before{content:"\f0a2" !important}.fa-coffee:before{content:"\f0f4" !important}.fa-cutlery:before{content:"\f0f5" !important}.fa-file-text-o:before{content:"\f0f6" !important}.fa-building-o:before{content:"\f0f7" !important}.fa-hospital-o:before{content:"\f0f8" !important}.fa-ambulance:before{content:"\f0f9" !important}.fa-medkit:before{content:"\f0fa" !important}.fa-fighter-jet:before{content:"\f0fb" !important}.fa-beer:before{content:"\f0fc" !important}.fa-h-square:before{content:"\f0fd" !important}.fa-plus-square:before{content:"\f0fe" !important}.fa-angle-double-left:before{content:"\f100" !important}.fa-angle-double-right:before{content:"\f101" !important}.fa-angle-double-up:before{content:"\f102" !important}.fa-angle-double-down:before{content:"\f103" !important}.fa-angle-left:before{content:"\f104" !important}.fa-angle-right:before{content:"\f105" !important}.fa-angle-up:before{content:"\f106" !important}.fa-angle-down:before{content:"\f107" !important}.fa-desktop:before{content:"\f108" !important}.fa-laptop:before{content:"\f109" !important}.fa-tablet:before{content:"\f10a" !important}.fa-mobile-phone:before,.fa-mobile:before{content:"\f10b" !important}.fa-circle-o:before{content:"\f10c" !important}.fa-quote-left:before{content:"\f10d" !important}.fa-quote-right:before{content:"\f10e" !important}.fa-spinner:before{content:"\f110" !important}.fa-circle:before{content:"\f111" !important}.fa-mail-reply:before,.fa-reply:before{content:"\f112" !important}.fa-github-alt:before{content:"\f113" !important}.fa-folder-o:before{content:"\f114" !important}.fa-folder-open-o:before{content:"\f115" !important}.fa-smile-o:before{content:"\f118" !important}.fa-frown-o:before{content:"\f119" !important}.fa-meh-o:before{content:"\f11a" !important}.fa-gamepad:before{content:"\f11b" !important}.fa-keyboard-o:before{content:"\f11c" !important}.fa-flag-o:before{content:"\f11d" !important}.fa-flag-checkered:before{content:"\f11e" !important}.fa-terminal:before{content:"\f120" !important}.fa-code:before{content:"\f121" !important}.fa-mail-reply-all:before,.fa-reply-all:before{content:"\f122" !important}.fa-star-half-empty:before,.fa-star-half-full:before,.fa-star-half-o:before{content:"\f123" !important}.fa-location-arrow:before{content:"\f124" !important}.fa-crop:before{content:"\f125" !important}.fa-code-fork:before{content:"\f126" !important}.fa-unlink:before,.fa-chain-broken:before{content:"\f127" !important}.fa-question:before{content:"\f128" !important}.fa-info:before{content:"\f129" !important}.fa-exclamation:before{content:"\f12a" !important}.fa-superscript:before{content:"\f12b" !important}.fa-subscript:before{content:"\f12c" !important}.fa-eraser:before{content:"\f12d" !important}.fa-puzzle-piece:before{content:"\f12e" !important}.fa-microphone:before{content:"\f130" !important}.fa-microphone-slash:before{content:"\f131" !important}.fa-shield:before{content:"\f132" !important}.fa-calendar-o:before{content:"\f133" !important}.fa-fire-extinguisher:before{content:"\f134" !important}.fa-rocket:before{content:"\f135" !important}.fa-maxcdn:before{content:"\f136" !important}.fa-chevron-circle-left:before{content:"\f137" !important}.fa-chevron-circle-right:before{content:"\f138" !important}.fa-chevron-circle-up:before{content:"\f139" !important}.fa-chevron-circle-down:before{content:"\f13a" !important}.fa-html5:before{content:"\f13b" !important}.fa-css3:before{content:"\f13c" !important}.fa-anchor:before{content:"\f13d" !important}.fa-unlock-alt:before{content:"\f13e" !important}.fa-bullseye:before{content:"\f140" !important}.fa-ellipsis-h:before{content:"\f141" !important}.fa-ellipsis-v:before{content:"\f142" !important}.fa-rss-square:before{content:"\f143" !important}.fa-play-circle:before{content:"\f144" !important}.fa-ticket:before{content:"\f145" !important}.fa-minus-square:before{content:"\f146" !important}.fa-minus-square-o:before{content:"\f147" !important}.fa-level-up:before{content:"\f148" !important}.fa-level-down:before{content:"\f149" !important}.fa-check-square:before{content:"\f14a" !important}.fa-pencil-square:before{content:"\f14b" !important}.fa-external-link-square:before{content:"\f14c" !important}.fa-share-square:before{content:"\f14d" !important}.fa-compass:before{content:"\f14e" !important}.fa-toggle-down:before,.fa-caret-square-o-down:before{content:"\f150" !important}.fa-toggle-up:before,.fa-caret-square-o-up:before{content:"\f151" !important}.fa-toggle-right:before,.fa-caret-square-o-right:before{content:"\f152" !important}.fa-euro:before,.fa-eur:before{content:"\f153" !important}.fa-gbp:before{content:"\f154" !important}.fa-dollar:before,.fa-usd:before{content:"\f155" !important}.fa-rupee:before,.fa-inr:before{content:"\f156" !important}.fa-cny:before,.fa-rmb:before,.fa-yen:before,.fa-jpy:before{content:"\f157" !important}.fa-ruble:before,.fa-rouble:before,.fa-rub:before{content:"\f158" !important}.fa-won:before,.fa-krw:before{content:"\f159" !important}.fa-bitcoin:before,.fa-btc:before{content:"\f15a" !important}.fa-file:before{content:"\f15b" !important}.fa-file-text:before{content:"\f15c" !important}.fa-sort-alpha-asc:before{content:"\f15d" !important}.fa-sort-alpha-desc:before{content:"\f15e" !important}.fa-sort-amount-asc:before{content:"\f160" !important}.fa-sort-amount-desc:before{content:"\f161" !important}.fa-sort-numeric-asc:before{content:"\f162" !important}.fa-sort-numeric-desc:before{content:"\f163" !important}.fa-thumbs-up:before{content:"\f164" !important}.fa-thumbs-down:before{content:"\f165" !important}.fa-youtube-square:before{content:"\f166" !important}.fa-youtube:before{content:"\f167" !important}.fa-xing:before{content:"\f168" !important}.fa-xing-square:before{content:"\f169" !important}.fa-youtube-play:before{content:"\f16a" !important}.fa-dropbox:before{content:"\f16b" !important}.fa-stack-overflow:before{content:"\f16c" !important}.fa-instagram:before{content:"\f16d" !important}.fa-flickr:before{content:"\f16e" !important}.fa-adn:before{content:"\f170" !important}.fa-bitbucket:before{content:"\f171" !important}.fa-bitbucket-square:before{content:"\f172" !important}.fa-tumblr:before{content:"\f173" !important}.fa-tumblr-square:before{content:"\f174" !important}.fa-long-arrow-down:before{content:"\f175" !important}.fa-long-arrow-up:before{content:"\f176" !important}.fa-long-arrow-left:before{content:"\f177" !important}.fa-long-arrow-right:before{content:"\f178" !important}.fa-apple:before{content:"\f179" !important}.fa-windows:before{content:"\f17a" !important}.fa-android:before{content:"\f17b" !important}.fa-linux:before{content:"\f17c" !important}.fa-dribbble:before{content:"\f17d" !important}.fa-skype:before{content:"\f17e" !important}.fa-foursquare:before{content:"\f180" !important}.fa-trello:before{content:"\f181" !important}.fa-female:before{content:"\f182" !important}.fa-male:before{content:"\f183" !important}.fa-gittip:before,.fa-gratipay:before{content:"\f184" !important}.fa-sun-o:before{content:"\f185" !important}.fa-moon-o:before{content:"\f186" !important}.fa-archive:before{content:"\f187" !important}.fa-bug:before{content:"\f188" !important}.fa-vk:before{content:"\f189" !important}.fa-weibo:before{content:"\f18a" !important}.fa-renren:before{content:"\f18b" !important}.fa-pagelines:before{content:"\f18c" !important}.fa-stack-exchange:before{content:"\f18d" !important}.fa-arrow-circle-o-right:before{content:"\f18e" !important}.fa-arrow-circle-o-left:before{content:"\f190" !important}.fa-toggle-left:before,.fa-caret-square-o-left:before{content:"\f191" !important}.fa-dot-circle-o:before{content:"\f192" !important}.fa-wheelchair:before{content:"\f193" !important}.fa-vimeo-square:before{content:"\f194" !important}.fa-turkish-lira:before,.fa-try:before{content:"\f195" !important}.fa-plus-square-o:before{content:"\f196" !important}.fa-space-shuttle:before{content:"\f197" !important}.fa-slack:before{content:"\f198" !important}.fa-envelope-square:before{content:"\f199" !important}.fa-wordpress:before{content:"\f19a" !important}.fa-openid:before{content:"\f19b" !important}.fa-institution:before,.fa-bank:before,.fa-university:before{content:"\f19c" !important}.fa-mortar-board:before,.fa-graduation-cap:before{content:"\f19d" !important}.fa-yahoo:before{content:"\f19e" !important}.fa-google:before{content:"\f1a0" !important}.fa-reddit:before{content:"\f1a1" !important}.fa-reddit-square:before{content:"\f1a2" !important}.fa-stumbleupon-circle:before{content:"\f1a3" !important}.fa-stumbleupon:before{content:"\f1a4" !important}.fa-delicious:before{content:"\f1a5" !important}.fa-digg:before{content:"\f1a6" !important}.fa-pied-piper-pp:before{content:"\f1a7" !important}.fa-pied-piper-alt:before{content:"\f1a8" !important}.fa-drupal:before{content:"\f1a9" !important}.fa-joomla:before{content:"\f1aa" !important}.fa-language:before{content:"\f1ab" !important}.fa-fax:before{content:"\f1ac" !important}.fa-building:before{content:"\f1ad" !important}.fa-child:before{content:"\f1ae" !important}.fa-paw:before{content:"\f1b0" !important}.fa-spoon:before{content:"\f1b1" !important}.fa-cube:before{content:"\f1b2" !important}.fa-cubes:before{content:"\f1b3" !important}.fa-behance:before{content:"\f1b4" !important}.fa-behance-square:before{content:"\f1b5" !important}.fa-steam:before{content:"\f1b6" !important}.fa-steam-square:before{content:"\f1b7" !important}.fa-recycle:before{content:"\f1b8" !important}.fa-automobile:before,.fa-car:before{content:"\f1b9" !important}.fa-cab:before,.fa-taxi:before{content:"\f1ba" !important}.fa-tree:before{content:"\f1bb" !important}.fa-spotify:before{content:"\f1bc" !important}.fa-deviantart:before{content:"\f1bd" !important}.fa-soundcloud:before{content:"\f1be" !important}.fa-database:before{content:"\f1c0" !important}.fa-file-pdf-o:before{content:"\f1c1" !important}.fa-file-word-o:before{content:"\f1c2" !important}.fa-file-excel-o:before{content:"\f1c3" !important}.fa-file-powerpoint-o:before{content:"\f1c4" !important}.fa-file-photo-o:before,.fa-file-picture-o:before,.fa-file-image-o:before{content:"\f1c5" !important}.fa-file-zip-o:before,.fa-file-archive-o:before{content:"\f1c6" !important}.fa-file-sound-o:before,.fa-file-audio-o:before{content:"\f1c7" !important}.fa-file-movie-o:before,.fa-file-video-o:before{content:"\f1c8" !important}.fa-file-code-o:before{content:"\f1c9" !important}.fa-vine:before{content:"\f1ca" !important}.fa-codepen:before{content:"\f1cb" !important}.fa-jsfiddle:before{content:"\f1cc" !important}.fa-life-bouy:before,.fa-life-buoy:before,.fa-life-saver:before,.fa-support:before,.fa-life-ring:before{content:"\f1cd" !important}.fa-circle-o-notch:before{content:"\f1ce" !important}.fa-ra:before,.fa-resistance:before,.fa-rebel:before{content:"\f1d0" !important}.fa-ge:before,.fa-empire:before{content:"\f1d1" !important}.fa-git-square:before{content:"\f1d2" !important}.fa-git:before{content:"\f1d3" !important}.fa-y-combinator-square:before,.fa-yc-square:before,.fa-hacker-news:before{content:"\f1d4" !important}.fa-tencent-weibo:before{content:"\f1d5" !important}.fa-qq:before{content:"\f1d6" !important}.fa-wechat:before,.fa-weixin:before{content:"\f1d7" !important}.fa-send:before,.fa-paper-plane:before{content:"\f1d8" !important}.fa-send-o:before,.fa-paper-plane-o:before{content:"\f1d9" !important}.fa-history:before{content:"\f1da" !important}.fa-circle-thin:before{content:"\f1db" !important}.fa-header:before{content:"\f1dc" !important}.fa-paragraph:before{content:"\f1dd" !important}.fa-sliders:before{content:"\f1de" !important}.fa-share-alt:before{content:"\f1e0" !important}.fa-share-alt-square:before{content:"\f1e1" !important}.fa-bomb:before{content:"\f1e2" !important}.fa-soccer-ball-o:before,.fa-futbol-o:before{content:"\f1e3" !important}.fa-tty:before{content:"\f1e4" !important}.fa-binoculars:before{content:"\f1e5" !important}.fa-plug:before{content:"\f1e6" !important}.fa-slideshare:before{content:"\f1e7" !important}.fa-twitch:before{content:"\f1e8" !important}.fa-yelp:before{content:"\f1e9" !important}.fa-newspaper-o:before{content:"\f1ea" !important}.fa-wifi:before{content:"\f1eb" !important}.fa-calculator:before{content:"\f1ec" !important}.fa-paypal:before{content:"\f1ed" !important}.fa-google-wallet:before{content:"\f1ee" !important}.fa-cc-visa:before{content:"\f1f0" !important}.fa-cc-mastercard:before{content:"\f1f1" !important}.fa-cc-discover:before{content:"\f1f2" !important}.fa-cc-amex:before{content:"\f1f3" !important}.fa-cc-paypal:before{content:"\f1f4" !important}.fa-cc-stripe:before{content:"\f1f5" !important}.fa-bell-slash:before{content:"\f1f6" !important}.fa-bell-slash-o:before{content:"\f1f7" !important}.fa-trash:before{content:"\f1f8" !important}.fa-copyright:before{content:"\f1f9" !important}.fa-at:before{content:"\f1fa" !important}.fa-eyedropper:before{content:"\f1fb" !important}.fa-paint-brush:before{content:"\f1fc" !important}.fa-birthday-cake:before{content:"\f1fd" !important}.fa-area-chart:before{content:"\f1fe" !important}.fa-pie-chart:before{content:"\f200" !important}.fa-line-chart:before{content:"\f201" !important}.fa-lastfm:before{content:"\f202" !important}.fa-lastfm-square:before{content:"\f203" !important}.fa-toggle-off:before{content:"\f204" !important}.fa-toggle-on:before{content:"\f205" !important}.fa-bicycle:before{content:"\f206" !important}.fa-bus:before{content:"\f207" !important}.fa-ioxhost:before{content:"\f208" !important}.fa-angellist:before{content:"\f209" !important}.fa-cc:before{content:"\f20a" !important}.fa-shekel:before,.fa-sheqel:before,.fa-ils:before{content:"\f20b" !important}.fa-meanpath:before{content:"\f20c" !important}.fa-buysellads:before{content:"\f20d" !important}.fa-connectdevelop:before{content:"\f20e" !important}.fa-dashcube:before{content:"\f210" !important}.fa-forumbee:before{content:"\f211" !important}.fa-leanpub:before{content:"\f212" !important}.fa-sellsy:before{content:"\f213" !important}.fa-shirtsinbulk:before{content:"\f214" !important}.fa-simplybuilt:before{content:"\f215" !important}.fa-skyatlas:before{content:"\f216" !important}.fa-cart-plus:before{content:"\f217" !important}.fa-cart-arrow-down:before{content:"\f218" !important}.fa-diamond:before{content:"\f219" !important}.fa-ship:before{content:"\f21a" !important}.fa-user-secret:before{content:"\f21b" !important}.fa-motorcycle:before{content:"\f21c" !important}.fa-street-view:before{content:"\f21d" !important}.fa-heartbeat:before{content:"\f21e" !important}.fa-venus:before{content:"\f221" !important}.fa-mars:before{content:"\f222" !important}.fa-mercury:before{content:"\f223" !important}.fa-intersex:before,.fa-transgender:before{content:"\f224" !important}.fa-transgender-alt:before{content:"\f225" !important}.fa-venus-double:before{content:"\f226" !important}.fa-mars-double:before{content:"\f227" !important}.fa-venus-mars:before{content:"\f228" !important}.fa-mars-stroke:before{content:"\f229" !important}.fa-mars-stroke-v:before{content:"\f22a" !important}.fa-mars-stroke-h:before{content:"\f22b" !important}.fa-neuter:before{content:"\f22c" !important}.fa-genderless:before{content:"\f22d" !important}.fa-facebook-official:before{content:"\f230" !important}.fa-pinterest-p:before{content:"\f231" !important}.fa-whatsapp:before{content:"\f232" !important}.fa-server:before{content:"\f233" !important}.fa-user-plus:before{content:"\f234" !important}.fa-user-times:before{content:"\f235" !important}.fa-hotel:before,.fa-bed:before{content:"\f236" !important}.fa-viacoin:before{content:"\f237" !important}.fa-train:before{content:"\f238" !important}.fa-subway:before{content:"\f239" !important}.fa-medium:before{content:"\f23a" !important}.fa-yc:before,.fa-y-combinator:before{content:"\f23b" !important}.fa-optin-monster:before{content:"\f23c" !important}.fa-opencart:before{content:"\f23d" !important}.fa-expeditedssl:before{content:"\f23e" !important}.fa-battery-4:before,.fa-battery:before,.fa-battery-full:before{content:"\f240" !important}.fa-battery-3:before,.fa-battery-three-quarters:before{content:"\f241" !important}.fa-battery-2:before,.fa-battery-half:before{content:"\f242" !important}.fa-battery-1:before,.fa-battery-quarter:before{content:"\f243" !important}.fa-battery-0:before,.fa-battery-empty:before{content:"\f244" !important}.fa-mouse-pointer:before{content:"\f245" !important}.fa-i-cursor:before{content:"\f246" !important}.fa-object-group:before{content:"\f247" !important}.fa-object-ungroup:before{content:"\f248" !important}.fa-sticky-note:before{content:"\f249" !important}.fa-sticky-note-o:before{content:"\f24a" !important}.fa-cc-jcb:before{content:"\f24b" !important}.fa-cc-diners-club:before{content:"\f24c" !important}.fa-clone:before{content:"\f24d" !important}.fa-balance-scale:before{content:"\f24e" !important}.fa-hourglass-o:before{content:"\f250" !important}.fa-hourglass-1:before,.fa-hourglass-start:before{content:"\f251" !important}.fa-hourglass-2:before,.fa-hourglass-half:before{content:"\f252" !important}.fa-hourglass-3:before,.fa-hourglass-end:before{content:"\f253" !important}.fa-hourglass:before{content:"\f254" !important}.fa-hand-grab-o:before,.fa-hand-rock-o:before{content:"\f255" !important}.fa-hand-stop-o:before,.fa-hand-paper-o:before{content:"\f256" !important}.fa-hand-scissors-o:before{content:"\f257" !important}.fa-hand-lizard-o:before{content:"\f258" !important}.fa-hand-spock-o:before{content:"\f259" !important}.fa-hand-pointer-o:before{content:"\f25a" !important}.fa-hand-peace-o:before{content:"\f25b" !important}.fa-trademark:before{content:"\f25c" !important}.fa-registered:before{content:"\f25d" !important}.fa-creative-commons:before{content:"\f25e" !important}.fa-gg:before{content:"\f260" !important}.fa-gg-circle:before{content:"\f261" !important}.fa-tripadvisor:before{content:"\f262" !important}.fa-odnoklassniki:before{content:"\f263" !important}.fa-odnoklassniki-square:before{content:"\f264" !important}.fa-get-pocket:before{content:"\f265" !important}.fa-wikipedia-w:before{content:"\f266" !important}.fa-safari:before{content:"\f267" !important}.fa-chrome:before{content:"\f268" !important}.fa-firefox:before{content:"\f269" !important}.fa-opera:before{content:"\f26a" !important}.fa-internet-explorer:before{content:"\f26b" !important}.fa-tv:before,.fa-television:before{content:"\f26c" !important}.fa-contao:before{content:"\f26d" !important}.fa-500px:before{content:"\f26e" !important}.fa-amazon:before{content:"\f270" !important}.fa-calendar-plus-o:before{content:"\f271" !important}.fa-calendar-minus-o:before{content:"\f272" !important}.fa-calendar-times-o:before{content:"\f273" !important}.fa-calendar-check-o:before{content:"\f274" !important}.fa-industry:before{content:"\f275" !important}.fa-map-pin:before{content:"\f276" !important}.fa-map-signs:before{content:"\f277" !important}.fa-map-o:before{content:"\f278" !important}.fa-map:before{content:"\f279" !important}.fa-commenting:before{content:"\f27a" !important}.fa-commenting-o:before{content:"\f27b" !important}.fa-houzz:before{content:"\f27c" !important}.fa-vimeo:before{content:"\f27d" !important}.fa-black-tie:before{content:"\f27e" !important}.fa-fonticons:before{content:"\f280" !important}.fa-reddit-alien:before{content:"\f281" !important}.fa-edge:before{content:"\f282" !important}.fa-credit-card-alt:before{content:"\f283" !important}.fa-codiepie:before{content:"\f284" !important}.fa-modx:before{content:"\f285" !important}.fa-fort-awesome:before{content:"\f286" !important}.fa-usb:before{content:"\f287" !important}.fa-product-hunt:before{content:"\f288" !important}.fa-mixcloud:before{content:"\f289" !important}.fa-scribd:before{content:"\f28a" !important}.fa-pause-circle:before{content:"\f28b" !important}.fa-pause-circle-o:before{content:"\f28c" !important}.fa-stop-circle:before{content:"\f28d" !important}.fa-stop-circle-o:before{content:"\f28e" !important}.fa-shopping-bag:before{content:"\f290" !important}.fa-shopping-basket:before{content:"\f291" !important}.fa-hashtag:before{content:"\f292" !important}.fa-bluetooth:before{content:"\f293" !important}.fa-bluetooth-b:before{content:"\f294" !important}.fa-percent:before{content:"\f295" !important}.fa-gitlab:before{content:"\f296" !important}.fa-wpbeginner:before{content:"\f297" !important}.fa-wpforms:before{content:"\f298" !important}.fa-envira:before{content:"\f299" !important}.fa-universal-access:before{content:"\f29a" !important}.fa-wheelchair-alt:before{content:"\f29b" !important}.fa-question-circle-o:before{content:"\f29c" !important}.fa-blind:before{content:"\f29d" !important}.fa-audio-description:before{content:"\f29e" !important}.fa-volume-control-phone:before{content:"\f2a0" !important}.fa-braille:before{content:"\f2a1" !important}.fa-assistive-listening-systems:before{content:"\f2a2" !important}.fa-asl-interpreting:before,.fa-american-sign-language-interpreting:before{content:"\f2a3" !important}.fa-deafness:before,.fa-hard-of-hearing:before,.fa-deaf:before{content:"\f2a4" !important}.fa-glide:before{content:"\f2a5" !important}.fa-glide-g:before{content:"\f2a6" !important}.fa-signing:before,.fa-sign-language:before{content:"\f2a7" !important}.fa-low-vision:before{content:"\f2a8" !important}.fa-viadeo:before{content:"\f2a9" !important}.fa-viadeo-square:before{content:"\f2aa" !important}.fa-snapchat:before{content:"\f2ab" !important}.fa-snapchat-ghost:before{content:"\f2ac" !important}.fa-snapchat-square:before{content:"\f2ad" !important}.fa-pied-piper:before{content:"\f2ae" !important}.fa-first-order:before{content:"\f2b0" !important}.fa-yoast:before{content:"\f2b1" !important}.fa-themeisle:before{content:"\f2b2" !important}.fa-google-plus-circle:before,.fa-google-plus-official:before{content:"\f2b3" !important}.fa-fa:before,.fa-font-awesome:before{content:"\f2b4" !important}.fa-handshake-o:before{content:"\f2b5" !important}.fa-envelope-open:before{content:"\f2b6" !important}.fa-envelope-open-o:before{content:"\f2b7" !important}.fa-linode:before{content:"\f2b8" !important}.fa-address-book:before{content:"\f2b9" !important}.fa-address-book-o:before{content:"\f2ba" !important}.fa-vcard:before,.fa-address-card:before{content:"\f2bb" !important}.fa-vcard-o:before,.fa-address-card-o:before{content:"\f2bc" !important}.fa-user-circle:before{content:"\f2bd" !important}.fa-user-circle-o:before{content:"\f2be" !important}.fa-user-o:before{content:"\f2c0" !important}.fa-id-badge:before{content:"\f2c1" !important}.fa-drivers-license:before,.fa-id-card:before{content:"\f2c2" !important}.fa-drivers-license-o:before,.fa-id-card-o:before{content:"\f2c3" !important}.fa-quora:before{content:"\f2c4" !important}.fa-free-code-camp:before{content:"\f2c5" !important}.fa-telegram:before{content:"\f2c6" !important}.fa-thermometer-4:before,.fa-thermometer:before,.fa-thermometer-full:before{content:"\f2c7" !important}.fa-thermometer-3:before,.fa-thermometer-three-quarters:before{content:"\f2c8" !important}.fa-thermometer-2:before,.fa-thermometer-half:before{content:"\f2c9" !important}.fa-thermometer-1:before,.fa-thermometer-quarter:before{content:"\f2ca" !important}.fa-thermometer-0:before,.fa-thermometer-empty:before{content:"\f2cb" !important}.fa-shower:before{content:"\f2cc" !important}.fa-bathtub:before,.fa-s15:before,.fa-bath:before{content:"\f2cd" !important}.fa-podcast:before{content:"\f2ce" !important}.fa-window-maximize:before{content:"\f2d0" !important}.fa-window-minimize:before{content:"\f2d1" !important}.fa-window-restore:before{content:"\f2d2" !important}.fa-times-rectangle:before,.fa-window-close:before{content:"\f2d3" !important}.fa-times-rectangle-o:before,.fa-window-close-o:before{content:"\f2d4" !important}.fa-bandcamp:before{content:"\f2d5" !important}.fa-grav:before{content:"\f2d6" !important}.fa-etsy:before{content:"\f2d7" !important}.fa-imdb:before{content:"\f2d8" !important}.fa-ravelry:before{content:"\f2d9" !important}.fa-eercast:before{content:"\f2da" !important}.fa-microchip:before{content:"\f2db" !important}.fa-snowflake-o:before{content:"\f2dc" !important}.fa-superpowers:before{content:"\f2dd" !important}.fa-wpexplorer:before{content:"\f2de" !important}.fa-meetup:before{content:"\f2e0" !important}.x-fa:before{font-family:FontAwesome !important}@font-face{font-family:'ExtJS';src:url('font-ext/fonts/ExtJS.eot?-tqegh9');src:url('font-ext/fonts/ExtJS.eot?#iefix-tqegh9') format('embedded-opentype'), url('font-ext/fonts/ExtJS.ttf?-tqegh9') format('truetype'), url('font-ext/fonts/ExtJS.woff?-tqegh9') format('woff'), url('font-ext/fonts/ExtJS.svg?-tqegh9#ExtJS') format('svg');font-weight:normal;font-style:normal}.ext{font-family:ExtJS}.ext-sencha:before{content:"\e61e"}.ext-checkbox-checked:before{content:"\e613"}.ext-checkbox-unchecked:before{content:"\e614"}.ext-chevron-left:before{content:"\e615"}.ext-chevron-right:before{content:"\e616"}.ext-double-chevron-left:before{content:"\e617"}.ext-double-chevron-right:before{content:"\e618"}.ext-sort-down:before{content:"\e619"}.ext-sort-up:before{content:"\e61a"}.ext-spinner-down:before{content:"\e61b"}.ext-spinner-up:before{content:"\e61c"}.ext-square-edit:before{content:"\e61d"}.ext-equals-vertical:before{content:"\e612"}.ext-expand:before{content:"\e600"}.ext-columns:before{content:"\e601"}.ext-dirty:before{content:"\e602"}.ext-dirty-rtl:before{content:"\e603"}.ext-edit-html:before{content:"\e604"}.ext-equals:before{content:"\e605"}.ext-collapse:before{content:"\e606"}.ext-group-by:before{content:"\e607"}.ext-minimize:before{content:"\e608"}.ext-nw-handle:before{content:"\e609"}.ext-ne-handle:before{content:"\e60a"}.ext-sw-handle:before{content:"\e60b"}.ext-se-handle:before{content:"\e60c"}.ext-text-background-color:before{content:"\e60d"}.ext-text-color:before{content:"\e60e"}.ext-text-decrease:before{content:"\e60f"}.ext-text-increase:before{content:"\e610"}.ext-unpin:before{content:"\e611"}@font-face{font-family:'Open Sans';src:local("OpenSans-Light");src:url('fonts/OpenSans-Light.ttf');font-weight:300;font-style:normal}@font-face{font-family:'Open Sans';src:local("OpenSans-LightItalic");src:url('fonts/OpenSans-LightItalic.ttf');font-weight:300;font-style:italic}@font-face{font-family:'Open Sans';src:local("OpenSans-Regular");src:url('fonts/OpenSans-Regular.ttf');font-weight:400;font-style:normal}@font-face{font-family:'Open Sans';src:local("OpenSans-Italic");src:url('fonts/OpenSans-Italic.ttf');font-weight:400;font-style:italic}@font-face{font-family:'Open Sans';src:local("OpenSans-Semibold");src:url('fonts/OpenSans-Semibold.ttf');font-weight:600;font-style:normal}@font-face{font-family:'Open Sans';src:local("OpenSans-SemiboldItalic");src:url('fonts/OpenSans-SemiboldItalic.ttf');font-weight:600;font-style:italic}@font-face{font-family:'Open Sans';src:local("OpenSans-Bold");src:url('fonts/OpenSans-Bold.ttf');font-weight:700;font-style:normal}@font-face{font-family:'Open Sans';src:local("OpenSans-BoldItalic");src:url('fonts/OpenSans-BoldItalic.ttf');font-weight:700;font-style:italic}@font-face{font-family:'Open Sans';src:local("OpenSans-ExtraBold");src:url('fonts/OpenSans-ExtraBold.ttf');font-weight:800;font-style:normal}@font-face{font-family:'Open Sans';src:local("OpenSans-ExtraBoldItalic");src:url('fonts/OpenSans-ExtraBoldItalic.ttf');font-weight:800;font-style:italic}.x-fieldset{border-top:1px solid #bbb !important;background:#f6f6f6;position:static}.x-fieldset .x-fieldset-body{position:relative}.x-fieldset.x-fieldset-collapsed{background:none}.x-menu-item-active .x-menu-item-text{font-weight:400}.x-tab-close-btn:before{display:block;width:16px;line-height:16px;text-align:center}.x-breadcrumb-btn > .x-btn-arrow-right:after{content:''}.x-toast{-webkit-box-shadow:rgba(0, 0, 0, 0.5) 0 2px 2px;-moz-box-shadow:rgba(0, 0, 0, 0.5) 0 2px 2px;box-shadow:rgba(0, 0, 0, 0.5) 0 2px 2px} \ No newline at end of file diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/ux-all.css b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/ux-all.css new file mode 100644 index 0000000..1d6f639 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/resources/ux-all.css @@ -0,0 +1 @@ +.x-gauge svg{display:block}.x-gauge-text{position:absolute;text-align:center}.x-gauge svg{display:block}.x-gauge .x-gauge-track{fill:#ececec;fill-opacity:1;stroke:#d0d0d0;stroke-opacity:1;stroke-width:1}.x-gauge .x-gauge-value{fill:#7fb5e4;fill-opacity:1;stroke:none;stroke-opacity:1;stroke-width:1}.ux-rating-picker{overflow:hidden;color:#ccc;-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=80)";opacity:0.8;display:inline-block;vertical-align:top;line-height:1}.ux-rating-picker-inner{position:relative;overflow:hidden;display:inline-block;vertical-align:top;cursor:pointer;white-space:nowrap}.ux-rating-picker-over.ux-rating-picker-track-over{color:#ccc}.ux-rating-picker-over.ux-rating-picker-track-over > * > .ux-rating-picker-value{display:none;width:0}.ux-rating-picker-over.ux-rating-picker-track-over > * > .ux-rating-picker-value:hover{color:inherit}.ux-rating-picker-over.ux-rating-picker-track-over > * > .ux-rating-picker-tracker{display:inline-block}.ux-rating-picker-value,.ux-rating-picker-tracker{overflow:hidden;position:absolute;white-space:nowrap;top:0;width:0;height:100%;color:#ffe850}.ux-rating-picker-tracker{display:none}.ux-rating-picker-over{-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=100)";opacity:1}.x-view-selector{position:absolute;border:1px dotted #39b}.x-explorer-view{background-color:#fff}.x-explorer-item{float:left}.x-explorer-item-text{text-align:center}.x-explorer-node-icon{height:100px;width:100px;background:url(images/explorer/node.png)}.x-explorer-leaf-icon{background:url(images/explorer/leaf.png)}.x-statusbar .x-status-text{cursor:default}.x-statusbar .x-status-busy{padding-left:25px !important;background:transparent no-repeat 3px 0}.x-statusbar .x-status-text-panel{border:0 none;padding:2px 8px 2px 5px}.x-statusbar .x-status-error{cursor:pointer;padding-left:25px !important;background:transparent no-repeat 3px 0}.x-statusbar .x-status-valid{padding-left:25px !important;background:transparent no-repeat 3px 0}.x-status-error-list{font:11px tahoma, arial, verdana, sans-serif;position:absolute;z-index:9999;border-top:1px solid;border-right:1px solid;border-bottom:1px solid;border-left:1px solid;padding:5px 10px}.x-status-error-list li{cursor:pointer;list-style:disc;margin-left:10px}.x-status-error-list li a{text-decoration:none}.x-status-error-list li a:hover{text-decoration:underline}.x-statusbar .x-status-busy{background-image:url(images/statusbar/loading.gif)}.x-statusbar .x-status-error{color:#c33;background-image:url(images/statusbar/exclamation.gif)}.x-statusbar .x-status-valid{background-image:url(images/statusbar/accept.png)}.x-status-error-list{border-color:#c33;background:white}.x-status-error-list li a{color:#15428b}.x-livesearch-match{font-weight:bold;background-color:yellow}.x-tab-tabmenu-right{background:transparent url(images/tabscrollermenu/menu.gif) no-repeat 0 0;width:18px;height:20px;cursor:pointer;zoom:1;z-index:6;float:right}.x-tab-tabmenu-over{background-position:-18px 0}.x-tab-tabmenu-disabled{background-position:0 0;opacity:0.5;-moz-opacity:0.5;filter:opacity=50;cursor:default}.x-colorpicker{overflow:visible}.x-colorpicker >.x-box-inner{overflow:visible}.x-colorpicker .x-form-item-label{text-align:center}.x-colopicker-escape-overflow{overflow:visible}.x-colopicker-escape-overflow >.x-box-inner{overflow:visible}.x-colorpicker-colormap{background-image:url(images/colorpick/map_gradient.png)}.x-colorpicker-colormap-draghandle-container{overflow:visible;z-index:1}.x-colorpicker-colormap-blender{position:absolute;top:0;left:0;width:100%;height:100%}.x-colorpicker-colormap-draghandle{width:15px;height:15px;position:relative;left:-7px;top:-7px;background-image:url(images/colorpick/drag_circle.png)}.x-colorpicker-draghandle-container{width:20px}.x-colorpicker-draghandle-container .x-autocontainer-outerCt{height:100%}.x-colorpicker-draghandle{width:32px;height:9px;position:relative;left:-6px;top:-4px;background-image:url(images/colorpick/pickerslider.png);background-repeat:no-repeat;z-index:1}.x-colorpicker-hue{background-image:url(images/colorpick/huegradient.png)}.x-colorpicker-hue-gradient{position:absolute;top:0;left:0;width:100%;height:100%}.x-colorpicker-saturation .x-colorpicker-draghandle-container{background:-moz-linear-gradient(top,#fff 0%,#000 100%);background:-webkit-linear-gradient(top,#fff 0%,#000 100%);background:-o-linear-gradient(top,#fff 0%,#000 100%);background:-ms-linear-gradient(top,#fff 0%,#000 100%);background:linear-gradient(to bottom,#fff 0%, #000 100%);filter:progid:DXImageTransform.Microsoft.gradient( startColorstr='#ffffff', endColorstr='#000000',GradientType=0 )}.x-colorpicker-value .x-colorpicker-draghandle-container{background:-moz-linear-gradient(top,red 0%,#000 100%);background:-webkit-linear-gradient(top,red 0%,#000 100%);background:-o-linear-gradient(top,red 0%,#000 100%);background:-ms-linear-gradient(top,red 0%,#000 100%);background:linear-gradient(to bottom,red 0%, #000 100%);filter:progid:DXImageTransform.Microsoft.gradient( startColorstr='#ff0000', endColorstr='#000000',GradientType=0 )}.x-colorpicker-alpha .x-colorpicker-draghandle-container{background-image:url(images/colorpick/checkerboard.png)}.x-colorpicker-preview{background-image:url(images/colorpick/checkerboard.png)}.x-colorpicker-button{position:relative;border:1px solid gray;background-image:url(images/colorpick/checkerboard.png)}.x-colorpicker-field .x-form-item-body{position:relative}.x-colorpicker-field input{padding-left:26px}.x-colorpicker-field-swatch{position:absolute;width:20px;height:20px;left:4px;background-image:url(images/colorpick/checkerboard.png);top:0px;bottom:0px;margin:auto}.x-colorpicker-field-swatch-inner{position:absolute;height:100%;width:100%}.x-form-multiselect-body .x-boundlist .x-mask{background:none}.x-form-itemselector-body .x-form-item{margin:0}.x-form-itemselector-top{background-image:url(images/itemselector/top.gif)}.x-form-itemselector-up{background-image:url(images/itemselector/up.gif)}.x-form-itemselector-add{background-image:url(images/itemselector/right.gif)}.x-form-itemselector-remove{background-image:url(images/itemselector/left.gif)}.x-form-itemselector-down{background-image:url(images/itemselector/down.gif)}.x-form-itemselector-bottom{background-image:url(images/itemselector/bottom.gif)}.x-grid-subtable{border-collapse:collapse}tr.x-grid-subtable-row{background-color:#fff}.x-grid-subtable-header{border:1px solid #d0d0d0;color:#404040;font:400 13px/19px 'Open Sans', 'Helvetica Neue', helvetica, arial, verdana, sans-serif;background-image:none;background-color:#fff;padding:6px 10px 5px 10px;text-overflow:ellipsis}.x-grid-subtable-cell{border-top:1px solid #e9e9e9;border-right:1px solid #e9e9e9;border-bottom:1px solid #e9e9e9;border-left:1px solid #e9e9e9}.x-responsivecolumn{padding:20px 0 0 20px}.x-responsivecolumn > *{margin:0 20px 20px 0;float:left} \ No newline at end of file diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/theme-triton-debug.js b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/theme-triton-debug.js new file mode 100644 index 0000000..03cfcb5 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/theme-triton-debug.js @@ -0,0 +1,577 @@ +Ext.define('Ext.theme.neptune.Component', { + override: 'Ext.Component', + initComponent: function() { + this.callParent(); + if (this.dock && this.border === undefined) { + this.border = false; + } + }, + privates: { + initStyles: function() { + var me = this, + hasOwnBorder = me.hasOwnProperty('border'), + border = me.border; + if (me.dock) { + // prevent the superclass method from setting the border style. We want to + // allow dock layout to decide which borders to suppress. + me.border = null; + } + me.callParent(arguments); + if (hasOwnBorder) { + me.border = border; + } else { + delete me.border; + } + } + } +}, function() { + Ext.namespace('Ext.theme.is').Neptune = true; + Ext.theme.name = 'Neptune'; +}); + +Ext.define('Ext.theme.triton.Component', { + override: 'Ext.Component' +}, function() { + Ext.namespace('Ext.theme.is').Triton = true; + Ext.theme.name = 'Triton'; +}); + +Ext.define('Ext.theme.triton.list.TreeItem', { + override: 'Ext.list.TreeItem', + compatibility: Ext.isIE8, + setFloated: function(floated, wasFloated) { + this.callParent([ + floated, + wasFloated + ]); + this.toolElement.syncRepaint(); + } +}); + +Ext.define('Ext.theme.neptune.resizer.Splitter', { + override: 'Ext.resizer.Splitter', + size: 8 +}); + +Ext.define('Ext.theme.triton.resizer.Splitter', { + override: 'Ext.resizer.Splitter', + size: 10 +}); + +Ext.define('Ext.theme.neptune.toolbar.Toolbar', { + override: 'Ext.toolbar.Toolbar', + usePlainButtons: false, + border: false +}); + +Ext.define('Ext.theme.neptune.layout.component.Dock', { + override: 'Ext.layout.component.Dock', + /** + * This table contains the border removal classes indexed by the sum of the edges to + * remove. Each edge is assigned a value: + * + * * `left` = 1 + * * `bottom` = 2 + * * `right` = 4 + * * `top` = 8 + * + * @private + */ + noBorderClassTable: [ + 0, + // TRBL + Ext.baseCSSPrefix + 'noborder-l', + // 0001 = 1 + Ext.baseCSSPrefix + 'noborder-b', + // 0010 = 2 + Ext.baseCSSPrefix + 'noborder-bl', + // 0011 = 3 + Ext.baseCSSPrefix + 'noborder-r', + // 0100 = 4 + Ext.baseCSSPrefix + 'noborder-rl', + // 0101 = 5 + Ext.baseCSSPrefix + 'noborder-rb', + // 0110 = 6 + Ext.baseCSSPrefix + 'noborder-rbl', + // 0111 = 7 + Ext.baseCSSPrefix + 'noborder-t', + // 1000 = 8 + Ext.baseCSSPrefix + 'noborder-tl', + // 1001 = 9 + Ext.baseCSSPrefix + 'noborder-tb', + // 1010 = 10 + Ext.baseCSSPrefix + 'noborder-tbl', + // 1011 = 11 + Ext.baseCSSPrefix + 'noborder-tr', + // 1100 = 12 + Ext.baseCSSPrefix + 'noborder-trl', + // 1101 = 13 + Ext.baseCSSPrefix + 'noborder-trb', + // 1110 = 14 + Ext.baseCSSPrefix + 'noborder-trbl' + ], + // 1111 = 15 + /** + * The numeric values assigned to each edge indexed by the `dock` config value. + * @private + */ + edgeMasks: { + top: 8, + right: 4, + bottom: 2, + left: 1 + }, + handleItemBorders: function() { + var me = this, + edges = 0, + maskT = 8, + maskR = 4, + maskB = 2, + maskL = 1, + owner = me.owner, + bodyBorder = owner.bodyBorder, + ownerBorder = owner.border, + collapsed = me.collapsed, + edgeMasks = me.edgeMasks, + noBorderCls = me.noBorderClassTable, + dockedItemsGen = owner.dockedItems.generation, + b, borderCls, docked, edgesTouched, i, ln, item, dock, lastValue, mask, addCls, removeCls; + if (me.initializedBorders === dockedItemsGen) { + return; + } + addCls = []; + removeCls = []; + borderCls = me.getBorderCollapseTable(); + noBorderCls = me.getBorderClassTable ? me.getBorderClassTable() : noBorderCls; + me.initializedBorders = dockedItemsGen; + // Borders have to be calculated using expanded docked item collection. + me.collapsed = false; + docked = me.getDockedItems('visual'); + me.collapsed = collapsed; + for (i = 0 , ln = docked.length; i < ln; i++) { + item = docked[i]; + if (item.ignoreBorderManagement) { + // headers in framed panels ignore border management, so we do not want + // to set "satisfied" on the edge in question + + continue; + } + dock = item.dock; + mask = edgesTouched = 0; + addCls.length = 0; + removeCls.length = 0; + if (dock !== 'bottom') { + if (edges & maskT) { + // if (not touching the top edge) + b = item.border; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskT; + } + } + if (b === false) { + mask += maskT; + } + } + if (dock !== 'left') { + if (edges & maskR) { + // if (not touching the right edge) + b = item.border; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskR; + } + } + if (b === false) { + mask += maskR; + } + } + if (dock !== 'top') { + if (edges & maskB) { + // if (not touching the bottom edge) + b = item.border; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskB; + } + } + if (b === false) { + mask += maskB; + } + } + if (dock !== 'right') { + if (edges & maskL) { + // if (not touching the left edge) + b = item.border; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskL; + } + } + if (b === false) { + mask += maskL; + } + } + if ((lastValue = item.lastBorderMask) !== mask) { + item.lastBorderMask = mask; + if (lastValue) { + removeCls[0] = noBorderCls[lastValue]; + } + if (mask) { + addCls[0] = noBorderCls[mask]; + } + } + if ((lastValue = item.lastBorderCollapse) !== edgesTouched) { + item.lastBorderCollapse = edgesTouched; + if (lastValue) { + removeCls[removeCls.length] = borderCls[lastValue]; + } + if (edgesTouched) { + addCls[addCls.length] = borderCls[edgesTouched]; + } + } + if (removeCls.length) { + item.removeCls(removeCls); + } + if (addCls.length) { + item.addCls(addCls); + } + // mask can use += but edges must use |= because there can be multiple items + // on an edge but the mask is reset per item + edges |= edgeMasks[dock]; + } + // = T, R, B or L (8, 4, 2 or 1) + mask = edgesTouched = 0; + addCls.length = 0; + removeCls.length = 0; + if (edges & maskT) { + // if (not touching the top edge) + b = bodyBorder; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskT; + } + } + if (b === false) { + mask += maskT; + } + if (edges & maskR) { + // if (not touching the right edge) + b = bodyBorder; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskR; + } + } + if (b === false) { + mask += maskR; + } + if (edges & maskB) { + // if (not touching the bottom edge) + b = bodyBorder; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskB; + } + } + if (b === false) { + mask += maskB; + } + if (edges & maskL) { + // if (not touching the left edge) + b = bodyBorder; + } else { + b = ownerBorder; + if (b !== false) { + edgesTouched += maskL; + } + } + if (b === false) { + mask += maskL; + } + if ((lastValue = me.lastBodyBorderMask) !== mask) { + me.lastBodyBorderMask = mask; + if (lastValue) { + removeCls[0] = noBorderCls[lastValue]; + } + if (mask) { + addCls[0] = noBorderCls[mask]; + } + } + if ((lastValue = me.lastBodyBorderCollapse) !== edgesTouched) { + me.lastBodyBorderCollapse = edgesTouched; + if (lastValue) { + removeCls[removeCls.length] = borderCls[lastValue]; + } + if (edgesTouched) { + addCls[addCls.length] = borderCls[edgesTouched]; + } + } + if (removeCls.length) { + owner.removeBodyCls(removeCls); + } + if (addCls.length) { + owner.addBodyCls(addCls); + } + }, + onRemove: function(item) { + var me = this, + lastBorderMask = item.lastBorderMask, + lastBorderCollapse = item.lastBorderCollapse; + if (!item.destroyed && !item.ignoreBorderManagement) { + if (lastBorderMask) { + item.lastBorderMask = 0; + item.removeCls(me.noBorderClassTable[lastBorderMask]); + } + if (lastBorderCollapse) { + item.lastBorderCollapse = 0; + item.removeCls(me.getBorderCollapseTable()[lastBorderCollapse]); + } + } + me.callParent([ + item + ]); + } +}); + +Ext.define('Ext.theme.neptune.panel.Panel', { + override: 'Ext.panel.Panel', + border: false, + bodyBorder: false, + initBorderProps: Ext.emptyFn, + initBodyBorder: function() { + // The superclass method converts a truthy bodyBorder into a number and sets + // an inline border-width style on the body element. This prevents that from + // happening if borderBody === true so that the body will get its border-width + // the stylesheet. + if (this.bodyBorder !== true) { + this.callParent(); + } + } +}); + +Ext.define('Ext.theme.neptune.container.ButtonGroup', { + override: 'Ext.container.ButtonGroup', + usePlainButtons: false +}); + +Ext.define('Ext.theme.triton.form.field.Checkbox', { + override: 'Ext.form.field.Checkbox', + compatibility: Ext.isIE8, + initComponent: function() { + this.callParent(); + Ext.on({ + show: 'onGlobalShow', + scope: this + }); + }, + onFocus: function(e) { + var focusClsEl; + this.callParent([ + e + ]); + focusClsEl = this.getFocusClsEl(); + if (focusClsEl) { + focusClsEl.syncRepaint(); + } + }, + onBlur: function(e) { + var focusClsEl; + this.callParent([ + e + ]); + focusClsEl = this.getFocusClsEl(); + if (focusClsEl) { + focusClsEl.syncRepaint(); + } + }, + onGlobalShow: function(cmp) { + if (cmp.isAncestor(this)) { + this.getFocusClsEl().syncRepaint(); + } + } +}); + +Ext.define('Ext.theme.neptune.toolbar.Paging', { + override: 'Ext.toolbar.Paging', + defaultButtonUI: 'plain-toolbar', + inputItemWidth: 40 +}); + +Ext.define('Ext.theme.triton.toolbar.Paging', { + override: 'Ext.toolbar.Paging', + inputItemWidth: 50 +}); + +Ext.define('Ext.theme.neptune.picker.Month', { + override: 'Ext.picker.Month', + // Monthpicker contains logic that reduces the margins of the month items if it detects + // that the text has wrapped. This can happen in the classic theme in certain + // locales such as zh_TW. In order to work around this, Month picker measures + // the month items to see if the height is greater than "measureMaxHeight". + // In neptune the height of the items is larger, so we must increase this value. + // While the actual height of the month items in neptune is 24px, we will only + // determine that the text has wrapped if the height of the item exceeds 36px. + // this allows theme developers some leeway to increase the month item size in + // a neptune-derived theme. + measureMaxHeight: 36 +}); + +Ext.define('Ext.theme.triton.picker.Month', { + override: 'Ext.picker.Month', + footerButtonUI: 'default-toolbar', + calculateMonthMargin: Ext.emptyFn +}); + +Ext.define('Ext.theme.triton.picker.Date', { + override: 'Ext.picker.Date', + footerButtonUI: 'default-toolbar' +}); + +Ext.define('Ext.theme.neptune.form.field.HtmlEditor', { + override: 'Ext.form.field.HtmlEditor', + defaultButtonUI: 'plain-toolbar' +}); + +Ext.define('Ext.theme.neptune.panel.Table', { + override: 'Ext.panel.Table', + lockableBodyBorder: true, + initComponent: function() { + var me = this; + me.callParent(); + if (!me.hasOwnProperty('bodyBorder') && !me.hideHeaders && (me.lockableBodyBorder || !me.lockable)) { + me.bodyBorder = true; + } + } +}); + +Ext.define('Ext.theme.neptune.grid.RowEditor', { + override: 'Ext.grid.RowEditor', + buttonUI: 'default-toolbar' +}); + +Ext.define('Ext.theme.triton.grid.column.Column', { + override: 'Ext.grid.column.Column', + compatibility: Ext.isIE8, + onTitleMouseOver: function() { + var triggerEl = this.triggerEl; + this.callParent(arguments); + if (triggerEl) { + triggerEl.syncRepaint(); + } + } +}); + +Ext.define('Ext.theme.triton.grid.column.Check', { + override: 'Ext.grid.column.Check', + compatibility: Ext.isIE8, + setRecordCheck: function(record, index, checked, cell) { + this.callParent(arguments); + Ext.fly(cell).syncRepaint(); + } +}); + +Ext.define('Ext.theme.neptune.grid.column.RowNumberer', { + override: 'Ext.grid.column.RowNumberer', + width: 25 +}); + +Ext.define('Ext.theme.triton.grid.column.RowNumberer', { + override: 'Ext.grid.column.RowNumberer', + width: 32 +}); + +Ext.define('Ext.theme.triton.menu.Item', { + override: 'Ext.menu.Item', + compatibility: Ext.isIE8, + onFocus: function(e) { + this.callParent([ + e + ]); + this.repaintIcons(); + }, + onFocusLeave: function(e) { + this.callParent([ + e + ]); + this.repaintIcons(); + }, + privates: { + repaintIcons: function() { + var iconEl = this.iconEl, + arrowEl = this.arrowEl, + checkEl = this.checkEl; + if (iconEl) { + iconEl.syncRepaint(); + } + if (arrowEl) { + arrowEl.syncRepaint(); + } + if (checkEl) { + checkEl.syncRepaint(); + } + } + } +}); + +Ext.define('Ext.theme.neptune.menu.Separator', { + override: 'Ext.menu.Separator', + border: true +}); + +Ext.define('Ext.theme.neptune.menu.Menu', { + override: 'Ext.menu.Menu', + showSeparator: false +}); + +Ext.define('Ext.theme.triton.menu.Menu', { + override: 'Ext.menu.Menu', + compatibility: Ext.isIE8, + afterShow: function() { + var me = this, + items, item, i, len; + me.callParent(arguments); + items = me.items.getRange(); + for (i = 0 , len = items.length; i < len; i++) { + item = items[i]; + // Just in case if it happens to be a non-menu Item + if (item && item.repaintIcons) { + item.repaintIcons(); + } + } + } +}); + +Ext.define('Ext.theme.triton.grid.plugin.RowExpander', { + override: 'Ext.grid.plugin.RowExpander', + headerWidth: 32 +}); + +Ext.define('Ext.theme.triton.grid.selection.SpreadsheetModel', { + override: 'Ext.grid.selection.SpreadsheetModel', + checkboxHeaderWidth: 32 +}); + +Ext.define('Ext.theme.triton.selection.CheckboxModel', { + override: 'Ext.selection.CheckboxModel', + headerWidth: 32, + onHeaderClick: function(headerCt, header, e) { + this.callParent([ + headerCt, + header, + e + ]); + // Every checkbox needs repainting. + if (Ext.isIE8) { + header.getView().ownerGrid.el.syncRepaint(); + } + } +}); + diff --git a/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/theme-triton.js b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/theme-triton.js new file mode 100644 index 0000000..120b1c0 --- /dev/null +++ b/src/main/webapp/resources/ext-6.5.3/classic/theme-triton/theme-triton.js @@ -0,0 +1 @@ +Ext.define('Ext.theme.neptune.Component',{override:'Ext.Component',initComponent:function(){this.callParent();if(this.dock&&this.border===undefined){this.border=!1}},privates:{initStyles:function(){var a=this,b=a.hasOwnProperty('border'),c=a.border;if(a.dock){a.border=null}a.callParent(arguments);if(b){a.border=c}else {delete a.border}}}},function(){Ext.namespace('Ext.theme.is').Neptune=!0;Ext.theme.name='Neptune'});Ext.define('Ext.theme.triton.Component',{override:'Ext.Component'},function(){Ext.namespace('Ext.theme.is').Triton=!0;Ext.theme.name='Triton'});Ext.define('Ext.theme.triton.list.TreeItem',{override:'Ext.list.TreeItem',compatibility:Ext.isIE8,setFloated:function(b,a){this.callParent([b,a]);this.toolElement.syncRepaint()}});Ext.define('Ext.theme.neptune.resizer.Splitter',{override:'Ext.resizer.Splitter',size:8});Ext.define('Ext.theme.triton.resizer.Splitter',{override:'Ext.resizer.Splitter',size:10});Ext.define('Ext.theme.neptune.toolbar.Toolbar',{override:'Ext.toolbar.Toolbar',usePlainButtons:!1,border:!1});Ext.define('Ext.theme.neptune.layout.component.Dock',{override:'Ext.layout.component.Dock',noBorderClassTable:[0,Ext.baseCSSPrefix+'noborder-l',Ext.baseCSSPrefix+'noborder-b',Ext.baseCSSPrefix+'noborder-bl',Ext.baseCSSPrefix+'noborder-r',Ext.baseCSSPrefix+'noborder-rl',Ext.baseCSSPrefix+'noborder-rb',Ext.baseCSSPrefix+'noborder-rbl',Ext.baseCSSPrefix+'noborder-t',Ext.baseCSSPrefix+'noborder-tl',Ext.baseCSSPrefix+'noborder-tb',Ext.baseCSSPrefix+'noborder-tbl',Ext.baseCSSPrefix+'noborder-tr',Ext.baseCSSPrefix+'noborder-trl',Ext.baseCSSPrefix+'noborder-trb',Ext.baseCSSPrefix+'noborder-trbl'],edgeMasks:{top:8,right:4,bottom:2,left:1},handleItemBorders:function(){var d=this,i=0,o=8,n=4,l=2,m=1,r=d.owner,s=r.bodyBorder,j=r.border,x=d.collapsed,y=d.edgeMasks,k=d.noBorderClassTable,v=r.dockedItems.generation,a,q,u,b,t,w,g,p,h,c,f,e;if(d.initializedBorders===v){return}f=[];e=[];q=d.getBorderCollapseTable();k=d.getBorderClassTable?d.getBorderClassTable():k;d.initializedBorders=v;d.collapsed=!1;u=d.getDockedItems('visual');d.collapsed=x;for(t=0,w=u.length;t +/** + * @class Ext.Boot + * @singleton + * @private + */ +Ext.Boot = Ext.Boot || (function(emptyFn) { + var doc = document, + _emptyArray = [], + _config = { + /** + * @cfg {Boolean} [disableCaching=true] + * If `true` current timestamp is added to script URL's to prevent caching. + * In debug builds, adding a "cache" or "disableCacheBuster" query parameter + * to the page's URL will set this to `false`. + */ + disableCaching: (/[?&](?:cache|disableCacheBuster)\b/i.test(location.search) || !(/http[s]?\:/i.test(location.href)) || /(^|[ ;])ext-cache=1/.test(doc.cookie)) ? false : true, + /** + * @cfg {String} [disableCachingParam="_dc"] + * The query parameter name for the cache buster's timestamp. + */ + disableCachingParam: '_dc', + /** + * @cfg {Boolean} loadDelay + * Millisecond delay between asynchronous script injection (prevents stack + * overflow on some user agents) 'false' disables delay but potentially + * increases stack load. + */ + loadDelay: false, + /** + * @cfg {Boolean} preserveScripts + * `false` to remove asynchronously loaded scripts, `true` to retain script + * element for browser debugger compatibility and improved load performance. + */ + preserveScripts: true, + /** + * @cfg {String} [charset=UTF-8] + * Optional charset to specify encoding of dynamic content. + */ + charset: 'UTF-8' + }, + _assetConfig = {}, + cssRe = /\.css(?:\?|$)/i, + resolverEl = doc.createElement('a'), + isBrowser = typeof window !== 'undefined', + _environment = { + browser: isBrowser, + node: !isBrowser && (typeof require === 'function'), + phantom: (window && (window._phantom || window.callPhantom)) || /PhantomJS/.test(window.navigator.userAgent) + }, + _tags = (Ext.platformTags = {}), + // All calls to _debug are commented out to speed up old browsers a bit; + // yes that makes a difference because the cost of concatenating strings + // and passing them into _debug() adds up pretty quickly. + _debug = function(message) {}, + //console.log(message); + _apply = function(object, config, defaults) { + if (defaults) { + _apply(object, defaults); + } + if (object && config && typeof config === 'object') { + for (var i in config) { + object[i] = config[i]; + } + } + return object; + }, + _merge = function() { + var lowerCase = false, + obj = Array.prototype.shift.call(arguments), + index, i, len, value; + if (typeof arguments[arguments.length - 1] === 'boolean') { + lowerCase = Array.prototype.pop.call(arguments); + } + len = arguments.length; + for (index = 0; index < len; index++) { + value = arguments[index]; + if (typeof value === 'object') { + for (i in value) { + obj[lowerCase ? i.toLowerCase() : i] = value[i]; + } + } + } + return obj; + }, + _getKeys = (typeof Object.keys == 'function') ? function(object) { + if (!object) { + return []; + } + return Object.keys(object); + } : function(object) { + var keys = [], + property; + for (property in object) { + if (object.hasOwnProperty(property)) { + keys.push(property); + } + } + return keys; + }, + /* + * The Boot loader class manages Request objects that contain one or + * more individual urls that need to be loaded. Requests can be performed + * synchronously or asynchronously, but will always evaluate urls in the + * order specified on the request object. + */ + Boot = { + loading: 0, + loaded: 0, + apply: _apply, + env: _environment, + config: _config, + /** + * @cfg {Object} assetConfig + * A map (url->assetConfig) that contains information about assets loaded by the Microlaoder. + */ + assetConfig: _assetConfig, + // Keyed by absolute URL this object holds "true" if that URL is already loaded + // or an array of callbacks to call once it loads. + scripts: {}, + /* + Entry objects + + 'http://foo.com/bar/baz/Thing.js': { + done: true, + el: scriptEl || linkEl, + preserve: true, + requests: [ request1, ... ] + } + */ + /** + * contains the current script name being loaded + * (loadSync or sequential load only) + */ + currentFile: null, + suspendedQueue: [], + currentRequest: null, + // when loadSync is called, need to cause subsequent load requests to also be loadSync, + // eg, when Ext.require(...) is called + syncMode: false, + /* + * simple helper method for debugging + */ + debug: _debug, + /** + * enables / disables loading scripts via script / link elements rather + * than using ajax / eval + */ + useElements: true, + listeners: [], + Request: Request, + Entry: Entry, + allowMultipleBrowsers: false, + browserNames: { + ie: 'IE', + firefox: 'Firefox', + safari: 'Safari', + chrome: 'Chrome', + opera: 'Opera', + dolfin: 'Dolfin', + edge: 'Edge', + webosbrowser: 'webOSBrowser', + chromeMobile: 'ChromeMobile', + chromeiOS: 'ChromeiOS', + silk: 'Silk', + other: 'Other' + }, + osNames: { + ios: 'iOS', + android: 'Android', + windowsPhone: 'WindowsPhone', + webos: 'webOS', + blackberry: 'BlackBerry', + rimTablet: 'RIMTablet', + mac: 'MacOS', + win: 'Windows', + tizen: 'Tizen', + linux: 'Linux', + bada: 'Bada', + chromeOS: 'ChromeOS', + other: 'Other' + }, + browserPrefixes: { + ie: 'MSIE ', + edge: 'Edge/', + firefox: 'Firefox/', + chrome: 'Chrome/', + safari: 'Version/', + opera: 'OPR/', + dolfin: 'Dolfin/', + webosbrowser: 'wOSBrowser/', + chromeMobile: 'CrMo/', + chromeiOS: 'CriOS/', + silk: 'Silk/' + }, + // When a UA reports multiple browsers this list is used to prioritize the 'real' browser + // lower index number will win + browserPriority: [ + 'edge', + 'opera', + 'dolfin', + 'webosbrowser', + 'silk', + 'chromeiOS', + 'chromeMobile', + 'ie', + 'firefox', + 'safari', + 'chrome' + ], + osPrefixes: { + tizen: '(Tizen )', + ios: 'i(?:Pad|Phone|Pod)(?:.*)CPU(?: iPhone)? OS ', + android: '(Android |HTC_|Silk/)', + // Some HTC devices ship with an OSX userAgent by default, + // so we need to add a direct check for HTC_ + windowsPhone: 'Windows Phone ', + blackberry: '(?:BlackBerry|BB)(?:.*)Version/', + rimTablet: 'RIM Tablet OS ', + webos: '(?:webOS|hpwOS)/', + bada: 'Bada/', + chromeOS: 'CrOS ' + }, + fallbackOSPrefixes: { + windows: 'win', + mac: 'mac', + linux: 'linux' + }, + devicePrefixes: { + iPhone: 'iPhone', + iPod: 'iPod', + iPad: 'iPad' + }, + maxIEVersion: 12, + /** + * The default function that detects various platforms and sets tags + * in the platform map accordingly. Examples are iOS, android, tablet, etc. + * @param tags the set of tags to populate + */ + detectPlatformTags: function() { + var me = this, + ua = navigator.userAgent, + isMobile = /Mobile(\/|\s)/.test(ua), + element = document.createElement('div'), + isEventSupported = function(name, tag) { + if (tag === undefined) { + tag = window; + } + var eventName = 'on' + name.toLowerCase(), + isSupported = (eventName in element); + if (!isSupported) { + if (element.setAttribute && element.removeAttribute) { + element.setAttribute(eventName, ''); + isSupported = typeof element[eventName] === 'function'; + if (typeof element[eventName] !== 'undefined') { + element[eventName] = undefined; + } + element.removeAttribute(eventName); + } + } + return isSupported; + }, + // Browser Detection + getBrowsers = function() { + var browsers = {}, + maxIEVersion, prefix, value, key, index, len, match, version, matched; + // MS Edge browser (and possibly others) can report multiple browsers in the UserAgent + // "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/42.0.2311.135 Safari/537.36 Edge/12.10240" + // we use this to prioritize the actual browser in this situation + len = me.browserPriority.length; + for (index = 0; index < len; index++) { + key = me.browserPriority[index]; + if (!matched) { + value = me.browserPrefixes[key]; + match = ua.match(new RegExp('(' + value + ')([\\w\\._]+)')); + version = match && match.length > 1 ? parseInt(match[2]) : 0; + if (version) { + matched = true; + } + } else { + version = 0; + } + browsers[key] = version; + } + //Deal with IE document mode + if (browsers.ie) { + var mode = document.documentMode; + if (mode >= 8) { + browsers.ie = mode; + } + } + // Fancy IE greater than and less then quick tags + version = browsers.ie || false; + maxIEVersion = Math.max(version, me.maxIEVersion); + for (index = 8; index <= maxIEVersion; ++index) { + prefix = 'ie' + index; + browsers[prefix + 'm'] = version ? version <= index : 0; + browsers[prefix] = version ? version === index : 0; + browsers[prefix + 'p'] = version ? version >= index : 0; + } + return browsers; + }, + //OS Detection + getOperatingSystems = function() { + var systems = {}, + value, key, keys, index, len, match, matched, version, activeCount; + keys = _getKeys(me.osPrefixes); + len = keys.length; + for (index = 0 , activeCount = 0; index < len; index++) { + key = keys[index]; + value = me.osPrefixes[key]; + match = ua.match(new RegExp('(' + value + ')([^\\s;]+)')); + matched = match ? match[1] : null; + // This is here because some HTC android devices show an OSX Snow Leopard userAgent by default. + // And the Kindle Fire doesn't have any indicator of Android as the OS in its User Agent + if (matched && (matched === 'HTC_' || matched === 'Silk/')) { + version = 2.3; + } else { + version = match && match.length > 1 ? parseFloat(match[match.length - 1]) : 0; + } + if (version) { + activeCount++; + } + systems[key] = version; + } + keys = _getKeys(me.fallbackOSPrefixes); + // If no OS could be found we resort to the fallbacks, otherwise we just + // falsify the fallbacks + len = keys.length; + for (index = 0; index < len; index++) { + key = keys[index]; + // No OS was detected from osPrefixes + if (activeCount === 0) { + value = me.fallbackOSPrefixes[key]; + match = ua.toLowerCase().match(new RegExp(value)); + systems[key] = match ? true : 0; + } else { + systems[key] = 0; + } + } + return systems; + }, + // Device Detection + getDevices = function() { + var devices = {}, + value, key, keys, index, len, match; + keys = _getKeys(me.devicePrefixes); + len = keys.length; + for (index = 0; index < len; index++) { + key = keys[index]; + value = me.devicePrefixes[key]; + match = ua.match(new RegExp(value)); + devices[key] = match ? true : 0; + } + return devices; + }, + browsers = getBrowsers(), + systems = getOperatingSystems(), + devices = getDevices(), + platformParams = Boot.loadPlatformsParam(); + // We apply platformParams from the query here first to allow for forced user valued + // to be used in calculation of generated tags + _merge(_tags, browsers, systems, devices, platformParams, true); + _tags.phone = !!((_tags.iphone || _tags.ipod) || (!_tags.silk && (_tags.android && (_tags.android < 3 || isMobile))) || (_tags.blackberry && isMobile) || (_tags.windowsphone)); + _tags.tablet = !!(!_tags.phone && (_tags.ipad || _tags.android || _tags.silk || _tags.rimtablet || (_tags.ie10 && /; Touch/.test(ua)))); + _tags.touch = // if the browser has touch events we can be reasonably sure the device has + // a touch screen + isEventSupported('touchend') || // browsers that use pointer event have maxTouchPoints > 0 if the + // device supports touch input + // http://www.w3.org/TR/pointerevents/#widl-Navigator-maxTouchPoints + navigator.maxTouchPoints || // IE10 uses a vendor-prefixed maxTouchPoints property + navigator.msMaxTouchPoints; + _tags.desktop = !_tags.phone && !_tags.tablet; + _tags.cordova = _tags.phonegap = !!(window.PhoneGap || window.Cordova || window.cordova); + _tags.webview = /(iPhone|iPod|iPad).*AppleWebKit(?!.*Safari)(?!.*FBAN)/i.test(ua); + _tags.androidstock = (_tags.android <= 4.3) && (_tags.safari || _tags.silk); + // Re-apply any query params here to allow for user override of generated tags (desktop, touch, tablet, etc) + _merge(_tags, platformParams, true); + }, + /** + * Extracts user supplied platform tags from the "platformTags" query parameter + * of the form: + * + * ?platformTags=name:state,name:state,... + * + * (each tag defaults to true when state is unspecified) + * + * Example: + * + * ?platformTags=isTablet,isPhone:false,isDesktop:0,iOS:1,Safari:true, ... + * + * @returns {Object} the platform tags supplied by the query string + */ + loadPlatformsParam: function() { + // Check if the ?platform parameter is set in the URL + var paramsString = window.location.search.substr(1), + paramsArray = paramsString.split("&"), + params = {}, + i, + platforms = {}, + tmpArray, tmplen, platform, name, enabled; + for (i = 0; i < paramsArray.length; i++) { + tmpArray = paramsArray[i].split("="); + params[tmpArray[0]] = tmpArray[1]; + } + if (params.platformTags) { + tmpArray = params.platformTags.split(","); + for (tmplen = tmpArray.length , i = 0; i < tmplen; i++) { + platform = tmpArray[i].split(":"); + name = platform[0]; + enabled = true; + if (platform.length > 1) { + enabled = platform[1]; + if (enabled === 'false' || enabled === '0') { + enabled = false; + } + } + platforms[name] = enabled; + } + } + return platforms; + }, + filterPlatform: function(platform, excludes) { + platform = _emptyArray.concat(platform || _emptyArray); + excludes = _emptyArray.concat(excludes || _emptyArray); + var plen = platform.length, + elen = excludes.length, + include = (!plen && elen), + // default true if only excludes specified + i, tag; + for (i = 0; i < plen && !include; i++) { + tag = platform[i]; + include = !!_tags[tag]; + } + for (i = 0; i < elen && include; i++) { + tag = excludes[i]; + include = !_tags[tag]; + } + return include; + }, + init: function() { + var scriptEls = doc.getElementsByTagName('script'), + script = scriptEls[0], + len = scriptEls.length, + re = /\/ext(\-[a-z\-]+)?\.js$/, + entry, src, state, baseUrl, key, n, origin; + // No check for script definedness because there always should be at least one + Boot.hasReadyState = ("readyState" in script); + Boot.hasAsync = ("async" in script); + Boot.hasDefer = ("defer" in script); + Boot.hasOnLoad = ("onload" in script); + // Feature detecting IE + Boot.isIE8 = Boot.hasReadyState && !Boot.hasAsync && Boot.hasDefer && !Boot.hasOnLoad; + Boot.isIE9 = Boot.hasReadyState && !Boot.hasAsync && Boot.hasDefer && Boot.hasOnLoad; + Boot.isIE10p = Boot.hasReadyState && Boot.hasAsync && Boot.hasDefer && Boot.hasOnLoad; + if (Boot.isIE8) { + Boot.isIE10 = false; + Boot.isIE10m = true; + } else { + Boot.isIE10 = (new Function('/*@cc_on return @_jscript_version @*/')()) === 10; + Boot.isIE10m = Boot.isIE10 || Boot.isIE9 || Boot.isIE8; + } + // IE11 does not support conditional compilation so we detect it by exclusion + Boot.isIE11 = Boot.isIE10p && !Boot.isIE10; + // Since we are loading after other scripts, and we needed to gather them + // anyway, we track them in _scripts so we don't have to ask for them all + // repeatedly. + for (n = 0; n < len; n++) { + src = (script = scriptEls[n]).src; + if (!src) { + + continue; + } + state = script.readyState || null; + // If we find a script file called "ext-*.js", then the base path is that file's base path. + if (!baseUrl && re.test(src)) { + baseUrl = src; + } + if (!Boot.scripts[key = Boot.canonicalUrl(src)]) { + // _debug("creating entry " + key + " in Boot.init"); + entry = new Entry({ + key: key, + url: src, + done: state === null || // non-IE + state === 'loaded' || state === 'complete', + // IE only + el: script, + prop: 'src' + }); + } + } + if (!baseUrl) { + script = scriptEls[scriptEls.length - 1]; + baseUrl = script.src; + } + Boot.baseUrl = baseUrl.substring(0, baseUrl.lastIndexOf('/') + 1); + origin = window.location.origin || window.location.protocol + "//" + window.location.hostname + (window.location.port ? ':' + window.location.port : ''); + Boot.origin = origin; + Boot.detectPlatformTags(); + Ext.filterPlatform = Boot.filterPlatform; + }, + /** + * This method returns a canonical URL for the given URL. + * + * For example, the following all produce the same canonical URL (which is the + * last one): + * + * http://foo.com/bar/baz/zoo/derp/../../goo/Thing.js?_dc=12345 + * http://foo.com/bar/baz/zoo/derp/../../goo/Thing.js + * http://foo.com/bar/baz/zoo/derp/../jazz/../../goo/Thing.js + * http://foo.com/bar/baz/zoo/../goo/Thing.js + * http://foo.com/bar/baz/goo/Thing.js + * + * @private + */ + canonicalUrl: function(url) { + // *WARNING WARNING WARNING* + // This method yields the most correct result we can get but it is EXPENSIVE! + // In ALL browsers! When called multiple times in a sequence, as if when + // we resolve dependencies for entries, it will cause garbage collection events + // and overall painful slowness. This is why we try to avoid it as much as we can. + // + // @TODO - see if we need this fallback logic + // http://stackoverflow.com/questions/470832/getting-an-absolute-url-from-a-relative-one-ie6-issue + resolverEl.href = url; + var ret = resolverEl.href, + dc = _config.disableCachingParam, + pos = dc ? ret.indexOf(dc + '=') : -1, + c, end; + // If we have a _dc query parameter we need to remove it from the canonical + // URL. + if (pos > 0 && ((c = ret.charAt(pos - 1)) === '?' || c === '&')) { + end = ret.indexOf('&', pos); + end = (end < 0) ? '' : ret.substring(end); + if (end && c === '?') { + ++pos; + // keep the '?' + end = end.substring(1); + } + // remove the '&' + ret = ret.substring(0, pos - 1) + end; + } + return ret; + }, + /** + * Get the config value corresponding to the specified name. If no name is given, will return the config object + * @param {String} name The config property name + * @return {Object} + */ + getConfig: function(name) { + return name ? Boot.config[name] : Boot.config; + }, + /** + * Set the configuration. + * @param {Object} config The config object to override the default values. + * @return {Ext.Boot} this + */ + setConfig: function(name, value) { + if (typeof name === 'string') { + Boot.config[name] = value; + } else { + for (var s in name) { + Boot.setConfig(s, name[s]); + } + } + return Boot; + }, + getHead: function() { + return Boot.docHead || (Boot.docHead = doc.head || doc.getElementsByTagName('head')[0]); + }, + create: function(url, key, cfg) { + var config = cfg || {}; + config.url = url; + config.key = key; + return Boot.scripts[key] = new Entry(config); + }, + getEntry: function(url, cfg, canonicalPath) { + var key, entry; + // Canonicalizing URLs via anchor element href yields the most correct result + // but is *extremely* resource heavy so we need to avoid it whenever possible + key = canonicalPath ? url : Boot.canonicalUrl(url); + entry = Boot.scripts[key]; + if (!entry) { + entry = Boot.create(url, key, cfg); + if (canonicalPath) { + entry.canonicalPath = true; + } + } + return entry; + }, + registerContent: function(url, type, content) { + var cfg = { + content: content, + loaded: true, + css: type === 'css' + }; + return Boot.getEntry(url, cfg); + }, + processRequest: function(request, sync) { + request.loadEntries(sync); + }, + load: function(request) { + // _debug("Boot.load called"); + var request = new Request(request); + if (request.sync || Boot.syncMode) { + return Boot.loadSync(request); + } + // If there is a request in progress, we must + // queue this new request to be fired when the current request completes. + if (Boot.currentRequest) { + // _debug("current active request, suspending this request"); + // trigger assignment of entries now to ensure that overlapping + // entries with currently running requests will synchronize state + // with this pending one as they complete + request.getEntries(); + Boot.suspendedQueue.push(request); + } else { + Boot.currentRequest = request; + Boot.processRequest(request, false); + } + return Boot; + }, + loadSync: function(request) { + // _debug("Boot.loadSync called"); + var request = new Request(request); + Boot.syncMode++; + Boot.processRequest(request, true); + Boot.syncMode--; + return Boot; + }, + loadBasePrefix: function(request) { + request = new Request(request); + request.prependBaseUrl = true; + return Boot.load(request); + }, + loadSyncBasePrefix: function(request) { + request = new Request(request); + request.prependBaseUrl = true; + return Boot.loadSync(request); + }, + requestComplete: function(request) { + var next; + if (Boot.currentRequest === request) { + Boot.currentRequest = null; + while (Boot.suspendedQueue.length > 0) { + next = Boot.suspendedQueue.shift(); + if (!next.done) { + // _debug("resuming suspended request"); + Boot.load(next); + break; + } + } + } + if (!Boot.currentRequest && Boot.suspendedQueue.length == 0) { + Boot.fireListeners(); + } + }, + isLoading: function() { + return !Boot.currentRequest && Boot.suspendedQueue.length == 0; + }, + fireListeners: function() { + var listener; + while (Boot.isLoading() && (listener = Boot.listeners.shift())) { + listener(); + } + }, + onBootReady: function(listener) { + if (!Boot.isLoading()) { + listener(); + } else { + Boot.listeners.push(listener); + } + }, + /** + * this is a helper function used by Ext.Loader to flush out + * 'uses' arrays for classes in some Ext versions + */ + getPathsFromIndexes: function(indexMap, loadOrder) { + // In older versions indexMap was an object instead of a sparse array + if (!('length' in indexMap)) { + var indexArray = [], + index; + for (index in indexMap) { + if (!isNaN(+index)) { + indexArray[+index] = indexMap[index]; + } + } + indexMap = indexArray; + } + return Request.prototype.getPathsFromIndexes(indexMap, loadOrder); + }, + createLoadOrderMap: function(loadOrder) { + return Request.prototype.createLoadOrderMap(loadOrder); + }, + fetch: function(url, complete, scope, async) { + async = (async === undefined) ? !!complete : async; + var xhr = new XMLHttpRequest(), + result, status, content, + exception = false, + readyStateChange = function() { + if (xhr && xhr.readyState == 4) { + status = (xhr.status === 1223) ? 204 : (xhr.status === 0 && ((self.location || {}).protocol === 'file:' || (self.location || {}).protocol === 'ionp:')) ? 200 : xhr.status; + content = xhr.responseText; + result = { + content: content, + status: status, + exception: exception + }; + if (complete) { + complete.call(scope, result); + } + xhr.onreadystatechange = emptyFn; + xhr = null; + } + }; + if (async) { + xhr.onreadystatechange = readyStateChange; + } + try { + // _debug("fetching " + url + " " + (async ? "async" : "sync")); + xhr.open('GET', url, async); + xhr.send(null); + } catch (err) { + exception = err; + readyStateChange(); + return result; + } + if (!async) { + readyStateChange(); + } + return result; + }, + notifyAll: function(entry) { + entry.notifyRequests(); + } + }; + function Request(cfg) { + //The request class encapsulates a series of Entry objects + //and provides notification around the completion of all Entries + //in this request. + if (cfg.$isRequest) { + return cfg; + } + var cfg = cfg.url ? cfg : { + url: cfg + }, + url = cfg.url, + urls = url.charAt ? [ + url + ] : url, + charset = cfg.charset || Boot.config.charset; + _apply(this, cfg); + delete this.url; + this.urls = urls; + this.charset = charset; + } + + Request.prototype = { + $isRequest: true, + createLoadOrderMap: function(loadOrder) { + var len = loadOrder.length, + loadOrderMap = {}, + i, element; + for (i = 0; i < len; i++) { + element = loadOrder[i]; + loadOrderMap[element.path] = element; + } + return loadOrderMap; + }, + getLoadIndexes: function(item, indexMap, loadOrder, includeUses, skipLoaded) { + var resolved = [], + queue = [ + item + ], + itemIndex = item.idx, + queue, entry, dependencies, depIndex, i, len; + if (indexMap[itemIndex]) { + // prevent cycles + return resolved; + } + // Both indexMap and resolved are sparse arrays keyed by indexes. + // This gives us a naturally sorted sequence of indexes later on + // when we need to convert them to paths. + // indexMap is the map of all indexes we have visited at least once + // per the current expandUrls() invocation, and resolved is the map + // of all dependencies for the current item that are not included + // in indexMap. + indexMap[itemIndex] = resolved[itemIndex] = true; + while (item = queue.shift()) { + // Canonicalizing URLs is expensive, we try to avoid it + if (item.canonicalPath) { + entry = Boot.getEntry(item.path, null, true); + } else { + entry = Boot.getEntry(this.prepareUrl(item.path)); + } + if (!(skipLoaded && entry.done)) { + if (includeUses && item.uses && item.uses.length) { + dependencies = item.requires.concat(item.uses); + } else { + dependencies = item.requires; + } + for (i = 0 , len = dependencies.length; i < len; i++) { + depIndex = dependencies[i]; + if (!indexMap[depIndex]) { + indexMap[depIndex] = resolved[depIndex] = true; + queue.push(loadOrder[depIndex]); + } + } + } + } + return resolved; + }, + getPathsFromIndexes: function(indexes, loadOrder) { + var paths = [], + index, len; + // indexes is a sparse array with values being true for defined indexes + for (index = 0 , len = indexes.length; index < len; index++) { + if (indexes[index]) { + paths.push(loadOrder[index].path); + } + } + return paths; + }, + expandUrl: function(url, loadOrder, loadOrderMap, indexMap, includeUses, skipLoaded) { + var item, resolved; + if (loadOrder) { + item = loadOrderMap[url]; + if (item) { + resolved = this.getLoadIndexes(item, indexMap, loadOrder, includeUses, skipLoaded); + if (resolved.length) { + return this.getPathsFromIndexes(resolved, loadOrder); + } + } + } + return [ + url + ]; + }, + expandUrls: function(urls, includeUses) { + var me = this, + loadOrder = me.loadOrder, + expanded = [], + expandMap = {}, + indexMap = [], + loadOrderMap, tmpExpanded, i, len, t, tlen, tUrl; + if (typeof urls === "string") { + urls = [ + urls + ]; + } + if (loadOrder) { + loadOrderMap = me.loadOrderMap; + if (!loadOrderMap) { + loadOrderMap = me.loadOrderMap = me.createLoadOrderMap(loadOrder); + } + } + for (i = 0 , len = urls.length; i < len; i++) { + // We don't want to skip loaded entries (last argument === false). + // There are some overrides that get loaded before their respective classes, + // and when the class dependencies are processed we don't want to skip over + // the overrides' dependencies just because they were loaded first. + tmpExpanded = this.expandUrl(urls[i], loadOrder, loadOrderMap, indexMap, includeUses, false); + for (t = 0 , tlen = tmpExpanded.length; t < tlen; t++) { + tUrl = tmpExpanded[t]; + if (!expandMap[tUrl]) { + expandMap[tUrl] = true; + expanded.push(tUrl); + } + } + } + if (expanded.length === 0) { + expanded = urls; + } + return expanded; + }, + expandLoadOrder: function() { + var me = this, + urls = me.urls, + expanded; + if (!me.expanded) { + expanded = this.expandUrls(urls, true); + me.expanded = true; + } else { + expanded = urls; + } + me.urls = expanded; + // if we added some urls to the request to honor the indicated + // load order, the request needs to be sequential + if (urls.length != expanded.length) { + me.sequential = true; + } + return me; + }, + getUrls: function() { + this.expandLoadOrder(); + return this.urls; + }, + prepareUrl: function(url) { + if (this.prependBaseUrl) { + return Boot.baseUrl + url; + } + return url; + }, + getEntries: function() { + var me = this, + entries = me.entries, + loadOrderMap, item, i, entry, urls, url; + if (!entries) { + entries = []; + urls = me.getUrls(); + // If we have loadOrder array then the map will be expanded by now + if (me.loadOrder) { + loadOrderMap = me.loadOrderMap; + } + for (i = 0; i < urls.length; i++) { + url = me.prepareUrl(urls[i]); + if (loadOrderMap) { + item = loadOrderMap[url]; + } + entry = Boot.getEntry(url, { + buster: me.buster, + charset: me.charset + }, item && item.canonicalPath); + entry.requests.push(me); + entries.push(entry); + } + me.entries = entries; + } + return entries; + }, + loadEntries: function(sync) { + var me = this, + entries = me.getEntries(), + len = entries.length, + start = me.loadStart || 0, + continueLoad, entries, entry, i; + if (sync !== undefined) { + me.sync = sync; + } + me.loaded = me.loaded || 0; + me.loading = me.loading || len; + for (i = start; i < len; i++) { + entry = entries[i]; + if (!entry.loaded) { + continueLoad = entries[i].load(me.sync); + } else { + continueLoad = true; + } + if (!continueLoad) { + me.loadStart = i; + entry.onDone(function() { + me.loadEntries(sync); + }); + break; + } + } + me.processLoadedEntries(); + }, + processLoadedEntries: function() { + var me = this, + entries = me.getEntries(), + len = entries.length, + start = me.startIndex || 0, + i, entry; + if (!me.done) { + for (i = start; i < len; i++) { + entry = entries[i]; + if (!entry.loaded) { + me.startIndex = i; + return; + } + if (!entry.evaluated) { + entry.evaluate(); + } + if (entry.error) { + me.error = true; + } + } + me.notify(); + } + }, + notify: function() { + var me = this; + if (!me.done) { + var error = me.error, + fn = me[error ? 'failure' : 'success'], + delay = ('delay' in me) ? me.delay : (error ? 1 : Boot.config.chainDelay), + scope = me.scope || me; + me.done = true; + if (fn) { + if (delay === 0 || delay > 0) { + // Free the stack (and defer the next script) + setTimeout(function() { + fn.call(scope, me); + }, delay); + } else { + fn.call(scope, me); + } + } + me.fireListeners(); + Boot.requestComplete(me); + } + }, + onDone: function(listener) { + var me = this, + listeners = me.listeners || (me.listeners = []); + if (me.done) { + listener(me); + } else { + listeners.push(listener); + } + }, + fireListeners: function() { + var listeners = this.listeners, + listener; + if (listeners) { + // _debug("firing request listeners"); + while ((listener = listeners.shift())) { + listener(this); + } + } + } + }; + function Entry(cfg) { + //The Entry class is a token to manage the load and evaluation + //state of a particular url. It is used to notify all Requests + //interested in this url that the content is available. + if (cfg.$isEntry) { + return cfg; + } + // _debug("creating entry for " + cfg.url); + var charset = cfg.charset || Boot.config.charset, + manifest = Ext.manifest, + loader = manifest && manifest.loader, + cache = (cfg.cache !== undefined) ? cfg.cache : (loader && loader.cache), + buster, busterParam; + if (Boot.config.disableCaching) { + if (cache === undefined) { + cache = !Boot.config.disableCaching; + } + if (cache === false) { + buster = +new Date(); + } else if (cache !== true) { + buster = cache; + } + if (buster) { + busterParam = (loader && loader.cacheParam) || Boot.config.disableCachingParam; + buster = busterParam + "=" + buster; + } + } + _apply(this, cfg); + this.charset = charset; + this.buster = buster; + this.requests = []; + } + + Entry.prototype = { + $isEntry: true, + done: false, + evaluated: false, + loaded: false, + isCrossDomain: function() { + var me = this; + if (me.crossDomain === undefined) { + // _debug("checking " + me.getLoadUrl() + " for prefix " + Boot.origin); + me.crossDomain = (me.getLoadUrl().indexOf(Boot.origin) !== 0); + } + return me.crossDomain; + }, + isCss: function() { + var me = this; + if (me.css === undefined) { + if (me.url) { + var assetConfig = Boot.assetConfig[me.url]; + me.css = assetConfig ? assetConfig.type === "css" : cssRe.test(me.url); + } else { + me.css = false; + } + } + return this.css; + }, + getElement: function(tag) { + var me = this, + el = me.el; + if (!el) { + // _debug("creating element for " + me.url); + if (me.isCss()) { + tag = tag || "link"; + el = doc.createElement(tag); + if (tag == "link") { + el.rel = 'stylesheet'; + me.prop = 'href'; + } else { + me.prop = "textContent"; + } + el.type = "text/css"; + } else { + tag = tag || "script"; + el = doc.createElement(tag); + el.type = 'text/javascript'; + me.prop = 'src'; + if (me.charset) { + el.charset = me.charset; + } + if (Boot.hasAsync) { + el.async = false; + } + } + me.el = el; + } + return el; + }, + getLoadUrl: function() { + var me = this, + url; + url = me.canonicalPath ? me.url : Boot.canonicalUrl(me.url); + if (!me.loadUrl) { + me.loadUrl = !!me.buster ? (url + (url.indexOf('?') === -1 ? '?' : '&') + me.buster) : url; + } + return me.loadUrl; + }, + fetch: function(req) { + var url = this.getLoadUrl(), + async = !!req.async, + complete = req.complete; + Boot.fetch(url, complete, this, async); + }, + onContentLoaded: function(response) { + var me = this, + status = response.status, + content = response.content, + exception = response.exception, + url = this.getLoadUrl(); + me.loaded = true; + if ((exception || status === 0) && !_environment.phantom) { + me.error = ("Failed loading synchronously via XHR: '" + url + "'. It's likely that the file is either being loaded from a " + "different domain or from the local file system where cross " + "origin requests are not allowed for security reasons. Try " + "asynchronous loading instead.") || true; + me.evaluated = true; + } else if ((status >= 200 && status < 300) || status === 304 || _environment.phantom || (status === 0 && content.length > 0)) { + me.content = content; + } else { + me.error = ("Failed loading synchronously via XHR: '" + url + "'. Please verify that the file exists. XHR status code: " + status) || true; + me.evaluated = true; + } + }, + createLoadElement: function(callback) { + var me = this, + el = me.getElement(); + me.preserve = true; + el.onerror = function() { + me.error = true; + if (callback) { + callback(); + callback = null; + } + }; + if (Boot.isIE10m) { + el.onreadystatechange = function() { + if (this.readyState === 'loaded' || this.readyState === 'complete') { + if (callback) { + callback(); + callback = this.onreadystatechange = this.onerror = null; + } + } + }; + } else { + el.onload = function() { + callback(); + callback = this.onload = this.onerror = null; + }; + } + // IE starts loading here + el[me.prop] = me.getLoadUrl(); + }, + onLoadElementReady: function() { + Boot.getHead().appendChild(this.getElement()); + this.evaluated = true; + }, + inject: function(content, asset) { + // _debug("injecting content for " + this.url); + var me = this, + head = Boot.getHead(), + url = me.url, + key = me.key, + base, el, ieMode, basePath; + if (me.isCss()) { + me.preserve = true; + basePath = key.substring(0, key.lastIndexOf("/") + 1); + base = doc.createElement('base'); + base.href = basePath; + if (head.firstChild) { + head.insertBefore(base, head.firstChild); + } else { + head.appendChild(base); + } + // reset the href attribute to cuase IE to pick up the change + base.href = base.href; + if (url) { + content += "\n/*# sourceURL=" + key + " */"; + } + // create element after setting base + el = me.getElement("style"); + ieMode = ('styleSheet' in el); + head.appendChild(base); + if (ieMode) { + head.appendChild(el); + el.styleSheet.cssText = content; + } else { + el.textContent = content; + head.appendChild(el); + } + head.removeChild(base); + } else { + // Debugger friendly, file names are still shown even though they're + // eval'ed code. Breakpoints work on both Firebug and Chrome's Web + // Inspector. + if (url) { + content += "\n//# sourceURL=" + key; + } + Ext.globalEval(content); + } + return me; + }, + loadCrossDomain: function() { + var me = this, + complete = function() { + me.el.onerror = me.el.onload = emptyFn; + me.el = null; + me.loaded = me.evaluated = me.done = true; + me.notifyRequests(); + }; + me.createLoadElement(function() { + complete(); + }); + me.evaluateLoadElement(); + // at this point, we need sequential evaluation, + // which means we can't advance the load until + // this entry has fully completed + return false; + }, + loadElement: function() { + var me = this, + complete = function() { + me.el.onerror = me.el.onload = emptyFn; + me.el = null; + me.loaded = me.evaluated = me.done = true; + me.notifyRequests(); + }; + me.createLoadElement(function() { + complete(); + }); + me.evaluateLoadElement(); + return true; + }, + loadSync: function() { + var me = this; + me.fetch({ + async: false, + complete: function(response) { + me.onContentLoaded(response); + } + }); + me.evaluate(); + me.notifyRequests(); + }, + load: function(sync) { + var me = this; + if (!me.loaded) { + if (me.loading) { + // if we're calling back through load and we're loading but haven't + // yet loaded, then we should be in a sequential, cross domain + // load scenario which means we can't continue the load on the + // request until this entry has fully evaluated, which will mean + // loaded = evaluated = done = true in one step. For css files, this + // will happen immediately upon element creation / insertion, + // but + * + * + * + * Refer to config options of {@link Ext.Loader} for the list of possible properties + * + * @param {Object} config The config object to override the default values + * @return {Ext.Loader} this + */ + setConfig: Ext.Function.flexSetter(function(name, value) { + if (name === 'paths') { + Loader.setPath(value); + } else { + _config[name] = value; + var delegated = delegatedConfigs[name]; + if (delegated) { + Boot.setConfig((delegated === true) ? name : delegated, value); + } + } + return Loader; + }), + /** + * Get the config value corresponding to the specified name. If no name is given, + * will return the config object + * + * @param {String} name The config property name + * @return {Object} + */ + getConfig: function(name) { + return name ? _config[name] : _config; + }, + /** + * Sets the path of a namespace. + * For Example: + * + * Ext.Loader.setPath('Ext', '.'); + * + * @param {String/Object} name See {@link Ext.Function#flexSetter flexSetter} + * @param {String} [path] See {@link Ext.Function#flexSetter flexSetter} + * @return {Ext.Loader} this + * @method + */ + setPath: function() { + // Paths are an Ext.Inventory thing and ClassManager is an instance of that: + Manager.setPath.apply(Manager, arguments); + return Loader; + }, + /** + * Sets a batch of path entries + * + * @param {Object} paths a set of className: path mappings + * @return {Ext.Loader} this + */ + addClassPathMappings: function(paths) { + // Paths are an Ext.Inventory thing and ClassManager is an instance of that: + Manager.setPath(paths); + return Loader; + }, + /** + * fixes up loader path configs by prepending Ext.Boot#baseUrl to the beginning + * of the path, then delegates to Ext.Loader#addClassPathMappings + * @param pathConfig + */ + addBaseUrlClassPathMappings: function(pathConfig) { + for (var name in pathConfig) { + pathConfig[name] = Boot.baseUrl + pathConfig[name]; + } + Ext.Loader.addClassPathMappings(pathConfig); + }, + /** + * Translates a className to a file path by adding the + * the proper prefix and converting the .'s to /'s. For example: + * + * Ext.Loader.setPath('My', '/path/to/My'); + * + * alert(Ext.Loader.getPath('My.awesome.Class')); // alerts '/path/to/My/awesome/Class.js' + * + * Note that the deeper namespace levels, if explicitly set, are always resolved first. + * For example: + * + * Ext.Loader.setPath({ + * 'My': '/path/to/lib', + * 'My.awesome': '/other/path/for/awesome/stuff', + * 'My.awesome.more': '/more/awesome/path' + * }); + * + * alert(Ext.Loader.getPath('My.awesome.Class')); // alerts '/other/path/for/awesome/stuff/Class.js' + * + * alert(Ext.Loader.getPath('My.awesome.more.Class')); // alerts '/more/awesome/path/Class.js' + * + * alert(Ext.Loader.getPath('My.cool.Class')); // alerts '/path/to/lib/cool/Class.js' + * + * alert(Ext.Loader.getPath('Unknown.strange.Stuff')); // alerts 'Unknown/strange/Stuff.js' + * + * @param {String} className + * @return {String} path + */ + getPath: function(className) { + // Paths are an Ext.Inventory thing and ClassManager is an instance of that: + return Manager.getPath(className); + }, + require: function(expressions, fn, scope, excludes) { + if (excludes) { + return Loader.exclude(excludes).require(expressions, fn, scope); + } + var classNames = Manager.getNamesByExpression(expressions); + return Loader.load(classNames, fn, scope); + }, + syncRequire: function() { + var wasEnabled = Loader.syncModeEnabled; + Loader.syncModeEnabled = true; + var ret = Loader.require.apply(Loader, arguments); + Loader.syncModeEnabled = wasEnabled; + return ret; + }, + exclude: function(excludes) { + var selector = Manager.select({ + require: function(classNames, fn, scope) { + return Loader.load(classNames, fn, scope); + }, + syncRequire: function(classNames, fn, scope) { + var wasEnabled = Loader.syncModeEnabled; + Loader.syncModeEnabled = true; + var ret = Loader.load(classNames, fn, scope); + Loader.syncModeEnabled = wasEnabled; + return ret; + } + }); + selector.exclude(excludes); + return selector; + }, + load: function(classNames, callback, scope) { + if (callback) { + if (callback.length) { + // If callback expects arguments, shim it with a function that will map + // the requires class(es) from the names we are given. + callback = Loader.makeLoadCallback(classNames, callback); + } + callback = callback.bind(scope || Ext.global); + } + var state = Manager.classState, + missingClassNames = [], + urls = [], + urlByClass = {}, + numClasses = classNames.length, + url, className, i, numMissing; + for (i = 0; i < numClasses; ++i) { + className = Manager.resolveName(classNames[i]); + if (!Manager.isCreated(className)) { + missingClassNames.push(className); + if (!state[className]) { + urlByClass[className] = Loader.getPath(className); + urls.push(urlByClass[className]); + } + } + } + // If the dynamic dependency feature is not being used, throw an error + // if the dependencies are not defined + numMissing = missingClassNames.length; + if (numMissing) { + Loader.missingCount += numMissing; + Manager.onCreated(function() { + if (callback) { + Ext.callback(callback, scope, arguments); + } + Loader.checkReady(); + }, Loader, missingClassNames); + if (!_config.enabled) { + Ext.raise("Ext.Loader is not enabled, so dependencies cannot be resolved dynamically. " + "Missing required class" + ((missingClassNames.length > 1) ? "es" : "") + ": " + missingClassNames.join(', ')); + } + if (urls.length) { + Loader.loadScripts({ + url: urls, + // scope will be this options object so we can pass these along: + _classNames: missingClassNames, + _urlByClass: urlByClass + }); + } else { + // need to call checkReady here, as the _missingCoun + // may have transitioned from 0 to > 0, meaning we + // need to block ready + Loader.checkReady(); + } + } else { + if (callback) { + callback.call(scope); + } + // need to call checkReady here, as the _missingCoun + // may have transitioned from 0 to > 0, meaning we + // need to block ready + Loader.checkReady(); + } + if (Loader.syncModeEnabled) { + // Class may have been just loaded or was already loaded + if (numClasses === 1) { + return Manager.get(classNames[0]); + } + } + return Loader; + }, + makeLoadCallback: function(classNames, callback) { + return function() { + var classes = [], + i = classNames.length; + while (i-- > 0) { + classes[i] = Manager.get(classNames[i]); + } + return callback.apply(this, classes); + }; + }, + onLoadFailure: function(request) { + var options = this, + entries = request.entries || [], + onError = options.onError, + error, entry, i; + Loader.hasFileLoadError = true; + --Loader.scriptsLoading; + if (onError) { + for (i = 0; i < entries.length; i++) { + entry = entries[i]; + if (entry.error) { + error = new Error('Failed to load: ' + entry.url); + break; + } + } + error = error || new Error('Failed to load'); + onError.call(options.userScope, options, error, request); + } else { + Ext.log.error("[Ext.Loader] Some requested files failed to load."); + } + Loader.checkReady(); + }, + onLoadSuccess: function() { + var options = this, + onLoad = options.onLoad, + classNames = options._classNames, + urlByClass = options._urlByClass, + state = Manager.classState, + missingQueue = Loader.missingQueue, + className, i, len; + --Loader.scriptsLoading; + if (onLoad) { + //TODO: need an adapter to convert to v4 onLoad signatures + onLoad.call(options.userScope, options); + } + // onLoad can cause more loads to start, so it must run first + // classNames is the array of *all* classes that load() was asked to load, + // including those that might have been already loaded but not yet created. + // urlByClass is a map of only those classes that we asked Boot to load. + for (i = 0 , len = classNames.length; i < len; i++) { + className = classNames[i]; + // When a script is loaded and executed, we should have Ext.define() called + // for at least one of the classes in the list, which will set the state + // for that class. That by itself does not mean that the class is available + // *now* but it means that ClassManager is tracking it and will fire the + // onCreated callback that we set back in load(). + // However if there is no state for the class, that may mean two things: + // either it is not a Ext class, or it is truly missing. In any case we need + // to watch for that thing ourselves, which we will do every checkReady(). + if (!state[className]) { + missingQueue[className] = urlByClass[className]; + } + } + Loader.checkReady(); + }, + // TODO: this timing of this needs to be deferred until all classes have had + // a chance to be created + reportMissingClasses: function() { + if (!Loader.syncModeEnabled && !Loader.scriptsLoading && Loader.isLoading && !Loader.hasFileLoadError) { + var missingQueue = Loader.missingQueue, + missingClasses = [], + missingPaths = []; + for (var missingClassName in missingQueue) { + missingClasses.push(missingClassName); + missingPaths.push(missingQueue[missingClassName]); + } + if (missingClasses.length) { + throw new Error("The following classes are not declared even if their files have been " + "loaded: '" + missingClasses.join("', '") + "'. Please check the source code of their " + "corresponding files for possible typos: '" + missingPaths.join("', '")); + } + } + }, + /** + * Add a new listener to be executed when all required scripts are fully loaded + * + * @param {Function} fn The function callback to be executed + * @param {Object} scope The execution scope (`this`) of the callback function. + * @param {Boolean} [withDomReady=true] Pass `false` to not also wait for document + * dom ready. + * @param {Object} [options] Additional callback options. + * @param {Number} [options.delay=0] A number of milliseconds to delay. + * @param {Number} [options.priority=0] Relative priority of this callback. Negative + * numbers are reserved. + */ + onReady: function(fn, scope, withDomReady, options) { + if (withDomReady) { + Ready.on(fn, scope, options); + } else { + var listener = Ready.makeListener(fn, scope, options); + if (Loader.isLoading) { + readyListeners.push(listener); + } else { + Ready.invoke(listener); + } + } + }, + /** + * @private + * Ensure that any classes referenced in the `uses` property are loaded. + */ + addUsedClasses: function(classes) { + var cls, i, ln; + if (classes) { + classes = (typeof classes === 'string') ? [ + classes + ] : classes; + for (i = 0 , ln = classes.length; i < ln; i++) { + cls = classes[i]; + if (typeof cls === 'string' && !Ext.Array.contains(usedClasses, cls)) { + usedClasses.push(cls); + } + } + } + return Loader; + }, + /** + * @private + */ + triggerReady: function() { + var listener, + refClasses = usedClasses; + if (Loader.isLoading && refClasses.length) { + // Empty the array to eliminate potential recursive loop issue + usedClasses = []; + // this may immediately call us back if all 'uses' classes + // have been loaded + Loader.require(refClasses); + } else { + // Must clear this before calling callbacks. This will cause any new loads + // to call Ready.block() again. See below for more on this. + Loader.isLoading = false; + // These listeners are just those attached directly to Loader to wait for + // class loading only. + readyListeners.sort(Ready.sortFn); + // this method can be called with Loader.isLoading either true or false + // (can be called with false when all 'uses' classes are already loaded) + // this may bypass the above if condition + while (readyListeners.length && !Loader.isLoading) { + // we may re-enter triggerReady so we cannot necessarily iterate the + // readyListeners array + listener = readyListeners.pop(); + Ready.invoke(listener); + } + // If the DOM is also ready, this will fire the normal onReady listeners. + // An astute observer would note that we may now be back to isLoading and + // so ask "Why you call unblock?". The reason is that we must match the + // calls to block and since we transitioned from isLoading to !isLoading + // here we must call unblock. If we have transitioned back to isLoading in + // the above loop it will have called block again so the counter will be + // increased and this call will not reduce the block count to 0. This is + // done by loadScripts. + Ready.unblock(); + } + }, + /** + * @private + * @param {String} className + */ + historyPush: function(className) { + if (className && !isInHistory[className] && !Manager.overrideMap[className]) { + isInHistory[className] = true; + history.push(className); + } + return Loader; + }, + /** + * This is an internal method that delegate content loading to the + * bootstrap layer. + * @private + * @param params + */ + loadScripts: function(params) { + var manifest = Ext.manifest, + loadOrder = manifest && manifest.loadOrder, + loadOrderMap = manifest && manifest.loadOrderMap, + options; + ++Loader.scriptsLoading; + // if the load order map hasn't been created, create it now + // and cache on the manifest + if (loadOrder && !loadOrderMap) { + manifest.loadOrderMap = loadOrderMap = Boot.createLoadOrderMap(loadOrder); + } + // verify the loading state, as this may have transitioned us from + // not loading to loading + Loader.checkReady(); + options = Ext.apply({ + loadOrder: loadOrder, + loadOrderMap: loadOrderMap, + charset: _config.scriptCharset, + success: Loader.onLoadSuccess, + failure: Loader.onLoadFailure, + sync: Loader.syncModeEnabled, + _classNames: [] + }, params); + options.userScope = options.scope; + options.scope = options; + Boot.load(options); + }, + /** + * This method is provide for use by the bootstrap layer. + * @private + * @param {String[]} urls + */ + loadScriptsSync: function(urls) { + var syncwas = Loader.syncModeEnabled; + Loader.syncModeEnabled = true; + Loader.loadScripts({ + url: urls + }); + Loader.syncModeEnabled = syncwas; + }, + /** + * This method is provide for use by the bootstrap layer. + * @private + * @param {String[]} urls + */ + loadScriptsSyncBasePrefix: function(urls) { + var syncwas = Loader.syncModeEnabled; + Loader.syncModeEnabled = true; + Loader.loadScripts({ + url: urls, + prependBaseUrl: true + }); + Loader.syncModeEnabled = syncwas; + }, + /** + * Loads the specified script URL and calls the supplied callbacks. If this method + * is called before {@link Ext#isReady}, the script's load will delay the transition + * to ready. This can be used to load arbitrary scripts that may contain further + * {@link Ext#require Ext.require} calls. + * + * @param {Object/String/String[]} options The options object or simply the URL(s) to load. + * @param {String} options.url The URL from which to load the script. + * @param {Function} [options.onLoad] The callback to call on successful load. + * @param {Function} [options.onError] The callback to call on failure to load. + * @param {Object} [options.scope] The scope (`this`) for the supplied callbacks. + */ + loadScript: function(options) { + var isString = typeof options === 'string', + isArray = options instanceof Array, + isObject = !isArray && !isString, + url = isObject ? options.url : options, + onError = isObject && options.onError, + onLoad = isObject && options.onLoad, + scope = isObject && options.scope, + request = { + url: url, + scope: scope, + onLoad: onLoad, + onError: onError, + _classNames: [] + }; + Loader.loadScripts(request); + }, + /** + * @private + */ + checkMissingQueue: function() { + var missingQueue = Loader.missingQueue, + newQueue = {}, + name, + missing = 0; + for (name in missingQueue) { + // If class state is available for the name, that means ClassManager + // is tracking it and will fire callback when it is created. + // We only need to track non-class things in the Loader. + if (!(Manager.classState[name] || Manager.isCreated(name))) { + newQueue[name] = missingQueue[name]; + missing++; + } + } + Loader.missingCount = missing; + Loader.missingQueue = newQueue; + }, + /** + * @private + */ + checkReady: function() { + var wasLoading = Loader.isLoading, + isLoading; + Loader.checkMissingQueue(); + isLoading = Loader.missingCount + Loader.scriptsLoading; + if (isLoading && !wasLoading) { + Ready.block(); + Loader.isLoading = !!isLoading; + } else if (!isLoading && wasLoading) { + Loader.triggerReady(); + } + if (!Loader.scriptsLoading && Loader.missingCount) { + // Things look bad, but since load requests may come later, defer this + // for a bit then check if things are still stuck. + Ext.defer(function() { + if (!Loader.scriptsLoading && Loader.missingCount) { + Ext.log.error('[Loader] The following classes failed to load:'); + for (var name in Loader.missingQueue) { + Ext.log.error('[Loader] ' + name + ' from ' + Loader.missingQueue[name]); + } + } + }, 1000); + } + } + }); + /** + * Loads all classes by the given names and all their direct dependencies; optionally + * executes the given callback function when finishes, within the optional scope. + * + * @param {String/String[]} expressions The class, classes or wildcards to load. + * @param {Function} [fn] The callback function. + * @param {Object} [scope] The execution scope (`this`) of the callback function. + * @member Ext + * @method require + */ + Ext.require = alias(Loader, 'require'); + /** + * Synchronously loads all classes by the given names and all their direct dependencies; optionally + * executes the given callback function when finishes, within the optional scope. + * + * @param {String/String[]} expressions The class, classes or wildcards to load. + * @param {Function} [fn] The callback function. + * @param {Object} [scope] The execution scope (`this`) of the callback function. + * @member Ext + * @method syncRequire + */ + Ext.syncRequire = alias(Loader, 'syncRequire'); + /** + * Explicitly exclude files from being loaded. Useful when used in conjunction with a + * broad include expression. Can be chained with more `require` and `exclude` methods, + * for example: + * + * Ext.exclude('Ext.data.*').require('*'); + * + * Ext.exclude('widget.button*').require('widget.*'); + * + * @param {String/String[]} excludes + * @return {Object} Contains `exclude`, `require` and `syncRequire` methods for chaining. + * @member Ext + * @method exclude + */ + Ext.exclude = alias(Loader, 'exclude'); + /** + * @cfg {String[]} requires + * @member Ext.Class + * List of classes that have to be loaded before instantiating this class. + * For example: + * + * Ext.define('Mother', { + * requires: ['Child'], + * giveBirth: function() { + * // we can be sure that child class is available. + * return new Child(); + * } + * }); + */ + Class.registerPreprocessor('loader', function(cls, data, hooks, continueFn) { + Ext.classSystemMonitor && Ext.classSystemMonitor(cls, 'Ext.Loader#loaderPreprocessor', arguments); + // jshint ignore:line + var me = this, + dependencies = [], + dependency, + className = Manager.getName(cls), + i, j, ln, subLn, value, propertyName, propertyValue, requiredMap; + /* + Loop through the dependencyProperties, look for string class names and push + them into a stack, regardless of whether the property's value is a string, array or object. For example: + { + extend: 'Ext.MyClass', + requires: ['Ext.some.OtherClass'], + mixins: { + thing: 'Foo.bar.Thing'; + } + } + which will later be transformed into: + { + extend: Ext.MyClass, + requires: [Ext.some.OtherClass], + mixins: { + thing: Foo.bar.Thing; + } + } + */ + for (i = 0 , ln = dependencyProperties.length; i < ln; i++) { + propertyName = dependencyProperties[i]; + if (data.hasOwnProperty(propertyName)) { + propertyValue = data[propertyName]; + if (typeof propertyValue === 'string') { + dependencies.push(propertyValue); + } else if (propertyValue instanceof Array) { + for (j = 0 , subLn = propertyValue.length; j < subLn; j++) { + value = propertyValue[j]; + if (typeof value === 'string') { + dependencies.push(value); + } + } + } else if (typeof propertyValue !== 'function') { + for (j in propertyValue) { + if (propertyValue.hasOwnProperty(j)) { + value = propertyValue[j]; + if (typeof value === 'string') { + dependencies.push(value); + } + } + } + } + } + } + if (dependencies.length === 0) { + return; + } + if (className) { + _requiresMap[className] = dependencies; + } + var manifestClasses = Ext.manifest && Ext.manifest.classes, + deadlockPath = [], + detectDeadlock; + /* + * Automatically detect deadlocks before-hand, + * will throw an error with detailed path for ease of debugging. Examples + * of deadlock cases: + * + * - A extends B, then B extends A + * - A requires B, B requires C, then C requires A + * + * The detectDeadlock function will recursively transverse till the leaf, hence + * it can detect deadlocks no matter how deep the path is. However we don't need + * to run this check if the class name is in the manifest: that means Cmd has + * already resolved all dependencies for this class with no deadlocks. + */ + if (className && (!manifestClasses || !manifestClasses[className])) { + requiredMap = Loader.requiredByMap || (Loader.requiredByMap = {}); + for (i = 0 , ln = dependencies.length; i < ln; i++) { + dependency = dependencies[i]; + (requiredMap[dependency] || (requiredMap[dependency] = [])).push(className); + } + detectDeadlock = function(cls) { + deadlockPath.push(cls); + var requires = _requiresMap[cls], + dep, i, ln; + if (requires) { + if (Ext.Array.contains(requires, className)) { + Ext.Error.raise("Circular requirement detected! '" + className + "' and '" + deadlockPath[1] + "' mutually require each other. Path: " + deadlockPath.join(' -> ') + " -> " + deadlockPath[0]); + } + for (i = 0 , ln = requires.length; i < ln; i++) { + dep = requires[i]; + if (!isInHistory[dep]) { + detectDeadlock(requires[i]); + } + } + } + }; + detectDeadlock(className); + } + (className ? Loader.exclude(className) : Loader).require(dependencies, function() { + for (i = 0 , ln = dependencyProperties.length; i < ln; i++) { + propertyName = dependencyProperties[i]; + if (data.hasOwnProperty(propertyName)) { + propertyValue = data[propertyName]; + if (typeof propertyValue === 'string') { + data[propertyName] = Manager.get(propertyValue); + } else if (propertyValue instanceof Array) { + for (j = 0 , subLn = propertyValue.length; j < subLn; j++) { + value = propertyValue[j]; + if (typeof value === 'string') { + data[propertyName][j] = Manager.get(value); + } + } + } else if (typeof propertyValue !== 'function') { + for (var k in propertyValue) { + if (propertyValue.hasOwnProperty(k)) { + value = propertyValue[k]; + if (typeof value === 'string') { + data[propertyName][k] = Manager.get(value); + } + } + } + } + } + } + continueFn.call(me, cls, data, hooks); + }); + return false; + }, true, 'after', 'className'); + /** + * @cfg {String[]} uses + * @member Ext.Class + * List of optional classes to load together with this class. These aren't neccessarily loaded before + * this class is created, but are guaranteed to be available before Ext.onReady listeners are + * invoked. For example: + * + * Ext.define('Mother', { + * uses: ['Child'], + * giveBirth: function() { + * // This code might, or might not work: + * // return new Child(); + * + * // Instead use Ext.create() to load the class at the spot if not loaded already: + * return Ext.create('Child'); + * } + * }); + */ + Manager.registerPostprocessor('uses', function(name, cls, data) { + Ext.classSystemMonitor && Ext.classSystemMonitor(cls, 'Ext.Loader#usesPostprocessor', arguments); + // jshint ignore:line + var uses = data.uses, + classNames; + if (uses) { + classNames = Manager.getNamesByExpression(data.uses); + Loader.addUsedClasses(classNames); + } + }); + Manager.onCreated(Loader.historyPush); + Loader.init(); +}()); +//----------------------------------------------------------------------------- +// Use performance.now when available to keep timestamps consistent. +Ext._endTime = Ext.ticks(); +// This hook is to allow tools like DynaTrace to deterministically detect the availability +// of Ext.onReady. Since Loader takes over Ext.onReady this must be done here and not in +// Ext.env.Ready. +if (Ext._beforereadyhandler) { + Ext._beforereadyhandler(); +} + +/** + * This class is a base class for mixins. These are classes that extend this class and are + * designed to be used as a `mixin` by user code. + * + * It provides mixins with the ability to "hook" class methods of the classes in to which + * they are mixed. For example, consider the `destroy` method pattern. If a mixin class + * had cleanup requirements, it would need to be called as part of `destroy`. + * + * Starting with a basic class we might have: + * + * Ext.define('Foo.bar.Base', { + * destroy: function () { + * console.log('B'); + * // cleanup + * } + * }); + * + * A derived class would look like this: + * + * Ext.define('Foo.bar.Derived', { + * extend: 'Foo.bar.Base', + * + * destroy: function () { + * console.log('D'); + * // more cleanup + * + * this.callParent(); // let Foo.bar.Base cleanup as well + * } + * }); + * + * To see how using this class help, start with a "normal" mixin class that also needs to + * cleanup its resources. These mixins must be called explicitly by the classes that use + * them. For example: + * + * Ext.define('Foo.bar.Util', { + * destroy: function () { + * console.log('U'); + * } + * }); + * + * Ext.define('Foo.bar.Derived', { + * extend: 'Foo.bar.Base', + * + * mixins: { + * util: 'Foo.bar.Util' + * }, + * + * destroy: function () { + * console.log('D'); + * // more cleanup + * + * this.mixins.util.destroy.call(this); + * + * this.callParent(); // let Foo.bar.Base cleanup as well + * } + * }); + * + * var obj = new Foo.bar.Derived(); + * + * obj.destroy(); + * // logs D then U then B + * + * This class is designed to solve the above in simpler and more reliable way. + * + * ## mixinConfig + * + * Using `mixinConfig` the mixin class can provide "before" or "after" hooks that do not + * involve the derived class implementation. This also means the derived class cannot + * adjust parameters to the hook methods. + * + * Ext.define('Foo.bar.Util', { + * extend: 'Ext.Mixin', + * + * mixinConfig: { + * after: { + * destroy: 'destroyUtil' + * } + * }, + * + * destroyUtil: function () { + * console.log('U'); + * } + * }); + * + * Ext.define('Foo.bar.Class', { + * mixins: { + * util: 'Foo.bar.Util' + * }, + * + * destroy: function () { + * console.log('D'); + * } + * }); + * + * var obj = new Foo.bar.Derived(); + * + * obj.destroy(); + * // logs D then U + * + * If the destruction should occur in the other order, you can use `before`: + * + * Ext.define('Foo.bar.Util', { + * extend: 'Ext.Mixin', + * + * mixinConfig: { + * before: { + * destroy: 'destroyUtil' + * } + * }, + * + * destroyUtil: function () { + * console.log('U'); + * } + * }); + * + * Ext.define('Foo.bar.Class', { + * mixins: { + * util: 'Foo.bar.Util' + * }, + * + * destroy: function () { + * console.log('D'); + * } + * }); + * + * var obj = new Foo.bar.Derived(); + * + * obj.destroy(); + * // logs U then D + * + * ### Chaining + * + * One way for a mixin to provide methods that act more like normal inherited methods is + * to use an `on` declaration. These methods will be injected into the `callParent` chain + * between the derived and superclass. For example: + * + * Ext.define('Foo.bar.Util', { + * extend: 'Ext.Mixin', + * + * mixinConfig: { + * on: { + * destroy: function () { + * console.log('M'); + * } + * } + * } + * }); + * + * Ext.define('Foo.bar.Base', { + * destroy: function () { + * console.log('B'); + * } + * }); + * + * Ext.define('Foo.bar.Derived', { + * extend: 'Foo.bar.Base', + * + * mixins: { + * util: 'Foo.bar.Util' + * }, + * + * destroy: function () { + * this.callParent(); + * console.log('D'); + * } + * }); + * + * var obj = new Foo.bar.Derived(); + * + * obj.destroy(); + * // logs M then B then D + * + * As with `before` and `after`, the value of `on` can be a method name. + * + * Ext.define('Foo.bar.Util', { + * extend: 'Ext.Mixin', + * + * mixinConfig: { + * on: { + * destroy: 'onDestroy' + * } + * } + * + * onDestroy: function () { + * console.log('M'); + * } + * }); + * + * Because this technique leverages `callParent`, the derived class controls the time and + * parameters for the call to all of its bases (be they `extend` or `mixin` flavor). + * + * ### Derivations + * + * Some mixins need to process class extensions of their target class. To do this you can + * define an `extended` method like so: + * + * Ext.define('Foo.bar.Util', { + * extend: 'Ext.Mixin', + * + * mixinConfig: { + * extended: function (baseClass, derivedClass, classBody) { + * // This function is called whenever a new "derivedClass" is created + * // that extends a "baseClass" in to which this mixin was mixed. + * } + * } + * }); + * + * @protected + */ +Ext.define('Ext.Mixin', function(Mixin) { + return { + statics: { + addHook: function(hookFn, targetClass, methodName, mixinClassPrototype) { + var isFunc = Ext.isFunction(hookFn), + hook = function() { + var a = arguments, + fn = isFunc ? hookFn : mixinClassPrototype[hookFn], + result = this.callParent(a); + fn.apply(this, a); + return result; + }, + existingFn = targetClass.hasOwnProperty(methodName) && targetClass[methodName]; + if (isFunc) { + hookFn.$previous = Ext.emptyFn; + } + // no callParent for these guys + hook.$name = methodName; + hook.$owner = targetClass.self; + if (existingFn) { + hook.$previous = existingFn.$previous; + existingFn.$previous = hook; + } else { + targetClass[methodName] = hook; + } + } + }, + onClassExtended: function(cls, data) { + var mixinConfig = data.mixinConfig, + hooks = data.xhooks, + superclass = cls.superclass, + onClassMixedIn = data.onClassMixedIn, + parentMixinConfig, befores, afters, extended; + if (hooks) { + // Legacy way + delete data.xhooks; + (mixinConfig || (data.mixinConfig = mixinConfig = {})).on = hooks; + } + if (mixinConfig) { + parentMixinConfig = superclass.mixinConfig; + if (parentMixinConfig) { + data.mixinConfig = mixinConfig = Ext.merge({}, parentMixinConfig, mixinConfig); + } + data.mixinId = mixinConfig.id; + if (mixinConfig.beforeHooks) { + Ext.raise('Use of "beforeHooks" is deprecated - use "before" instead'); + } + if (mixinConfig.hooks) { + Ext.raise('Use of "hooks" is deprecated - use "after" instead'); + } + if (mixinConfig.afterHooks) { + Ext.raise('Use of "afterHooks" is deprecated - use "after" instead'); + } + befores = mixinConfig.before; + afters = mixinConfig.after; + hooks = mixinConfig.on; + extended = mixinConfig.extended; + } + if (befores || afters || hooks || extended) { + // Note: tests are with Ext.Class + data.onClassMixedIn = function(targetClass) { + var mixin = this.prototype, + targetProto = targetClass.prototype, + key; + if (befores) { + Ext.Object.each(befores, function(key, value) { + targetClass.addMember(key, function() { + if (mixin[value].apply(this, arguments) !== false) { + return this.callParent(arguments); + } + }); + }); + } + if (afters) { + Ext.Object.each(afters, function(key, value) { + targetClass.addMember(key, function() { + var ret = this.callParent(arguments); + mixin[value].apply(this, arguments); + return ret; + }); + }); + } + if (hooks) { + for (key in hooks) { + Mixin.addHook(hooks[key], targetProto, key, mixin); + } + } + if (extended) { + targetClass.onExtended(function() { + var args = Ext.Array.slice(arguments, 0); + args.unshift(targetClass); + return extended.apply(this, args); + }, this); + } + if (onClassMixedIn) { + onClassMixedIn.apply(this, arguments); + } + }; + } + } + }; +}); + +// @tag core +/** + * @class Ext.util.DelayedTask + * + * The DelayedTask class provides a convenient way to "buffer" the execution of a method, + * performing setTimeout where a new timeout cancels the old timeout. When called, the + * task will wait the specified time period before executing. If durng that time period, + * the task is called again, the original call will be cancelled. This continues so that + * the function is only called a single time for each iteration. + * + * This method is especially useful for things like detecting whether a user has finished + * typing in a text field. An example would be performing validation on a keypress. You can + * use this class to buffer the keypress events for a certain number of milliseconds, and + * perform only if they stop for that amount of time. + * + * ## Usage + * + * var task = new Ext.util.DelayedTask(function(){ + * alert(Ext.getDom('myInputField').value.length); + * }); + * + * // Wait 500ms before calling our function. If the user presses another key + * // during that 500ms, it will be cancelled and we'll wait another 500ms. + * Ext.get('myInputField').on('keypress', function() { + * task.delay(500); + * }); + * + * Note that we are using a DelayedTask here to illustrate a point. The configuration + * option `buffer` for {@link Ext.util.Observable#addListener addListener/on} will + * also setup a delayed task for you to buffer events. + * + * @constructor The parameters to this constructor serve as defaults and are not required. + * @param {Function} [fn] The default function to call. If not specified here, it must be specified during the {@link #delay} call. + * @param {Object} [scope] The default scope (The **`this`** reference) in which the + * function is called. If not specified, `this` will refer to the browser window. + * @param {Array} [args] The default Array of arguments. + * @param {Boolean} [cancelOnDelay=true] By default, each call to {@link #delay} cancels any pending invocation and reschedules a new + * invocation. Specifying this as `false` means that calls to {@link #delay} when an invocation is pending just update the call settings, + * `newDelay`, `newFn`, `newScope` or `newArgs`, whichever are passed. + */ +Ext.util = Ext.util || {}; +Ext.util.DelayedTask = function(fn, scope, args, cancelOnDelay, fireIdleEvent) { + // @define Ext.util.DelayedTask + // @uses Ext.GlobalEvents + var me = this, + delay, + call = function() { + me.id = null; + if (!(scope && scope.destroyed)) { + args ? fn.apply(scope, args) : fn.call(scope); + } + if (fireIdleEvent === false) { + Ext._suppressIdle = true; + } + }; + // DelayedTask can be called with no function upfront + if (fn) { + call.$origFn = fn.$origFn || fn; + call.$skipTimerCheck = call.$origFn.$skipTimerCheck; + } + cancelOnDelay = typeof cancelOnDelay === 'boolean' ? cancelOnDelay : true; + /** + * @property {Number} id + * The id of the currently pending invocation. Will be set to `null` if there is no + * invocation pending. + */ + me.id = null; + /** + * @method delay + * By default, cancels any pending timeout and queues a new one. + * + * If the `cancelOnDelay` parameter was specified as `false` in the constructor, this does not cancel and + * reschedule, but just updates the call settings, `newDelay`, `newFn`, `newScope` or `newArgs`, whichever are passed. + * + * @param {Number} newDelay The milliseconds to delay. `-1` means schedule for the next animation frame if supported. + * @param {Function} [newFn] Overrides function passed to constructor + * @param {Object} [newScope] Overrides scope passed to constructor. Remember that if no scope + * is specified, `this` will refer to the browser window. + * @param {Array} [newArgs] Overrides args passed to constructor + * @return {Number} The timer id being used. + */ + me.delay = function(newDelay, newFn, newScope, newArgs) { + if (cancelOnDelay) { + me.cancel(); + } + if (typeof newDelay === 'number') { + delay = newDelay; + } + fn = newFn || fn; + scope = newScope || scope; + args = newArgs || args; + me.delayTime = delay; + if (fn) { + call.$origFn = fn.$origFn || fn; + call.$skipTimerCheck = call.$origFn.$skipTimerCheck; + } + if (!me.id) { + if (delay === -1) { + me.id = Ext.raf(call); + } else { + me.id = Ext.defer(call, delay || 1); + } + } + // 0 == immediate call + return me.id; + }; + /** + * Cancel the last queued timeout + */ + me.cancel = function() { + if (me.id) { + if (me.delayTime === -1) { + Ext.unraf(me.id); + } else { + Ext.undefer(me.id); + } + me.id = null; + } + }; + me.flush = function() { + if (me.id) { + me.cancel(); + // we're not running on our own timer so don't mess with whatever thread + // is calling us... + var was = fireIdleEvent; + fireIdleEvent = true; + call(); + fireIdleEvent = was; + } + }; + /** + * @private + * Cancel the timeout if it was set for the specified fn and scope. + */ + me.stop = function(stopFn, stopScope) { + // This kludginess is here because Classic components use shared focus task + // and we need to be sure the task's current timeout was set for that + // particular component before we can safely cancel it. + if (stopFn && stopFn === fn && (!stopScope || stopScope === scope)) { + me.cancel(); + } + }; +}; + +// @tag core +/** + * Represents single event type that an Observable object listens to. + * All actual listeners are tracked inside here. When the event fires, + * it calls all the registered listener functions. + * + * @private + */ +Ext.define('Ext.util.Event', function() { + var arraySlice = Array.prototype.slice, + arrayInsert = Ext.Array.insert, + toArray = Ext.Array.toArray, + fireArgs = {}; + return { + requires: 'Ext.util.DelayedTask', + /** + * @property {Boolean} isEvent + * `true` in this class to identify an object as an instantiated Event, or subclass thereof. + */ + isEvent: true, + // Private. Event suspend count + suspended: 0, + noOptions: {}, + constructor: function(observable, name) { + this.name = name; + this.observable = observable; + this.listeners = []; + }, + addListener: function(fn, scope, options, caller, manager) { + var me = this, + added = false, + observable = me.observable, + eventName = me.name, + listeners, listener, priority, isNegativePriority, highestNegativePriorityIndex, hasNegativePriorityIndex, length, index, i, listenerPriority, managedListeners; + if (scope && !Ext._namedScopes[scope] && (typeof fn === 'string') && (typeof scope[fn] !== 'function')) { + Ext.raise("No method named '" + fn + "' found on scope object"); + } + if (me.findListener(fn, scope) === -1) { + listener = me.createListener(fn, scope, options, caller, manager); + if (me.firing) { + // if we are currently firing this event, don't disturb the listener loop + me.listeners = me.listeners.slice(0); + } + listeners = me.listeners; + index = length = listeners.length; + priority = options && options.priority; + highestNegativePriorityIndex = me._highestNegativePriorityIndex; + hasNegativePriorityIndex = highestNegativePriorityIndex !== undefined; + if (priority) { + // Find the index at which to insert the listener into the listeners array, + // sorted by priority highest to lowest. + isNegativePriority = (priority < 0); + if (!isNegativePriority || hasNegativePriorityIndex) { + // If the priority is a positive number, or if it is a negative number + // and there are other existing negative priority listenrs, then we + // need to calcuate the listeners priority-order index. + // If the priority is a negative number, begin the search for priority + // order index at the index of the highest existing negative priority + // listener, otherwise begin at 0 + for (i = (isNegativePriority ? highestNegativePriorityIndex : 0); i < length; i++) { + // Listeners created without options will have no "o" property + listenerPriority = listeners[i].o ? listeners[i].o.priority || 0 : 0; + if (listenerPriority < priority) { + index = i; + break; + } + } + } else { + // if the priority is a negative number, and there are no other negative + // priority listeners, then no calculation is needed - the negative + // priority listener gets appended to the end of the listeners array. + me._highestNegativePriorityIndex = index; + } + } else if (hasNegativePriorityIndex) { + // listeners with a priority of 0 or undefined are appended to the end of + // the listeners array unless there are negative priority listeners in the + // listeners array, then they are inserted before the highest negative + // priority listener. + index = highestNegativePriorityIndex; + } + if (!isNegativePriority && index <= highestNegativePriorityIndex) { + me._highestNegativePriorityIndex++; + } + if (index === length) { + listeners[length] = listener; + } else { + arrayInsert(listeners, index, [ + listener + ]); + } + if (observable.isElement) { + // It is the role of Ext.util.Event (vs Ext.Element) to handle subscribe/ + // unsubscribe because it is the lowest level place to intercept the + // listener before it is added/removed. For addListener this could easily + // be done in Ext.Element's doAddListener override, but since there are + // multiple paths for listener removal (un, clearListeners), it is best + // to keep all subscribe/unsubscribe logic here. + observable._getPublisher(eventName, options.translate === false).subscribe(observable, eventName, options.delegated !== false, options.capture); + } + // If the listener was passed with a manager, add it to the manager's list. + if (manager) { + // if scope is an observable, the listener will be automatically managed + // this eliminates the need to call mon() in a majority of cases + managedListeners = manager.managedListeners || (manager.managedListeners = []); + managedListeners.push({ + item: me.observable, + ename: (options && options.managedName) || me.name, + fn: fn, + scope: scope, + options: options + }); + } + added = true; + } + return added; + }, + createListener: function(fn, scope, o, caller, manager) { + var me = this, + namedScope = Ext._namedScopes[scope], + listener = { + fn: fn, + scope: scope, + ev: me, + caller: caller, + manager: manager, + namedScope: namedScope, + defaultScope: namedScope ? (scope || me.observable) : undefined, + lateBound: typeof fn === 'string' + }, + handler = fn, + wrapped = false, + type; + // The order is important. The 'single' wrapper must be wrapped by the 'buffer' and 'delayed' wrapper + // because the event removal that the single listener does destroys the listener's DelayedTask(s) + if (o) { + listener.o = o; + if (o.single) { + handler = me.createSingle(handler, listener, o, scope); + wrapped = true; + } + if (o.target) { + handler = me.createTargeted(handler, listener, o, scope, wrapped); + wrapped = true; + } + if (o.onFrame) { + handler = me.createAnimFrame(handler, listener, o, scope, wrapped); + wrapped = true; + } + if (o.delay) { + handler = me.createDelayed(handler, listener, o, scope, wrapped); + wrapped = true; + } + if (o.buffer) { + handler = me.createBuffered(handler, listener, o, scope, wrapped); + wrapped = true; + } + if (me.observable.isElement) { + // If the event type was translated, e.g. mousedown -> touchstart, we need to save + // the original type in the listener object so that the Ext.event.Event object can + // reflect the correct type at firing time + type = o.type; + if (type) { + listener.type = type; + } + } + } + listener.fireFn = handler; + listener.wrapped = wrapped; + return listener; + }, + findListener: function(fn, scope) { + var listeners = this.listeners, + i = listeners.length, + listener; + while (i--) { + listener = listeners[i]; + if (listener) { + // use ==, not === for scope comparison, so that undefined and null are equal + if (listener.fn === fn && listener.scope == scope) { + return i; + } + } + } + return -1; + }, + removeListener: function(fn, scope, index) { + var me = this, + removed = false, + observable = me.observable, + eventName = me.name, + listener, options, manager, managedListeners, managedListener, i; + index = index != null ? index : me.findListener(fn, scope); + if (index !== -1) { + listener = me.listeners[index]; + if (me.firing) { + me.listeners = me.listeners.slice(0); + } + // Remove this listener from the listeners array. We can use splice directly here. + // The IE8 bug which Ext.Array works around only affects *insertion* + // http://social.msdn.microsoft.com/Forums/en-US/iewebdevelopment/thread/6e946d03-e09f-4b22-a4dd-cd5e276bf05a/ + me.listeners.splice(index, 1); + // if the listeners array contains negative priority listeners, adjust the + // internal index if needed. + if (me._highestNegativePriorityIndex) { + if (index < me._highestNegativePriorityIndex) { + me._highestNegativePriorityIndex--; + } else if (index === me._highestNegativePriorityIndex && index === me.listeners.length) { + delete me._highestNegativePriorityIndex; + } + } + if (listener) { + options = listener.o; + // cancel and remove a buffered handler that hasn't fired yet. + // When the buffered listener is invoked, it must check whether + // it still has a task. + if (listener.task) { + listener.task.cancel(); + delete listener.task; + } + // cancel and remove all delayed handlers that haven't fired yet + i = listener.tasks && listener.tasks.length; + if (i) { + while (i--) { + listener.tasks[i].cancel(); + } + delete listener.tasks; + } + // Cancel the timer that could have been set if the event has already fired + listener.fireFn.timerId = Ext.undefer(listener.fireFn.timerId); + manager = listener.manager; + if (manager) { + // If this is a managed listener we need to remove it from the manager's + // managedListeners array. This ensures that if we listen using mon + // and then remove without using mun, the managedListeners array is updated + // accordingly, for example + // + // manager.on(target, 'foo', fn); + // + // target.un('foo', fn); + managedListeners = manager.managedListeners; + if (managedListeners) { + for (i = managedListeners.length; i--; ) { + managedListener = managedListeners[i]; + if (managedListener.item === me.observable && managedListener.ename === eventName && managedListener.fn === fn && managedListener.scope === scope) { + managedListeners.splice(i, 1); + } + } + } + } + if (observable.isElement) { + observable._getPublisher(eventName, options.translate === false).unsubscribe(observable, eventName, options.delegated !== false, options.capture); + } + } + removed = true; + } + return removed; + }, + // Iterate to stop any buffered/delayed events + clearListeners: function() { + var listeners = this.listeners, + i = listeners.length, + listener; + while (i--) { + listener = listeners[i]; + this.removeListener(listener.fn, listener.scope); + } + }, + suspend: function() { + ++this.suspended; + }, + resume: function() { + if (this.suspended) { + --this.suspended; + } + }, + isSuspended: function() { + return this.suspended > 0; + }, + fireDelegated: function(firingObservable, args) { + this.firingObservable = firingObservable; + return this.fire.apply(this, args); + }, + fire: function() { + var me = this, + CQ = Ext.ComponentQuery, + listeners = me.listeners, + count = listeners.length, + observable = me.observable, + isElement = observable.isElement, + isComponent = observable.isComponent, + firingObservable = me.firingObservable, + options, delegate, fireInfo, i, args, listener, len, delegateEl, currentTarget, type, chained, firingArgs, e, fireFn, fireScope; + if (!me.suspended && count > 0) { + me.firing = true; + args = arguments.length ? arraySlice.call(arguments, 0) : []; + len = args.length; + if (isElement) { + e = args[0]; + } + for (i = 0; i < count; i++) { + listener = listeners[i]; + // Listener may be undefined if one of the previous listeners + // destroyed the observable that was listening to these events. + // We'd be still in the middle of the loop here, unawares. + if (!listener) { + + continue; + } + options = listener.o; + if (isElement) { + if (currentTarget) { + // restore the previous currentTarget if we changed it last time + // around the loop while processing the delegate option. + e.setCurrentTarget(currentTarget); + } + // For events that have been translated to provide device compatibility, + // e.g. mousedown -> touchstart, we want the event object to reflect the + // type that was originally listened for, not the type of the actual event + // that fired. The listener's "type" property reflects the original type. + type = listener.type; + if (type) { + // chain a new object to the event object before changing the type. + // This is more efficient than creating a new event object, and we + // don't want to change the type of the original event because it may + // be used asynchronously by other handlers + // Translated events are not gestures. They must appear to be + // atomic events, so that they can be stopped. + chained = e; + e = args[0] = chained.chain({ + type: type, + isGesture: false + }); + } + // In Ext4 Ext.EventObject was a singleton event object that was reused as events + // were fired. Set Ext.EventObject to the last fired event for compatibility. + Ext.EventObject = e; + } + firingArgs = args; + if (options) { + delegate = options.delegate; + if (delegate) { + if (isElement) { + // prepending the currentTarget.id to the delegate selector + // allows us to match selectors such as "> div" + delegateEl = e.getTarget(typeof delegate === 'function' ? delegate : '#' + e.currentTarget.id + ' ' + delegate); + if (delegateEl) { + args[1] = delegateEl; + // save the current target before changing it to the delegateEl + // so that we can restore it next time around + currentTarget = e.currentTarget; + e.setCurrentTarget(delegateEl); + } else { + + continue; + } + } else if (isComponent && !CQ.is(firingObservable, delegate, observable)) { + + continue; + } + } + if (isElement) { + if (options.preventDefault) { + e.preventDefault(); + } + if (options.stopPropagation) { + e.stopPropagation(); + } + if (options.stopEvent) { + e.stopEvent(); + } + } + args[len] = options; + if (options.args) { + firingArgs = options.args.concat(args); + } + } + fireInfo = me.getFireInfo(listener); + fireFn = fireInfo.fn; + fireScope = fireInfo.scope; + // We don't want to keep closure and scope on the Event prototype! + fireInfo.fn = fireInfo.scope = null; + // If the scope is already destroyed, we absolutely cannot deliver events to it. + // We also need to clean up the listener to avoid it hanging around forever + // like a zombie. Scope can be null/undefined, that's normal. + if (fireScope && fireScope.destroyed) { + me.removeListener(fireFn, fireScope, i); + fireFn = null; + // Skip warnings for Ext.container.Monitor + // It is to be deprecated and removed shortly. + if (fireScope.$className !== 'Ext.container.Monitor') { + (Ext.raiseOnDestroyed ? Ext.raise : Ext.log.warn)({ + msg: 'Attempting to fire "' + me.name + '" event on destroyed ' + (fireScope.$className || 'object') + ' instance with id: ' + (fireScope.id || 'unknown'), + instance: fireScope + }); + } + } + // N.B. This is where actual listener code is called. Step boldly into! + if (fireFn && fireFn.apply(fireScope, firingArgs) === false) { + Ext.EventObject = null; + return (me.firing = false); + } + // We should remove the last item here to avoid future listeners + // in the Array to inherit these options by mistake + if (options) { + args.length--; + } + if (chained) { + // if we chained the event object for type translation we need to + // un-chain it before proceeding to process the next listener, which + // may not be a translated event. + e = args[0] = chained; + chained = null; + } + // We don't guarantee Ext.EventObject existence outside of the immediate + // event propagation scope + Ext.EventObject = null; + } + } + me.firing = false; + return true; + }, + getFireInfo: function(listener, fromWrapped) { + var observable = this.observable, + fireFn = listener.fireFn, + scope = listener.scope, + namedScope = listener.namedScope, + fn; + // If we are called with a wrapped listener, only attempt to do scope + // resolution if we are explicitly called by the last wrapped function + if (!fromWrapped && listener.wrapped) { + fireArgs.fn = fireFn; + return fireArgs; + } + fn = fromWrapped ? listener.fn : fireFn; + var name = fn; + if (listener.lateBound) { + // handler is a function name - need to resolve it to a function reference + if (!scope || namedScope) { + // Only invoke resolveListenerScope if the user did not specify a scope, + // or if the user specified a named scope. Named function handlers that + // use an arbitrary object as the scope just skip this part, and just + // use the given scope object to resolve the method. + scope = (listener.caller || observable).resolveListenerScope(listener.defaultScope); + } + if (!scope) { + Ext.raise('Unable to dynamically resolve scope for "' + listener.ev.name + '" listener on ' + this.observable.id); + } + if (!Ext.isFunction(scope[fn])) { + Ext.raise('No method named "' + fn + '" on ' + (scope.$className || 'scope object.')); + } + fn = scope[fn]; + } else if (namedScope && namedScope.isController) { + // If handler is a function reference and scope:'controller' was requested + // we'll do our best to look up a controller. + scope = (listener.caller || observable).resolveListenerScope(listener.defaultScope); + if (!scope) { + Ext.raise('Unable to dynamically resolve scope for "' + listener.ev.name + '" listener on ' + this.observable.id); + } + } else if (!scope || namedScope) { + // If handler is a function reference we use the observable instance as + // the default scope + scope = observable; + } + // We can only ever be firing one event at a time, so just keep + // overwriting the object we've got in our closure, otherwise we'll be + // creating a whole bunch of garbage objects + fireArgs.fn = fn; + fireArgs.scope = scope; + if (!fn) { + Ext.raise('Unable to dynamically resolve method "' + name + '" on ' + this.observable.$className); + } + return fireArgs; + }, + createAnimFrame: function(handler, listener, o, scope, wrapped) { + var fireInfo; + if (!wrapped) { + fireInfo = listener.ev.getFireInfo(listener, true); + handler = fireInfo.fn; + scope = fireInfo.scope; + // We don't want to keep closure and scope references on the Event prototype! + fireInfo.fn = fireInfo.scope = null; + } + return Ext.Function.createAnimationFrame(handler, scope, o.args); + }, + createTargeted: function(handler, listener, o, scope, wrapped) { + return function() { + if (o.target === arguments[0]) { + var fireInfo; + if (!wrapped) { + fireInfo = listener.ev.getFireInfo(listener, true); + handler = fireInfo.fn; + scope = fireInfo.scope; + // We don't want to keep closure and scope references on the Event prototype! + fireInfo.fn = fireInfo.scope = null; + } + return handler.apply(scope, arguments); + } + }; + }, + createBuffered: function(handler, listener, o, scope, wrapped) { + listener.task = new Ext.util.DelayedTask(); + return function() { + // If the listener is removed during the event call, the listener stays in the + // list of listeners to be invoked in the fire method, but the task is deleted + // So if we get here with no task, it's because the listener has been removed. + if (listener.task) { + var fireInfo; + if (Ext.Timer.track) { + o.$delayedTask = listener.task; + } + // for unit test access + if (!wrapped) { + fireInfo = listener.ev.getFireInfo(listener, true); + handler = fireInfo.fn; + scope = fireInfo.scope; + // We don't want to keep closure and scope references on the Event prototype! + fireInfo.fn = fireInfo.scope = null; + } + listener.task.delay(o.buffer, handler, scope, toArray(arguments)); + } + }; + }, + createDelayed: function(handler, listener, o, scope, wrapped) { + return function() { + var task = new Ext.util.DelayedTask(), + fireInfo; + if (!wrapped) { + fireInfo = listener.ev.getFireInfo(listener, true); + handler = fireInfo.fn; + scope = fireInfo.scope; + // We don't want to keep closure and scope references on the Event prototype! + fireInfo.fn = fireInfo.scope = null; + } + if (!listener.tasks) { + listener.tasks = []; + } + listener.tasks.push(task); + if (Ext.Timer.track) { + o.$delayedTask = task; + } + // for unit test access + task.delay(o.delay || 10, handler, scope, toArray(arguments)); + }; + }, + createSingle: function(handler, listener, o, scope, wrapped) { + return function() { + var event = listener.ev, + observable = event.observable, + fn = listener.fn, + fireInfo; + // If we have an observable, use that to clean up because there + // can be special cases that need handling. For example element + // listeners may bind multiple events (mousemove+touchmove) and they + // need to act in tandem. + if (observable) { + if (!observable.destroyed) { + observable.removeListener(event.name, fn, scope); + } + } else { + event.removeListener(fn, scope); + } + if (!wrapped) { + fireInfo = event.getFireInfo(listener, true); + handler = fireInfo.fn; + scope = fireInfo.scope; + // We don't want to keep closure and scope references on the Event prototype! + fireInfo.fn = fireInfo.scope = null; + } + return handler.apply(scope, arguments); + }; + } + }; +}); + +// @tag dom,core +/** + * An Identifiable mixin. + * @private + */ +Ext.define('Ext.mixin.Identifiable', { + statics: { + uniqueIds: {} + }, + isIdentifiable: true, + mixinId: 'identifiable', + idCleanRegex: /\.|[^\w\-]/g, + defaultIdPrefix: 'ext-', + defaultIdSeparator: '-', + getOptimizedId: function() { + return this.id; + }, + getUniqueId: function() { + var id = this.id, + prototype, separator, xtype, uniqueIds, prefix; + // Cannot test falsiness. Zero is a valid ID. + if (!(id || id === 0)) { + prototype = this.self.prototype; + separator = this.defaultIdSeparator; + uniqueIds = Ext.mixin.Identifiable.uniqueIds; + if (!prototype.hasOwnProperty('identifiablePrefix')) { + xtype = this.xtype; + if (xtype) { + prefix = this.defaultIdPrefix + xtype.replace(this.idCleanRegex, separator) + separator; + } else if (!(prefix = prototype.$className)) { + prefix = this.defaultIdPrefix + 'anonymous' + separator; + } else { + prefix = prefix.replace(this.idCleanRegex, separator).toLowerCase() + separator; + } + prototype.identifiablePrefix = prefix; + } + prefix = this.identifiablePrefix; + if (!uniqueIds.hasOwnProperty(prefix)) { + uniqueIds[prefix] = 0; + } + // The double assignment here and in setId is intentional to workaround a JIT + // issue that prevents me.id from being assigned in random scenarios. The issue + // occurs on 4th gen iPads and lower, possibly other older iOS devices. See EXTJS-16494. + id = this.id = this.id = prefix + (++uniqueIds[prefix]); + } + this.getUniqueId = this.getOptimizedId; + return id; + }, + setId: function(id) { + // See getUniqueId() + this.id = this.id = id; + }, + /** + * Retrieves the id of this component. Will autogenerate an id if one has not already been set. + * @return {String} id + */ + getId: function() { + var id = this.id; + if (!id) { + id = this.getUniqueId(); + } + this.getId = this.getOptimizedId; + return id; + } +}); + +// @tag core +/** + * Base class that provides a common interface for publishing events. Subclasses are + * expected to have a property "events" which is populated as event listeners register, + * and, optionally, a property "listeners" with configured listeners defined. + * + * *Note*: This mixin requires the constructor to be called, which is typically done + * during the construction of your object. The Observable constructor will call + * {@link #initConfig}, so it does not need to be called a second time. + * + * For example: + * + * Ext.define('Employee', { + * mixins: ['Ext.mixin.Observable'], + * + * config: { + * name: '' + * }, + * + * constructor: function (config) { + * // The `listeners` property is processed to add listeners and the config + * // is applied to the object. + * this.mixins.observable.constructor.call(this, config); + * // Config has been initialized + * console.log(this.getEmployeeName()); + * } + * }); + * + * This could then be used like this: + * + * var newEmployee = new Employee({ + * name: employeeName, + * listeners: { + * quit: function() { + * // By default, "this" will be the object that fired the event. + * alert(this.getName() + " has quit!"); + * } + * } + * }); + */ +Ext.define('Ext.mixin.Observable', function(Observable) { + var emptyFn = Ext.emptyFn, + emptyArray = [], + arrayProto = Array.prototype, + arraySlice = arrayProto.slice, + // Destroyable class which removes listeners + ListenerRemover = function(observable) { + // Passed a ListenerRemover: return it + if (observable instanceof ListenerRemover) { + return observable; + } + this.observable = observable; + // Called when addManagedListener is used with the event source as the second arg: + // (owner, eventSource, args...) + if (arguments[1].isObservable) { + this.managedListeners = true; + } + this.args = arraySlice.call(arguments, 1); + }, + // These properties should not be nulled during Base destroy(), + // we will take care of them in destroyObservable() + protectedProps = [ + 'events', + 'hasListeners', + 'managedListeners', + 'eventedBeforeEventNames' + ]; + ListenerRemover.prototype.destroy = function() { + var me = this, + args = me.args, + observable = me.observable, + // Extract the element reference from the options object. + // Single arg form first, options is args[3] in multi arg form. + elementName = args[0].element || (args[3] && args[3].element); + // If it was an element listener, then the listener is added to that element reference. + if (elementName) { + if (Ext.Array.indexOf(observable.referenceList, elementName) === -1) { + Ext.Logger.error("Destroying event listener with an invalid element reference of '" + elementName + "' for this component. Available values are: '" + observable.referenceList.join("', '") + "'", observable); + } + observable = observable[elementName]; + } + // If that observable is already destroyed, all its listeners were cleared + if (!observable.destroyed) { + observable[me.managedListeners ? 'mun' : 'un'].apply(observable, me.args); + } + me.destroy = Ext.emptyFn; + }; + return { + extend: 'Ext.Mixin', + mixinConfig: { + id: 'observable', + after: { + destroy: 'destroyObservable' + } + }, + requires: [ + 'Ext.util.Event' + ], + mixins: [ + 'Ext.mixin.Identifiable' + ], + statics: { + /** + * Removes **all** added captures from the Observable. + * + * @param {Ext.util.Observable} o The Observable to release + * @static + */ + releaseCapture: function(o) { + o.fireEventArgs = this.prototype.fireEventArgs; + }, + /** + * Starts capture on the specified Observable. All events will be passed to the supplied function with the event + * name + standard signature of the event **before** the event is fired. If the supplied function returns false, + * the event will not fire. + * + * @param {Ext.util.Observable} o The Observable to capture events from. + * @param {Function} fn The function to call when an event is fired. + * @param {Object} scope (optional) The scope (`this` reference) in which the function is executed. Defaults to + * the Observable firing the event. + * @static + */ + capture: function(o, fn, scope) { + // We're capturing calls to fireEventArgs to avoid duplication of events; + // however fn expects fireEvent's signature so we have to convert it here. + // To avoid unnecessary conversions, observe() below is aware of the changes + // and will capture fireEventArgs instead. + var newFn = function(eventName, args) { + return fn.apply(scope, [ + eventName + ].concat(args)); + }; + this.captureArgs(o, newFn, scope); + }, + /** + * @method + * @private + */ + captureArgs: function(o, fn, scope) { + o.fireEventArgs = Ext.Function.createInterceptor(o.fireEventArgs, fn, scope); + }, + /** + * Sets observability on the passed class constructor. + * + * This makes any event fired on any instance of the passed class also fire a single event through + * the **class** allowing for central handling of events on many instances at once. + * + * Usage: + * + * Ext.util.Observable.observe(Ext.data.Connection); + * Ext.data.Connection.on('beforerequest', function(con, options) { + * console.log('Ajax request made to ' + options.url); + * }); + * + * @param {Function} cls The class constructor to make observable. + * @param {Object} listeners An object containing a series of listeners to + * add. See {@link Ext.util.Observable#addListener addListener}. + * @static + */ + observe: function(cls, listeners) { + if (cls) { + if (!cls.isObservable) { + Ext.applyIf(cls, new this()); + this.captureArgs(cls.prototype, cls.fireEventArgs, cls); + } + if (Ext.isObject(listeners)) { + cls.on(listeners); + } + } + return cls; + }, + /** + * @method prepareClass + * Prepares a given class for observable instances. This method is called when a + * class derives from this class or uses this class as a mixin. + * @param {Function} T The class constructor to prepare. + * @param {Ext.util.Observable} mixin The mixin if being used as a mixin. + * @param {Object} data The raw class creation data if this is an extend. + * @private + */ + prepareClass: function(T, mixin, data) { + // T.hasListeners is the object to track listeners on class T. This object's + // prototype (__proto__) is the "hasListeners" of T.superclass. + // Instances of T will create "hasListeners" that have T.hasListeners as their + // immediate prototype (__proto__). + var listeners = T.listeners = [], + // If this function was called as a result of an "onExtended", it will + // receive the class as "T", but the members will not yet have been + // applied to the prototype. If this is the case, just grab listeners + // off of the raw data object. + target = data || T.prototype, + targetListeners = target.listeners, + superListeners = mixin ? mixin.listeners : T.superclass.self.listeners, + name, scope, namedScope, i, len; + // Process listeners that have been declared on the class body. These + // listeners must not override each other, but each must be added + // separately. This is accomplished by maintaining a nested array + // of listeners for the class and it's superclasses/mixins + if (superListeners) { + listeners.push(superListeners); + } + if (targetListeners) { + // Allow listener scope resolution mechanism to know if the listeners + // were declared on the class. This is only necessary when scope + // is unspecified, or when scope is 'controller'. We use special private + // named scopes of "self" and "self.controller" to indicate either + // unspecified scope, or scope declared as controller on the class + // body. To avoid iterating the listeners object multiple times, we + // only put this special scope on the outermost object at this point + // and allow addListener to handle scope:'controller' declared on + // inner objects of the listeners config. + scope = targetListeners.scope; + if (!scope) { + targetListeners.scope = 'self'; + } else { + namedScope = Ext._namedScopes[scope]; + if (namedScope && namedScope.isController) { + targetListeners.scope = 'self.controller'; + } + } + listeners.push(targetListeners); + // After adding the target listeners to the declared listeners array + // we can delete it off of the prototype (or data object). This ensures + // that we don't attempt to add the listeners twice, once during + // addDeclaredListeners, and again when we add this.listeners in the + // constructor. + target.listeners = null; + } + if (!T.HasListeners) { + // We create a HasListeners "class" for this class. The "prototype" of the + // HasListeners class is an instance of the HasListeners class associated + // with this class's super class (or with Observable). + var HasListeners = function() {}, + SuperHL = T.superclass.HasListeners || (mixin && mixin.HasListeners) || Observable.HasListeners; + // Make the HasListener class available on the class and its prototype: + T.prototype.HasListeners = T.HasListeners = HasListeners; + // And connect its "prototype" to the new HasListeners of our super class + // (which is also the class-level "hasListeners" instance). + HasListeners.prototype = T.hasListeners = new SuperHL(); + } + // Reusing a variable here + scope = T.prototype.$noClearOnDestroy || {}; + for (i = 0 , len = protectedProps.length; i < len; i++) { + scope[protectedProps[i]] = true; + } + T.prototype.$noClearOnDestroy = scope; + } + }, + /* End Definitions */ + /** + * @cfg {Object} listeners + * + * A config object containing one or more event handlers to be added to this object during initialization. This + * should be a valid listeners config object as specified in the + * {@link Ext.util.Observable#addListener addListener} example for attaching + * multiple handlers at once. + * + * **DOM events from Ext JS {@link Ext.Component Components}** + * + * While _some_ Ext JS Component classes export selected DOM events (e.g. "click", "mouseover" etc), this is usually + * only done when extra value can be added. For example the {@link Ext.view.View DataView}'s **`{@link + * Ext.view.View#itemclick itemclick}`** event passing the node clicked on. To access DOM events directly from a + * child element of a Component, we need to specify the `element` option to identify the Component property to add a + * DOM listener to: + * + * new Ext.panel.Panel({ + * width: 400, + * height: 200, + * dockedItems: [{ + * xtype: 'toolbar' + * }], + * listeners: { + * click: { + * element: 'el', //bind to the underlying el property on the panel + * fn: function(){ console.log('click el'); } + * }, + * dblclick: { + * element: 'body', //bind to the underlying body property on the panel + * fn: function(){ console.log('dblclick body'); } + * } + * } + * }); + */ + /** + * @property {Boolean} isObservable + * `true` in this class to identify an object as an instantiated Observable, or subclass thereof. + */ + isObservable: true, + /** + * @private + * We don't want the base destructor to clear the prototype because + * our destroyObservable handler must be called the very last. It will take care + * of the prototype after completing Observable destruction sequence. + */ + $vetoClearingPrototypeOnDestroy: true, + /** + * @private + * Initial suspended call count. Incremented when {@link #suspendEvents} is called, decremented when {@link #resumeEvents} is called. + */ + eventsSuspended: 0, + /** + * @property {Object} hasListeners + * @readonly + * This object holds a key for any event that has a listener. The listener may be set + * directly on the instance, or on its class or a super class (via {@link #observe}) or + * on the {@link Ext.app.EventBus MVC EventBus}. The values of this object are truthy + * (a non-zero number) and falsy (0 or undefined). They do not represent an exact count + * of listeners. The value for an event is truthy if the event must be fired and is + * falsy if there is no need to fire the event. + * + * The intended use of this property is to avoid the expense of fireEvent calls when + * there are no listeners. This can be particularly helpful when one would otherwise + * have to call fireEvent hundreds or thousands of times. It is used like this: + * + * if (this.hasListeners.foo) { + * this.fireEvent('foo', this, arg1); + * } + */ + constructor: function(config) { + var me = this, + self = me.self, + declaredListeners, listeners, bubbleEvents, len, i; + // Observable can be extended and/or mixed in at multiple levels in a Class + // hierarchy, and may have its constructor invoked multiple times for a given + // instance. The following ensures we only perform initialization the first + // time the constructor is called. + if (me.$observableInitialized) { + return; + } + me.$observableInitialized = true; + // This double assignment is intentional - it works around a strange JIT + // bug that prevents this.hasListeners from being assigned in some cases on + // some versions of iOS and iOS simulator. + // (This bug manifests itself in the unit tests for Ext.data.NodeInterface + // where we repeatedly create tree nodes in each spec. Sometimes node.hasListeners + // is undefined immediately after node construction). + // A similar issue occurs with the data property of Ext.data.Model (see + // constructor) + me.hasListeners = me.hasListeners = new me.HasListeners(); + me.eventedBeforeEventNames = {}; + me.events = me.events || {}; + declaredListeners = self.listeners; + if (declaredListeners && !me._addDeclaredListeners(declaredListeners)) { + // Nulling out declared listeners allows future instances to avoid + // recursing into the declared listeners arrays if the first instance + // discovers that there are no declarative listeners in its hierarchy + self.listeners = null; + } + listeners = (config && config.listeners) || me.listeners; + if (listeners) { + if (listeners instanceof Array) { + // Support for listeners declared as an array: + // + // listeners: [ + // { foo: fooHandler }, + // { bar: barHandler } + // ] + for (i = 0 , len = listeners.length; i < len; ++i) { + me.addListener(listeners[i]); + } + } else { + me.addListener(listeners); + } + } + bubbleEvents = (config && config.bubbleEvents) || me.bubbleEvents; + if (bubbleEvents) { + me.enableBubble(bubbleEvents); + } + if (me.$applyConfigs) { + // Ext.util.Observable applies config properties directly to the instance + if (config) { + Ext.apply(me, config); + } + } else { + // Ext.mixin.Observable uses the config system + me.initConfig(config); + } + if (listeners) { + // Set as an instance property to preempt the prototype in case any are set there. + // Prevents listeners from being added multiple times if this constructor + // is called more than once by multiple parties in the inheritance hierarchy + me.listeners = null; + } + }, + onClassExtended: function(T, data) { + if (!T.HasListeners) { + // Some classes derive from us and some others derive from those classes. All + // of these are passed to this method. + Observable.prepareClass(T, T.prototype.$observableMixedIn ? undefined : data); + } + }, + /** + * @private + * Matches options property names within a listeners specification object - property names which are never used as event names. + */ + $eventOptions: { + scope: 1, + delay: 1, + buffer: 1, + onFrame: 1, + single: 1, + args: 1, + destroyable: 1, + priority: 1, + order: 1 + }, + $orderToPriority: { + before: 100, + current: 0, + after: -100 + }, + /** + * Adds declarative listeners as nested arrays of listener objects. + * @private + * @param {Array} listeners + * @return {Boolean} `true` if any listeners were added + */ + _addDeclaredListeners: function(listeners) { + var me = this; + if (listeners instanceof Array) { + Ext.each(listeners, me._addDeclaredListeners, me); + } else { + me._addedDeclaredListeners = true; + me.addListener(listeners); + } + return me._addedDeclaredListeners; + }, + /** + * The addManagedListener method is used when some object (call it "A") is listening + * to an event on another observable object ("B") and you want to remove that listener + * from "B" when "A" is destroyed. This is not an issue when "B" is destroyed because + * all of its listeners will be removed at that time. + * + * Example: + * + * Ext.define('Foo', { + * extend: 'Ext.Component', + * + * initComponent: function () { + * this.addManagedListener(MyApp.SomeGlobalSharedMenu, 'show', this.doSomething); + * this.callParent(); + * } + * }); + * + * As you can see, when an instance of Foo is destroyed, it ensures that the 'show' + * listener on the menu (`MyApp.SomeGlobalSharedMenu`) is also removed. + * + * As of version 5.1 it is no longer necessary to use this method in most cases because + * listeners are automatically managed if the scope object provided to + * {@link Ext.util.Observable#addListener addListener} is an Observable instance. + * However, if the observable instance and scope are not the same object you + * still need to use `mon` or `addManagedListener` if you want the listener to be + * managed. + * + * @param {Ext.util.Observable/Ext.dom.Element} item The item to which to add a listener/listeners. + * @param {Object/String} ename The event name, or an object containing event name properties. + * @param {Function/String} fn (optional) If the `ename` parameter was an event + * name, this is the handler function or the name of a method on the specified + * `scope`. + * @param {Object} scope (optional) If the `ename` parameter was an event name, this is the scope (`this` reference) + * in which the handler function is executed. + * @param {Object} options (optional) If the `ename` parameter was an event name, this is the + * {@link Ext.util.Observable#addListener addListener} options. + * @param {Boolean} noDestroy (private) + * @return {Object} **Only when the `destroyable` option is specified. ** + * + * A `Destroyable` object. An object which implements the `destroy` method which removes all listeners added in this call. For example: + * + * this.btnListeners = myButton.mon({ + * destroyable: true + * mouseover: function() { console.log('mouseover'); }, + * mouseout: function() { console.log('mouseout'); }, + * click: function() { console.log('click'); } + * }); + * + * And when those listeners need to be removed: + * + * Ext.destroy(this.btnListeners); + * + * or + * + * this.btnListeners.destroy(); + */ + addManagedListener: function(item, ename, fn, scope, options, noDestroy) { + var me = this, + managedListeners = me.managedListeners = me.managedListeners || [], + config, passedOptions; + if (typeof ename !== 'string') { + // When creating listeners using the object form, allow caller to override the default of + // using the listeners object as options. + // This is used by relayEvents, when adding its relayer so that it does not contribute + // a spurious options param to the end of the arg list. + passedOptions = arguments.length > 4 ? options : ename; + options = ename; + for (ename in options) { + if (options.hasOwnProperty(ename)) { + config = options[ename]; + if (!item.$eventOptions[ename]) { + // recurse, but pass the noDestroy parameter as true so that lots of individual Destroyables are not created. + // We create a single one at the end if necessary. + me.addManagedListener(item, ename, config.fn || config, config.scope || options.scope || scope, config.fn ? config : passedOptions, true); + } + } + } + if (options && options.destroyable) { + return new ListenerRemover(me, item, options); + } + } else { + if (fn !== emptyFn) { + item.doAddListener(ename, fn, scope, options, null, me, me); + // The 'noDestroy' flag is sent if we're looping through a hash of listeners passing each one to addManagedListener separately + if (!noDestroy && options && options.destroyable) { + return new ListenerRemover(me, item, ename, fn, scope); + } + } + } + }, + /** + * Removes listeners that were added by the {@link #mon} method. + * + * @param {Ext.util.Observable/Ext.dom.Element} item The item from which to remove a listener/listeners. + * @param {Object/String} ename The event name, or an object containing event name properties. + * @param {Function} fn (optional) If the `ename` parameter was an event name, this is the handler function. + * @param {Object} scope (optional) If the `ename` parameter was an event name, this is the scope (`this` reference) + * in which the handler function is executed. + */ + removeManagedListener: function(item, ename, fn, scope) { + var me = this, + options, config, managedListeners, length, i; + if (item.$observableDestroyed) { + return; + } + if (typeof ename !== 'string') { + options = ename; + for (ename in options) { + if (options.hasOwnProperty(ename)) { + config = options[ename]; + if (!item.$eventOptions[ename]) { + me.removeManagedListener(item, ename, config.fn || config, config.scope || options.scope || scope); + } + } + } + } else { + managedListeners = me.managedListeners ? me.managedListeners.slice() : []; + ename = Ext.canonicalEventName(ename); + for (i = 0 , length = managedListeners.length; i < length; i++) { + me.removeManagedListenerItem(false, managedListeners[i], item, ename, fn, scope); + } + } + }, + /** + * Fires the specified event with the passed parameters (minus the event name, plus the `options` object passed + * to {@link Ext.util.Observable#addListener addListener}). + * + * An event may be set to bubble up an Observable parent hierarchy (See {@link Ext.Component#getBubbleTarget}) by + * calling {@link #enableBubble}. + * + * @param {String} eventName The name of the event to fire. + * @param {Object...} args Variable number of parameters are passed to handlers. + * @return {Boolean} returns false if any of the handlers return false otherwise it returns true. + */ + fireEvent: function(eventName) { + return this.fireEventArgs(eventName, arraySlice.call(arguments, 1)); + }, + /** + * Gets the default scope for firing late bound events (string names with + * no scope attached) at runtime. + * @param {Object} [defaultScope=this] The default scope to return if none is found. + * @return {Object} The default event scope + * @protected + */ + resolveListenerScope: function(defaultScope) { + var namedScope = Ext._namedScopes[defaultScope]; + if (namedScope) { + if (namedScope.isController) { + Ext.raise('scope: "controller" can only be specified on classes that derive from Ext.Component or Ext.Widget'); + } + if (namedScope.isSelf || namedScope.isThis) { + defaultScope = null; + } + } + return defaultScope || this; + }, + /** + * Fires the specified event with the passed parameter list. + * + * An event may be set to bubble up an Observable parent hierarchy (See {@link Ext.Component#getBubbleTarget}) by + * calling {@link #enableBubble}. + * + * @param {String} eventName The name of the event to fire. + * @param {Object[]} args An array of parameters which are passed to handlers. + * @return {Boolean} returns false if any of the handlers return false otherwise it returns true. + */ + fireEventArgs: function(eventName, args) { + eventName = Ext.canonicalEventName(eventName); + var me = this, + // no need to make events since we need an Event with listeners + events = me.events, + event = events && events[eventName], + ret = true; + // Only continue firing the event if there are listeners to be informed. + // Bubbled events will always have a listener count, so will be fired. + if (me.hasListeners[eventName]) { + ret = me.doFireEvent(eventName, args || emptyArray, event ? event.bubble : false); + } + return ret; + }, + /** + * Fires the specified event with the passed parameters and executes a function (action). + * By default, the action function will be executed after any "before" event handlers + * (as specified using the `order` option of + * `{@link Ext.util.Observable#addListener addListener}`), but before any other + * handlers are fired. This gives the "before" handlers an opportunity to + * cancel the event by returning `false`, and prevent the action function from + * being called. + * + * The action can also be configured to run after normal handlers, but before any "after" + * handlers (as specified using the `order` event option) by passing `'after'` + * as the `order` parameter. This configuration gives any event handlers except + * for "after" handlers the opportunity to cancel the event and prevent the action + * function from being called. + * + * @param {String} eventName The name of the event to fire. + * @param {Array} args Arguments to pass to handlers and to the action function. + * @param {Function} fn The action function. + * @param {Object} [scope] The scope (`this` reference) in which the handler function is + * executed. **If omitted, defaults to the object which fired the event.** + * @param {Object} [options] Event options for the action function. Accepts any + * of the options of `{@link Ext.util.Observable#addListener addListener}` + * @param {String} [order='before'] The order to call the action function relative + * too the event handlers (`'before'` or `'after'`). Note that this option is + * simply used to sort the action function relative to the event handlers by "priority". + * An order of `'before'` is equivalent to a priority of `99.5`, while an order of + * `'after'` is equivalent to a priority of `-99.5`. See the `priority` option + * of `{@link Ext.util.Observable#addListener addListener}` for more details. + * @deprecated 5.5 Use {@link #fireEventedAction} instead. + */ + fireAction: function(eventName, args, fn, scope, options, order) { + // The historical behaviour has been to default the scope to `this`. + if (typeof fn === 'string' && !scope) { + fn = this[fn]; + } + // chain options to avoid mutating the user's options object + options = options ? Ext.Object.chain(options) : {}; + options.single = true; + options.priority = ((order === 'after') ? -99.5 : 99.5); + this.doAddListener(eventName, fn, scope, options); + this.fireEventArgs(eventName, args); + }, + $eventedController: { + _paused: 1, + pause: function() { + ++this._paused; + }, + resume: function() { + var me = this, + fn = me.fn, + scope = me.scope, + fnArgs = me.fnArgs, + owner = me.owner, + args, ret; + if (!--me._paused) { + if (fn) { + args = Ext.Array.slice(fnArgs || me.args); + if (fnArgs === false) { + // Passing false will remove the first item (typically the owner) + args.shift(); + } + me.fn = null; + // only call fn once + args.push(me); + if (Ext.isFunction(fn)) { + ret = fn.apply(scope, args); + } else if (scope && Ext.isString(fn) && Ext.isFunction(scope[fn])) { + ret = scope[fn].apply(scope, args); + } + if (ret === false) { + return false; + } + } + if (!me._paused) { + // fn could have paused us + return me.owner.fireEventArgs(me.eventName, me.args); + } + } + } + }, + /** + * Fires the specified event with the passed parameters and executes a function (action). + * Evented Actions will automatically dispatch a 'before' event passing. This event will + * be given a special controller that allows for pausing/resuming of the event flow. + * + * By pausing the controller the updater and events will not run until resumed. Pausing, + * however, will not stop the processing of any other before events. + * + * @param {String} eventName The name of the event to fire. + * @param {Array} args Arguments to pass to handlers and to the action function. + * @param {Function/String} fn The action function. + * @param {Object} [scope] The scope (`this` reference) in which the handler function is + * executed. **If omitted, defaults to the object which fired the event.** + * @param {Array/Boolean} [fnArgs] Optional arguments for the action `fn`. If not + * given, the normal `args` will be used to call `fn`. If `false` is passed, the + * `args` are used but if the first argument is this instance it will be removed + * from the args passed to the action function. + */ + fireEventedAction: function(eventName, args, fn, scope, fnArgs) { + var me = this, + eventedBeforeEventNames = me.eventedBeforeEventNames, + beforeEventName = eventedBeforeEventNames[eventName] || (eventedBeforeEventNames[eventName] = 'before' + eventName), + controller = Ext.apply({ + owner: me, + eventName: eventName, + fn: fn, + scope: scope, + fnArgs: fnArgs, + args: args + }, me.$eventedController), + value; + args.push(controller); + value = me.fireEventArgs(beforeEventName, args); + args.pop(); + if (value === false) { + return false; + } + return controller.resume(); + }, + /** + * Continue to fire event. + * @private + * + * @param {String} eventName + * @param {Array} args + * @param {Boolean} bubbles + */ + doFireEvent: function(eventName, args, bubbles) { + var target = this, + queue, event, + ret = true; + do { + if (target.eventsSuspended) { + if ((queue = target.eventQueue)) { + queue.push([ + eventName, + args + ]); + } + return ret; + } else { + event = target.events && target.events[eventName]; + if (event && event !== true) { + if ((ret = event.fire.apply(event, args)) === false) { + break; + } + } + } + } while (// Continue bubbling if event exists and it is `true` or the handler didn't returns false and it + // configure to bubble. + bubbles && (target = target.getBubbleParent())); + return ret; + }, + /** + * Gets the bubbling parent for an Observable + * @private + * @return {Ext.util.Observable} The bubble parent. null is returned if no bubble target exists + */ + getBubbleParent: function() { + var me = this, + parent = me.getBubbleTarget && me.getBubbleTarget(); + if (parent && parent.isObservable) { + return parent; + } + return null; + }, + /** + * The {@link #on} method is shorthand for + * {@link Ext.util.Observable#addListener addListener}. + * + * Appends an event handler to this object. For example: + * + * myGridPanel.on("itemclick", this.onItemClick, this); + * + * The method also allows for a single argument to be passed which is a config object + * containing properties which specify multiple events. For example: + * + * myGridPanel.on({ + * cellclick: this.onCellClick, + * select: this.onSelect, + * viewready: this.onViewReady, + * scope: this // Important. Ensure "this" is correct during handler execution + * }); + * + * One can also specify options for each event handler separately: + * + * myGridPanel.on({ + * cellclick: {fn: this.onCellClick, scope: this, single: true}, + * viewready: {fn: panel.onViewReady, scope: panel} + * }); + * + * *Names* of methods in a specified scope may also be used: + * + * myGridPanel.on({ + * cellclick: {fn: 'onCellClick', scope: this, single: true}, + * viewready: {fn: 'onViewReady', scope: panel} + * }); + * + * @param {String/Object} eventName The name of the event to listen for. + * May also be an object who's property names are event names. + * + * @param {Function/String} [fn] The method the event invokes or the *name* of + * the method within the specified `scope`. Will be called with arguments + * given to {@link Ext.util.Observable#fireEvent} plus the `options` parameter described + * below. + * + * @param {Object} [scope] The scope (`this` reference) in which the handler function is + * executed. **If omitted, defaults to the object which fired the event.** + * + * @param {Object} [options] An object containing handler configuration. + * + * **Note:** The options object will also be passed as the last argument to every + * event handler. + * + * This object may contain any of the following properties: + * + * @param {Object} options.scope + * The scope (`this` reference) in which the handler function is executed. **If omitted, + * defaults to the object which fired the event.** + * + * @param {Number} options.delay + * The number of milliseconds to delay the invocation of the handler after the event + * fires. + * + * @param {Boolean} options.single + * True to add a handler to handle just the next firing of the event, and then remove + * itself. + * + * @param {Number} options.buffer + * Causes the handler to be scheduled to run in an {@link Ext.util.DelayedTask} delayed + * by the specified number of milliseconds. If the event fires again within that time, + * the original handler is _not_ invoked, but the new handler is scheduled in its place. + * + * @param {Number} options.onFrame + * Causes the handler to be scheduled to run at the next + * {@link Ext.Function#requestAnimationFrame animation frame event}. If the + * event fires again before that time, the handler is not rescheduled - the handler + * will only be called once when the next animation frame is fired, with the last set + * of arguments passed. + * + * @param {Ext.util.Observable} options.target + * Only call the handler if the event was fired on the target Observable, _not_ if the + * event was bubbled up from a child Observable. + * + * @param {String} options.element + * **This option is only valid for listeners bound to {@link Ext.Component Components}.** + * The name of a Component property which references an {@link Ext.dom.Element element} + * to add a listener to. + * + * This option is useful during Component construction to add DOM event listeners to + * elements of {@link Ext.Component Components} which will exist only after the + * Component is rendered. + * + * For example, to add a click listener to a Panel's body: + * + * var panel = new Ext.panel.Panel({ + * title: 'The title', + * listeners: { + * click: this.handlePanelClick, + * element: 'body' + * } + * }); + * + * In order to remove listeners attached using the element, you'll need to reference + * the element itself as seen below. + * + * panel.body.un(...) + * + * @param {String} [options.delegate] + * A simple selector to filter the event target or look for a descendant of the target. + * + * The "delegate" option is only available on Ext.dom.Element instances (or + * when attaching a listener to a Ext.dom.Element via a Component using the + * element option). + * + * See the *delegate* example below. + * + * @param {Boolean} [options.capture] + * When set to `true`, the listener is fired in the capture phase of the event propagation + * sequence, instead of the default bubble phase. + * + * The `capture` option is only available on Ext.dom.Element instances (or + * when attaching a listener to a Ext.dom.Element via a Component using the + * element option). + * + * @param {Boolean} [options.stopPropagation] + * **This option is only valid for listeners bound to {@link Ext.dom.Element Elements}.** + * `true` to call {@link Ext.event.Event#stopPropagation stopPropagation} on the event object + * before firing the handler. + * + * @param {Boolean} [options.preventDefault] + * **This option is only valid for listeners bound to {@link Ext.dom.Element Elements}.** + * `true` to call {@link Ext.event.Event#preventDefault preventDefault} on the event object + * before firing the handler. + * + * @param {Boolean} [options.stopEvent] + * **This option is only valid for listeners bound to {@link Ext.dom.Element Elements}.** + * `true` to call {@link Ext.event.Event#stopEvent stopEvent} on the event object + * before firing the handler. + * + * @param {Array} [options.args] + * + * Optional set of arguments to pass to the handler function before the actual + * fired event arguments. For example, if `args` is set to `['foo', 42]`, + * the event handler function will be called with an arguments list like this: + * + * handler('foo', 42, ...); + * + * @param {Boolean} [options.destroyable=false] + * When specified as `true`, the function returns a `destroyable` object. An object + * which implements the `destroy` method which removes all listeners added in this call. + * This syntax can be a helpful shortcut to using {@link #un}; particularly when + * removing multiple listeners. *NOTE* - not compatible when using the _element_ + * option. See {@link #un} for the proper syntax for removing listeners added using the + * _element_ config. + * + * @param {Number} [options.priority] + * An optional numeric priority that determines the order in which event handlers + * are run. Event handlers with no priority will be run as if they had a priority + * of 0. Handlers with a higher priority will be prioritized to run sooner than + * those with a lower priority. Negative numbers can be used to set a priority + * lower than the default. Internally, the framework uses a range of 1000 or + * greater, and -1000 or lesser for handlers that are intended to run before or + * after all others, so it is recommended to stay within the range of -999 to 999 + * when setting the priority of event handlers in application-level code. + * A priority must be an integer to be valid. Fractional values are reserved for + * internal framework use. + * + * @param {String} [options.order='current'] + * A legacy option that is provided for backward compatibility. + * It is recommended to use the `priority` option instead. Available options are: + * + * - `'before'`: equal to a priority of `100` + * - `'current'`: equal to a priority of `0` or default priority + * - `'after'`: equal to a priority of `-100` + * + * @param {String} [order='current'] + * A shortcut for the `order` event option. Provided for backward compatibility. + * Please use the `priority` event option instead. + * + * @param caller (private) + * + * **Combining Options** + * + * Using the options argument, it is possible to combine different types of listeners: + * + * A delayed, one-time listener. + * + * myPanel.on('hide', this.handleClick, this, { + * single: true, + * delay: 100 + * }); + * + * **Attaching multiple handlers in 1 call** + * + * The method also allows for a single argument to be passed which is a config object + * containing properties which specify multiple handlers and handler configs. + * + * grid.on({ + * itemclick: 'onItemClick', + * itemcontextmenu: grid.onItemContextmenu, + * destroy: { + * fn: function () { + * // function called within the 'altCmp' scope instead of grid + * }, + * scope: altCmp // unique scope for the destroy handler + * }, + * scope: grid // default scope - provided for example clarity + * }); + * + * **Delegate** + * + * This is a configuration option that you can pass along when registering a handler for + * an event to assist with event delegation. By setting this configuration option + * to a simple selector, the target element will be filtered to look for a + * descendant of the target. For example: + * + * var panel = Ext.create({ + * xtype: 'panel', + * renderTo: document.body, + * title: 'Delegate Handler Example', + * frame: true, + * height: 220, + * width: 220, + * html: '

BODY TITLE

Body content' + * }); + * + * // The click handler will only be called when the click occurs on the + * // delegate: h1.myTitle ("h1" tag with class "myTitle") + * panel.on({ + * click: function (e) { + * console.log(e.getTarget().innerHTML); + * }, + * element: 'body', + * delegate: 'h1.myTitle' + * }); + * + * @return {Object} **Only when the `destroyable` option is specified. ** + * + * A `Destroyable` object. An object which implements the `destroy` method which removes + * all listeners added in this call. For example: + * + * this.btnListeners = = myButton.on({ + * destroyable: true + * mouseover: function() { console.log('mouseover'); }, + * mouseout: function() { console.log('mouseout'); }, + * click: function() { console.log('click'); } + * }); + * + * And when those listeners need to be removed: + * + * Ext.destroy(this.btnListeners); + * + * or + * + * this.btnListeners.destroy(); + */ + addListener: function(eventName, fn, scope, options, order, caller) { + var me = this, + namedScopes = Ext._namedScopes, + config, namedScope, isClassListener, innerScope, eventOptions; + // Object listener hash passed + if (typeof eventName !== 'string') { + options = eventName; + scope = options.scope; + namedScope = scope && namedScopes[scope]; + isClassListener = namedScope && namedScope.isSelf; + // give subclasses the opportunity to switch the valid eventOptions + // (Ext.Component uses this when the "element" option is used) + eventOptions = ((me.isComponent || me.isWidget) && options.element) ? me.$elementEventOptions : me.$eventOptions; + for (eventName in options) { + config = options[eventName]; + if (!eventOptions[eventName]) { + /* This would be an API change so check removed until https://sencha.jira.com/browse/EXTJSIV-7183 is fully implemented in 4.2 + // Test must go here as well as in the simple form because of the attempted property access here on the config object. + if (!config || (typeof config !== 'function' && !config.fn)) { + Ext.raise('No function passed for event ' + me.$className + '.' + ename); + } + */ + innerScope = config.scope; + // for proper scope resolution, scope:'controller' specified on an + // inner object, must be translated to 'self.controller' if the + // listeners object was declared on the class body. + // see also Ext.util.Observable#prepareClass and + // Ext.mixin.Inheritable#resolveListenerScope + if (innerScope && isClassListener) { + namedScope = namedScopes[innerScope]; + if (namedScope && namedScope.isController) { + innerScope = 'self.controller'; + } + } + me.doAddListener(eventName, config.fn || config, innerScope || scope, config.fn ? config : options, order, caller); + } + } + if (options && options.destroyable) { + return new ListenerRemover(me, options); + } + } else { + me.doAddListener(eventName, fn, scope, options, order, caller); + if (options && options.destroyable) { + return new ListenerRemover(me, eventName, fn, scope, options); + } + } + return me; + }, + /** + * Removes an event handler. + * + * @param {String} eventName The type of event the handler was associated with. + * @param {Function} fn The handler to remove. **This must be a reference to the function + * passed into the + * {@link Ext.util.Observable#addListener addListener} call.** + * @param {Object} scope (optional) The scope originally specified for the handler. It + * must be the same as the scope argument specified in the original call to + * {@link Ext.util.Observable#addListener} or the listener will not be removed. + * @param eventOptions (private) + * + * **Convenience Syntax** + * + * You can use the {@link Ext.util.Observable#addListener addListener} + * `destroyable: true` config option in place of calling un(). For example: + * + * var listeners = cmp.on({ + * scope: cmp, + * afterrender: cmp.onAfterrender, + * beforehide: cmp.onBeforeHide, + * destroyable: true + * }); + * + * // Remove listeners + * listeners.destroy(); + * // or + * cmp.un( + * scope: cmp, + * afterrender: cmp.onAfterrender, + * beforehide: cmp.onBeforeHide + * ); + * + * **Exception - DOM event handlers using the element config option** + * + * You must go directly through the element to detach an event handler attached using + * the {@link Ext.util.Observable#addListener addListener} _element_ option. + * + * panel.on({ + * element: 'body', + * click: 'onBodyCLick' + * }); + * + * panel.body.un({ + * click: 'onBodyCLick' + * }); + */ + removeListener: function(eventName, fn, scope, eventOptions) { + var me = this, + config, options; + if (typeof eventName !== 'string') { + options = eventName; + // give subclasses the opportunity to switch the valid eventOptions + // (Ext.Component uses this when the "element" option is used) + eventOptions = eventOptions || me.$eventOptions; + for (eventName in options) { + if (options.hasOwnProperty(eventName)) { + config = options[eventName]; + if (!me.$eventOptions[eventName]) { + me.doRemoveListener(eventName, config.fn || config, config.scope || options.scope); + } + } + } + } else { + me.doRemoveListener(eventName, fn, scope); + } + return me; + }, + /** + * Appends a before-event handler. Returning `false` from the handler will stop the event. + * + * Same as {@link Ext.util.Observable#addListener addListener} with `order` set + * to `'before'`. + * + * @param {String/String[]/Object} eventName The name of the event to listen for. + * @param {Function/String} fn The method the event invokes. + * @param {Object} [scope] The scope for `fn`. + * @param {Object} [options] An object containing handler configuration. + */ + onBefore: function(eventName, fn, scope, options) { + return this.addListener(eventName, fn, scope, options, 'before'); + }, + /** + * Appends an after-event handler. + * + * Same as {@link Ext.util.Observable#addListener addListener} with `order` set + * to `'after'`. + * + * @param {String/String[]/Object} eventName The name of the event to listen for. + * @param {Function/String} fn The method the event invokes. + * @param {Object} [scope] The scope for `fn`. + * @param {Object} [options] An object containing handler configuration. + */ + onAfter: function(eventName, fn, scope, options) { + return this.addListener(eventName, fn, scope, options, 'after'); + }, + /** + * Removes a before-event handler. + * + * Same as {@link #removeListener} with `order` set to `'before'`. + * + * @param {String/String[]/Object} eventName The name of the event the handler was associated with. + * @param {Function/String} fn The handler to remove. + * @param {Object} [scope] The scope originally specified for `fn`. + * @param {Object} [options] Extra options object. + */ + unBefore: function(eventName, fn, scope, options) { + return this.removeListener(eventName, fn, scope, options, 'before'); + }, + /** + * Removes a before-event handler. + * + * Same as {@link #removeListener} with `order` set to `'after'`. + * + * @param {String/String[]/Object} eventName The name of the event the handler was associated with. + * @param {Function/String} fn The handler to remove. + * @param {Object} [scope] The scope originally specified for `fn`. + * @param {Object} [options] Extra options object. + */ + unAfter: function(eventName, fn, scope, options) { + return this.removeListener(eventName, fn, scope, options, 'after'); + }, + /** + * Alias for {@link #onBefore}. + */ + addBeforeListener: function() { + return this.onBefore.apply(this, arguments); + }, + /** + * Alias for {@link #onAfter}. + */ + addAfterListener: function() { + return this.onAfter.apply(this, arguments); + }, + /** + * Alias for {@link #unBefore}. + */ + removeBeforeListener: function() { + return this.unBefore.apply(this, arguments); + }, + /** + * Alias for {@link #unAfter}. + */ + removeAfterListener: function() { + return this.unAfter.apply(this, arguments); + }, + /** + * Removes all listeners for this object including the managed listeners + */ + clearListeners: function() { + var me = this, + events = me.events, + hasListeners = me.hasListeners, + event, key; + if (events) { + for (key in events) { + if (events.hasOwnProperty(key)) { + event = events[key]; + if (event.isEvent) { + delete hasListeners[key]; + event.clearListeners(); + } + } + } + me.events = null; + } + me.clearManagedListeners(); + }, + purgeListeners: function() { + if (Ext.global.console) { + Ext.global.console.warn('Observable: purgeListeners has been deprecated. Please use clearListeners.'); + } + return this.clearListeners.apply(this, arguments); + }, + /** + * Removes all managed listeners for this object. + */ + clearManagedListeners: function() { + var me = this, + managedListeners = me.managedListeners, + i, len; + if (managedListeners) { + // So that Event#removeListener doesn't find a managedListeners array from which to remove + // the listener it is removing. It iterates the array to find a match, and splices it. + me.managedListeners = null; + for (i = 0 , len = managedListeners.length; i < len; i++) { + me.removeManagedListenerItem(true, managedListeners[i]); + } + managedListeners.length = 0; + } + me.managedListeners = managedListeners; + }, + /** + * Remove a single managed listener item + * @private + * @param {Boolean} isClear True if this is being called during a clear + * @param {Object} managedListener The managed listener item + * @param {Object} item + * @param {String} ename + * @param {Function} fn + * @param {Object} scope + * See removeManagedListener for other args + */ + removeManagedListenerItem: function(isClear, managedListener, item, ename, fn, scope) { + if (isClear || (managedListener.item === item && managedListener.ename === ename && (!fn || managedListener.fn === fn) && (!scope || managedListener.scope === scope))) { + // Pass along the options for mixin.Observable, for example if using delegate. + // If the item has already been destroyed, its listeners were already cleared. + if (!managedListener.item.destroyed) { + managedListener.item.doRemoveListener(managedListener.ename, managedListener.fn, managedListener.scope, managedListener.options); + } + if (!isClear) { + Ext.Array.remove(this.managedListeners, managedListener); + } + } + }, + purgeManagedListeners: function() { + if (Ext.global.console) { + Ext.global.console.warn('Observable: purgeManagedListeners has been deprecated. Please use clearManagedListeners.'); + } + return this.clearManagedListeners.apply(this, arguments); + }, + /** + * Checks to see if this object has any listeners for a specified event, or whether the event bubbles. The answer + * indicates whether the event needs firing or not. + * + * @param {String} eventName The name of the event to check for + * @return {Boolean} `true` if the event is being listened for or bubbles, else `false` + */ + hasListener: function(eventName) { + eventName = Ext.canonicalEventName(eventName); + return !!this.hasListeners[eventName]; + }, + /** + * Checks if all events, or a specific event, is suspended. + * @param {String} [event] The name of the specific event to check + * @return {Boolean} `true` if events are suspended + */ + isSuspended: function(event) { + var suspended = this.eventsSuspended > 0, + events = this.events; + if (!suspended && event && events) { + event = events[event]; + if (event && event.isEvent) { + return event.isSuspended(); + } + } + return suspended; + }, + /** + * Suspends the firing of all events. (see {@link #resumeEvents}) + * + * @param {Boolean} queueSuspended `true` to queue up suspended events to be fired + * after the {@link #resumeEvents} call instead of discarding all suspended events. + */ + suspendEvents: function(queueSuspended) { + ++this.eventsSuspended; + if (queueSuspended && !this.eventQueue) { + this.eventQueue = []; + } + }, + /** + * Suspends firing of the named event(s). + * + * After calling this method to suspend events, the events will no longer fire when requested to fire. + * + * **Note that if this is called multiple times for a certain event, the converse method + * {@link #resumeEvent} will have to be called the same number of times for it to resume firing.** + * + * @param {String...} eventName Multiple event names to suspend. + */ + suspendEvent: function() { + var me = this, + events = me.events, + len = arguments.length, + i, event, ename; + for (i = 0; i < len; i++) { + ename = arguments[i]; + ename = Ext.canonicalEventName(ename); + event = events[ename]; + // we need to spin up the Event instance so it can hold the suspend count + if (!event || !event.isEvent) { + event = me._initEvent(ename); + } + event.suspend(); + } + }, + /** + * Resumes firing of the named event(s). + * + * After calling this method to resume events, the events will fire when requested to fire. + * + * **Note that if the {@link #suspendEvent} method is called multiple times for a certain event, + * this converse method will have to be called the same number of times for it to resume firing.** + * + * @param {String...} eventName Multiple event names to resume. + */ + resumeEvent: function() { + var events = this.events || 0, + len = events && arguments.length, + i, event, ename; + for (i = 0; i < len; i++) { + ename = Ext.canonicalEventName(arguments[i]); + event = events[ename]; + // If it exists, and is an Event object (not still a boolean placeholder), resume it + if (event && event.resume) { + event.resume(); + } + } + }, + /** + * Resumes firing events (see {@link #suspendEvents}). + * + * If events were suspended using the `queueSuspended` parameter, then all events fired + * during event suspension will be sent to any listeners now. + * + * @param {Boolean} [discardQueue] `true` to prevent any previously queued events from firing + * while we were suspended. See {@link #suspendEvents}. + */ + resumeEvents: function(discardQueue) { + var me = this, + queued = me.eventQueue, + qLen, q; + if (me.eventsSuspended && !--me.eventsSuspended) { + delete me.eventQueue; + if (!discardQueue && queued) { + qLen = queued.length; + for (q = 0; q < qLen; q++) { + // Important to call fireEventArgs here so MVC can hook in + me.fireEventArgs.apply(me, queued[q]); + } + } + } + }, + /** + * Relays selected events from the specified Observable as if the events were fired by `this`. + * + * For example if you are extending Grid, you might decide to forward some events from store. + * So you can do this inside your initComponent: + * + * this.relayEvents(this.getStore(), ['load']); + * + * The grid instance will then have an observable 'load' event which will be passed + * the parameters of the store's load event and any function fired with the grid's + * load event would have access to the grid using the this keyword (unless the event + * is handled by a controller's control/listen event listener in which case 'this' + * will be the controller rather than the grid). + * + * @param {Object} origin The Observable whose events this object is to relay. + * @param {String[]/Object} events Array of event names to relay or an Object with key/value + * pairs translating to ActualEventName/NewEventName respectively. For example: + * this.relayEvents(this, {add:'push', remove:'pop'}); + * + * Would now redispatch the add event of this as a push event and the remove event as a pop event. + * + * @param {String} [prefix] A common prefix to prepend to the event names. For example: + * + * this.relayEvents(this.getStore(), ['load', 'clear'], 'store'); + * + * Now the grid will forward 'load' and 'clear' events of store as 'storeload' and 'storeclear'. + * + * @return {Object} A `Destroyable` object. An object which implements the `destroy` method which, when destroyed, removes all relayers. For example: + * + * this.storeRelayers = this.relayEvents(this.getStore(), ['load', 'clear'], 'store'); + * + * Can be undone by calling + * + * Ext.destroy(this.storeRelayers); + * + * or + * this.store.relayers.destroy(); + */ + relayEvents: function(origin, events, prefix) { + var me = this, + len = events.length, + i = 0, + oldName, newName, + relayers = {}; + if (Ext.isObject(events)) { + for (i in events) { + newName = events[i]; + relayers[i] = me.createRelayer(newName); + } + } else { + for (; i < len; i++) { + oldName = events[i]; + // Build up the listener hash. + relayers[oldName] = me.createRelayer(prefix ? prefix + oldName : oldName); + } + } + // Add the relaying listeners as ManagedListeners so that they are removed when this.clearListeners is called (usually when _this_ is destroyed) + // Explicitly pass options as undefined so that the listener does not get an extra options param + // which then has to be sliced off in the relayer. + me.mon(origin, relayers, null, null, undefined); + // relayed events are always destroyable. + return new ListenerRemover(me, origin, relayers); + }, + /** + * @private + * Creates an event handling function which re-fires the event from this object as the passed event name. + * @param {String} newName The name under which to re-fire the passed parameters. + * @param {Array} beginEnd (optional) The caller can specify on which indices to slice. + * @return {Function} + */ + createRelayer: function(newName, beginEnd) { + var me = this; + return function() { + return me.fireEventArgs.call(me, newName, beginEnd ? arraySlice.apply(arguments, beginEnd) : arguments); + }; + }, + /** + * Enables events fired by this Observable to bubble up an owner hierarchy by calling `this.getBubbleTarget()` if + * present. There is no implementation in the Observable base class. + * + * This is commonly used by Ext.Components to bubble events to owner Containers. + * See {@link Ext.Component#getBubbleTarget}. The default implementation in Ext.Component returns the + * Component's immediate owner. But if a known target is required, this can be overridden to access the + * required target more quickly. + * + * Example: + * + * Ext.define('Ext.overrides.form.field.Base', { + * override: 'Ext.form.field.Base', + * + * // Add functionality to Field's initComponent to enable the change event to bubble + * initComponent: function () { + * this.callParent(); + * this.enableBubble('change'); + * } + * }); + * + * var myForm = Ext.create('Ext.form.Panel', { + * title: 'User Details', + * items: [{ + * ... + * }], + * listeners: { + * change: function() { + * // Title goes red if form has been modified. + * myForm.header.setStyle('color', 'red'); + * } + * } + * }); + * + * @param {String/String[]} eventNames The event name to bubble, or an Array of event names. + */ + enableBubble: function(eventNames) { + if (eventNames) { + var me = this, + names = (typeof eventNames == 'string') ? arguments : eventNames, + // we must create events now if we have not yet + events = me.events, + length = events && names.length, + ename, event, i; + for (i = 0; i < length; ++i) { + ename = names[i]; + ename = Ext.canonicalEventName(ename); + event = events[ename]; + if (!event || !event.isEvent) { + event = me._initEvent(ename); + } + // Event must fire if it bubbles (We don't know if anyone up the + // bubble hierarchy has listeners added) + me.hasListeners._incr_(ename); + event.bubble = true; + } + } + }, + /** + * @private + * Destructor for classes that extend Observable. + */ + destroy: function() { + this.clearListeners(); + this.callParent(); + this.destroyObservable(true); + }, + destroyObservable: function(skipClearListeners) { + var me = this, + clearPropertiesOnDestroy = me.clearPropertiesOnDestroy; + if (me.$observableDestroyed) { + return; + } + if (!skipClearListeners) { + me.clearListeners(); + } + // This method is called after the Base destructor, and most of the instances + // should be already destroyed at this point. However Classic Components are + // conditionally destructible and so can possibly *not* be destroyed before + // our mixed-in destructor is called. Component's destructor will take care + // of that by calling this method explicitly. + if (me.destroyed) { + if (clearPropertiesOnDestroy) { + if (clearPropertiesOnDestroy === true && !me.$nulled) { + me.$reap(); + } + // At this point we can safely assume that the instance is completely + // destroyed and should not be able to fire events anymore. We don't + // want to do this when the prototype is going to be cleared below, + // because having these emptyFns on the object instance will defy + // the purpose of prototype clearing. + if (!me.clearPrototypeOnDestroy) { + me.fireEvent = me.fireEventArgs = me.fireAction = me.fireEventedAction = Ext.emptyFn; + } + // We do not null hasListeners reference since it's a) very special, + // and b) can't possibly lead to significant leaks. (In theory, right). + me.events = me.managedListeners = me.eventedBeforeEventNames = null; + me.$observableDestroyed = true; + } + // Due to the way Observable mixin installs the after handler, + // this can be called twice in a row. Doing that the second time + // will most probably blow up on some method call -- and that is + // totally what we are about, except in this particular case. + if (me.clearPrototypeOnDestroy && Object.setPrototypeOf && !me.$alreadyNulled) { + Object.setPrototypeOf(me, null); + me.$alreadyNulled = true; + } + } + }, + privates: { + doAddListener: function(ename, fn, scope, options, order, caller, manager) { + var me = this, + ret = false, + event, priority; + order = order || (options && options.order); + if (order) { + priority = (options && options.priority); + if (!priority) { + // priority option takes precedence over order + // do not mutate the user's options + options = options ? Ext.Object.chain(options) : {}; + options.priority = me.$orderToPriority[order]; + } + } + ename = Ext.canonicalEventName(ename); + if (!fn) { + Ext.raise("Cannot add '" + ename + "' listener to " + me.$className + " instance. No function specified."); + } + event = (me.events || (me.events = {}))[ename]; + if (!event || !event.isEvent) { + event = me._initEvent(ename); + } + if (fn !== emptyFn) { + // Check whether the listener should be managed. + // Event#addListener will add it to the manager's managedListeners stack + // upon successful add of the listener to the event. + if (!manager && (scope && scope.isObservable && (scope !== me))) { + manager = scope; + } + if (event.addListener(fn, scope, options, caller, manager)) { + // If a new listener has been added (Event.addListener rejects duplicates of the same fn+scope) + // then increment the hasListeners counter + me.hasListeners._incr_(ename); + ret = true; + } + } + return ret; + }, + doRemoveListener: function(ename, fn, scope) { + var me = this, + ret = false, + events = me.events, + event; + ename = Ext.canonicalEventName(ename); + event = events && events[ename]; + if (!fn) { + Ext.raise("Cannot remove '" + ename + "' listener to " + me.$className + " instance. No function specified."); + } + if (event && event.isEvent) { + if (event.removeListener(fn, scope)) { + me.hasListeners._decr_(ename); + ret = true; + } + } + return ret; + }, + _initEvent: function(eventName) { + return (this.events[eventName] = new Ext.util.Event(this, eventName)); + } + }, + deprecated: { + '5.0': { + methods: { + addEvents: null + } + } + } + }; +}, function() { + var Observable = this, + proto = Observable.prototype, + HasListeners = function() {}, + prepareMixin = function(T) { + if (!T.HasListeners) { + var proto = T.prototype; + // Keep track of whether we were added via a mixin or not, this becomes + // important later when discovering merged listeners on the class. + proto.$observableMixedIn = 1; + // Classes that use us as a mixin (best practice) need to be prepared. + Observable.prepareClass(T, this); + // Now that we are mixed in to class T, we need to watch T for derivations + // and prepare them also. + T.onExtended(function(U, data) { + Ext.classSystemMonitor && Ext.classSystemMonitor('extend mixin', arguments); + Observable.prepareClass(U, null, data); + }); + // Also, if a class uses us as a mixin and that class is then used as + // a mixin, we need to be notified of that as well. + if (proto.onClassMixedIn) { + // play nice with other potential overrides... + Ext.override(T, { + onClassMixedIn: function(U) { + prepareMixin.call(this, U); + this.callParent(arguments); + } + }); + } else { + // just us chickens, so add the method... + proto.onClassMixedIn = function(U) { + prepareMixin.call(this, U); + }; + } + } + superOnClassMixedIn.call(this, T); + }, + // We are overriding the onClassMixedIn of Ext.Mixin. Save a reference to it + // so we can call it after our onClassMixedIn. + superOnClassMixedIn = proto.onClassMixedIn; + HasListeners.prototype = { + //$$: 42 // to make sure we have a proper prototype + _decr_: function(ev, count) { + // count is optionally passed when clearing listeners in bulk + // e.g. when clearListeners is called on a component that has listeners that + // were attached using the "delegate" option + if (count == null) { + count = 1; + } + if (!(this[ev] -= count)) { + // Delete this entry, since 0 does not mean no one is listening, just + // that no one is *directly* listening. This allows the eventBus or + // class observers to "poke" through and expose their presence. + delete this[ev]; + } + }, + _incr_: function(ev) { + if (this.hasOwnProperty(ev)) { + // if we already have listeners at this level, just increment the count... + ++this[ev]; + } else { + // otherwise, start the count at 1 (which hides whatever is in our prototype + // chain)... + this[ev] = 1; + } + } + }; + proto.HasListeners = Observable.HasListeners = HasListeners; + Observable.createAlias({ + /** + * @method on + * @inheritdoc Ext.util.Observable#method-addListener + */ + on: 'addListener', + /** + * @method un + * Shorthand for {@link #removeListener}. + * @inheritdoc Ext.util.Observable#method-removeListener + */ + un: 'removeListener', + /** + * @method mon + * Shorthand for {@link #addManagedListener}. + * @inheritdoc Ext.util.Observable#method-addManagedListener + */ + mon: 'addManagedListener', + /** + * @method mun + * Shorthand for {@link #removeManagedListener}. + * @inheritdoc Ext.util.Observable#method-removeManagedListener + */ + mun: 'removeManagedListener', + /** + * @method + * An alias for {@link Ext.util.Observable#addListener addListener}. In + * versions prior to 5.1, {@link #listeners} had a generated setter which could + * be called to add listeners. In 5.1 the listeners config is not processed + * using the config system and has no generated setter, so this method is + * provided for backward compatibility. The preferred way of adding listeners + * is to use the {@link #on} method. + * @param {Object} listeners The listeners + */ + setListeners: 'addListener' + }); + //deprecated, will be removed in 5.0 + Observable.observeClass = Observable.observe; + // Used by Ext.mixin.Hookable to create sequences. + function getMethodEvent(method) { + var event = (this.methodEvents = this.methodEvents || {})[method], + returnValue, v, cancel, + me = this, + makeCall; + if (!event) { + me.methodEvents[method] = event = {}; + event.originalFn = me[method]; + event.methodName = method; + event.before = []; + event.after = []; + makeCall = function(fn, scope, args) { + scope = scope || me; + if (typeof fn === 'string') { + fn = scope[fn]; + } + if ((v = fn.apply(scope, args)) !== undefined) { + if (typeof v == 'object') { + if (v.returnValue !== undefined) { + returnValue = v.returnValue; + } else { + returnValue = v; + } + cancel = !!v.cancel; + } else if (v === false) { + cancel = true; + } else { + returnValue = v; + } + } + }; + me[method] = function() { + var args = Array.prototype.slice.call(arguments, 0), + argsLen = args.length, + b, i, len; + returnValue = v = undefined; + cancel = false; + for (i = 0 , len = event.before.length; i < len; i++) { + b = event.before[i]; + if (b.extraArgs) { + args.push.apply(args, b.extraArgs); + } + makeCall(b.fn, b.scope, args); + args.length = argsLen; + if (cancel || b.preventDefault) { + return returnValue; + } + } + if ((v = event.originalFn.apply(me, args)) !== undefined) { + returnValue = v; + } + for (i = 0 , len = event.after.length; i < len; i++) { + b = event.after[i]; + if (b.extraArgs) { + args.push.apply(args, b.extraArgs); + } + makeCall(b.fn, b.scope, args); + args.length = argsLen; + if (cancel || b.preventDefault) { + return returnValue; + } + } + return returnValue; + }; + } + return event; + } + Ext.apply(proto, { + onClassMixedIn: prepareMixin, + // adds an 'interceptor' called before the original method + beforeMethod: function(method, fn, scope, preventDefault, extraArgs) { + getMethodEvent.call(this, method).before.push({ + fn: fn, + scope: scope, + extraArgs: extraArgs, + preventDefault: preventDefault + }); + }, + // adds a 'sequence' called after the original method + afterMethod: function(method, fn, scope, preventDefault, extraArgs) { + getMethodEvent.call(this, method).after.push({ + fn: fn, + scope: scope, + extraArgs: extraArgs, + preventDefault: preventDefault + }); + }, + removeMethodListener: function(method, fn, scope) { + var e = getMethodEvent.call(this, method), + i, len; + for (i = 0 , len = e.before.length; i < len; i++) { + if (e.before[i].fn == fn && e.before[i].scope == scope) { + Ext.Array.erase(e.before, i, 1); + return; + } + } + for (i = 0 , len = e.after.length; i < len; i++) { + if (e.after[i].fn == fn && e.after[i].scope == scope) { + Ext.Array.erase(e.after, i, 1); + return; + } + } + }, + toggleEventLogging: function(toggle) { + Ext.util.Observable[toggle ? 'capture' : 'releaseCapture'](this, function(en) { + if (Ext.isDefined(Ext.global.console)) { + Ext.global.console.log(en, arguments); + } + }); + } + }); +}); + +/** + * Represents a collection of a set of key and value pairs. Each key in the HashMap + * must be unique, the same key cannot exist twice. Access to items is provided via + * the key only. Sample usage: + * + * var map = new Ext.util.HashMap(); + * map.add('key1', 1); + * map.add('key2', 2); + * map.add('key3', 3); + * + * map.each(function(key, value, length){ + * console.log(key, value, length); + * }); + * + * The HashMap is an unordered class, + * there is no guarantee when iterating over the items that they will be in any particular + * order. If this is required, then use a {@link Ext.util.MixedCollection}. + */ +Ext.define('Ext.util.HashMap', { + mixins: [ + 'Ext.mixin.Observable' + ], + /** + * Mutation counter which is incremented upon add and remove. + * @readonly + */ + generation: 0, + config: { + /** + * @cfg {Function} keyFn A function that is used to retrieve a default key for a passed object. + * A default is provided that returns the `id` property on the object. This function is only used + * if the `add` method is called with a single argument. + */ + keyFn: null + }, + /** + * @event add + * Fires when a new item is added to the hash. + * @param {Ext.util.HashMap} this + * @param {String} key The key of the added item. + * @param {Object} value The value of the added item. + */ + /** + * @event clear + * Fires when the hash is cleared. + * @param {Ext.util.HashMap} this + */ + /** + * @event remove + * Fires when an item is removed from the hash. + * @param {Ext.util.HashMap} this + * @param {String} key The key of the removed item. + * @param {Object} value The value of the removed item. + */ + /** + * @event replace + * Fires when an item is replaced in the hash. + * @param {Ext.util.HashMap} this + * @param {String} key The key of the replaced item. + * @param {Object} value The new value for the item. + * @param {Object} old The old value for the item. + */ + /** + * Creates new HashMap. + * @param {Object} config (optional) Config object. + */ + constructor: function(config) { + var me = this, + fn; + // Will call initConfig + me.mixins.observable.constructor.call(me, config); + me.clear(true); + fn = me.getKeyFn(); + if (fn) { + me.getKey = fn; + } + }, + /** + * Gets the number of items in the hash. + * @return {Number} The number of items in the hash. + */ + getCount: function() { + return this.length; + }, + /** + * Implementation for being able to extract the key from an object if only + * a single argument is passed. + * @private + * @param {String} key The key + * @param {Object} value The value + * @return {Array} [key, value] + */ + getData: function(key, value) { + // if we have no value, it means we need to get the key from the object + if (value === undefined) { + value = key; + key = this.getKey(value); + } + return [ + key, + value + ]; + }, + /** + * Extracts the key from an object. This is a default implementation, it may be overridden + * @param {Object} o The object to get the key from + * @return {String} The key to use. + */ + getKey: function(o) { + return o.id; + }, + /** + * Adds an item to the collection. Fires the {@link #event-add} event when complete. + * + * @param {String/Object} key The key to associate with the item, or the new item. + * + * If a {@link #getKey} implementation was specified for this HashMap, + * or if the key of the stored items is in a property called `id`, + * the HashMap will be able to *derive* the key for the new item. + * In this case just pass the new item in this parameter. + * + * @param {Object} [value] The item to add. + * @return {Object} The item added. + */ + add: function(key, value) { + var me = this; + // Need to check arguments length here, since we could have called: + // map.add('foo', undefined); + if (arguments.length === 1) { + value = key; + key = me.getKey(value); + } + if (me.containsKey(key)) { + return me.replace(key, value); + } + me.map[key] = value; + ++me.length; + me.generation++; + if (me.hasListeners.add) { + me.fireEvent('add', me, key, value); + } + return value; + }, + /** + * Replaces an item in the hash. If the key doesn't exist, the + * {@link #method-add} method will be used. + * @param {String} key The key of the item. + * @param {Object} value The new value for the item. + * @return {Object} The new value of the item. + */ + replace: function(key, value) { + var me = this, + map = me.map, + old; + // Need to check arguments length here, since we could have called: + // map.replace('foo', undefined); + if (arguments.length === 1) { + value = key; + key = me.getKey(value); + } + if (!me.containsKey(key)) { + me.add(key, value); + } + old = map[key]; + map[key] = value; + me.generation++; + if (me.hasListeners.replace) { + me.fireEvent('replace', me, key, value, old); + } + return value; + }, + /** + * Remove an item from the hash. + * @param {Object} o The value of the item to remove. + * @return {Boolean} True if the item was successfully removed. + */ + remove: function(o) { + var key = this.findKey(o); + if (key !== undefined) { + return this.removeAtKey(key); + } + return false; + }, + /** + * Remove an item from the hash. + * @param {String} key The key to remove. + * @return {Boolean} True if the item was successfully removed. + */ + removeAtKey: function(key) { + var me = this, + value; + if (me.containsKey(key)) { + value = me.map[key]; + delete me.map[key]; + --me.length; + me.generation++; + if (me.hasListeners.remove) { + me.fireEvent('remove', me, key, value); + } + return true; + } + return false; + }, + /** + * Retrieves an item with a particular key. + * @param {String} key The key to lookup. + * @return {Object} The value at that key. If it doesn't exist, `undefined` is returned. + */ + get: function(key) { + var map = this.map; + return map.hasOwnProperty(key) ? map[key] : undefined; + }, + /** + * @ignore + */ + clear: function(initial) { + // We use the above syntax because we don't want the initial param to be part of the public API + var me = this; + // Only clear if it has ever had any content + if (initial || me.generation) { + me.map = {}; + me.length = 0; + me.generation = initial ? 0 : me.generation + 1; + } + if (initial !== true && me.hasListeners.clear) { + me.fireEvent('clear', me); + } + return me; + }, + /** + * Checks whether a key exists in the hash. + * @param {String} key The key to check for. + * @return {Boolean} True if they key exists in the hash. + */ + containsKey: function(key) { + var map = this.map; + return map.hasOwnProperty(key) && map[key] !== undefined; + }, + /** + * Checks whether a value exists in the hash. + * @param {Object} value The value to check for. + * @return {Boolean} True if the value exists in the dictionary. + */ + contains: function(value) { + return this.containsKey(this.findKey(value)); + }, + /** + * Return all of the keys in the hash. + * @return {Array} An array of keys. + */ + getKeys: function() { + return this.getArray(true); + }, + /** + * Return all of the values in the hash. + * @return {Array} An array of values. + */ + getValues: function() { + return this.getArray(false); + }, + /** + * Gets either the keys/values in an array from the hash. + * @private + * @param {Boolean} isKey True to extract the keys, otherwise, the value + * @return {Array} An array of either keys/values from the hash. + */ + getArray: function(isKey) { + var arr = [], + key, + map = this.map; + for (key in map) { + if (map.hasOwnProperty(key)) { + arr.push(isKey ? key : map[key]); + } + } + return arr; + }, + /** + * Executes the specified function once for each item in the hash. + * Returning false from the function will cease iteration. + * + * @param {Function} fn The function to execute. + * @param {String} fn.key The key of the item. + * @param {Number} fn.value The value of the item. + * @param {Number} fn.length The total number of items in the hash. + * @param {Object} [scope] The scope to execute in. Defaults to this. + * @return {Ext.util.HashMap} this + */ + each: function(fn, scope) { + // copy items so they may be removed during iteration. + var items = Ext.apply({}, this.map), + key, + length = this.length; + scope = scope || this; + for (key in items) { + if (items.hasOwnProperty(key)) { + if (fn.call(scope, key, items[key], length) === false) { + break; + } + } + } + return this; + }, + /** + * Performs a shallow copy on this hash. + * @return {Ext.util.HashMap} The new hash object. + */ + clone: function() { + var hash = new this.self(this.initialConfig), + map = this.map, + key; + hash.suspendEvents(); + for (key in map) { + if (map.hasOwnProperty(key)) { + hash.add(key, map[key]); + } + } + hash.resumeEvents(); + return hash; + }, + /** + * @private + * Find the key for a value. + * @param {Object} value The value to find. + * @return {Object} The value of the item. Returns undefined if not found. + */ + findKey: function(value) { + var key, + map = this.map; + for (key in map) { + if (map.hasOwnProperty(key) && map[key] === value) { + return key; + } + } + return undefined; + } +}, function(HashMap) { + var prototype = HashMap.prototype; + /** + * @method removeByKey + * An alias for {@link #removeAtKey} + * @inheritdoc Ext.util.HashMap#removeAtKey + */ + prototype.removeByKey = prototype.removeAtKey; +}); + +/** + * Base Manager class + * @private + * @deprecated 5.0.0 Will be removed in 7.0. + */ +Ext.define('Ext.AbstractManager', { + /* Begin Definitions */ + requires: [ + 'Ext.util.HashMap' + ], + /* End Definitions */ + typeName: 'type', + constructor: function(config) { + Ext.apply(this, config || {}); + /** + * @property {Ext.util.HashMap} all + * Contains all of the items currently managed + */ + this.all = new Ext.util.HashMap(); + this.types = {}; + }, + /** + * Returns an item by id. + * For additional details see {@link Ext.util.HashMap#get}. + * @param {String} id The id of the item + * @return {Object} The item, undefined if not found. + */ + get: function(id) { + return this.all.get(id); + }, + /** + * Registers an item to be managed + * @param {Object} item The item to register + */ + register: function(item) { + var key = this.all.getKey(item); + if (key === undefined) { + Ext.raise('Key is undefined. Please ensure the item has a key before registering the item.'); + } + if (this.all.containsKey(key)) { + Ext.raise('Registering duplicate id "' + key + '" with ' + this.$className); + } + this.all.add(item); + }, + /** + * Unregisters an item by removing it from this manager + * @param {Object} item The item to unregister + */ + unregister: function(item) { + this.all.remove(item); + }, + /** + * Registers a new item constructor, keyed by a type key. + * @param {String} type The mnemonic string by which the class may be looked up. + * @param {Function} cls The new instance class. + */ + registerType: function(type, cls) { + this.types[type] = cls; + cls[this.typeName] = type; + }, + /** + * Checks if an item type is registered. + * @param {String} type The mnemonic string by which the class may be looked up + * @return {Boolean} Whether the type is registered. + */ + isRegistered: function(type) { + return this.types[type] !== undefined; + }, + /** + * Creates and returns an instance of whatever this manager manages, based on the supplied type and + * config object. + * @param {Object} config The config object + * @param {String} defaultType If no type is discovered in the config object, we fall back to this type + * @return {Object} The instance of whatever this manager is managing + */ + create: function(config, defaultType) { + var type = config[this.typeName] || config.type || defaultType, + Constructor = this.types[type]; + if (Constructor === undefined) { + Ext.raise("The '" + type + "' type has not been registered with this manager"); + } + return new Constructor(config); + }, + /** + * Registers a function that will be called when an item with the specified id is added to the manager. + * This will happen on instantiation. + * @param {String} id The item id + * @param {Function} fn The callback function. Called with a single parameter, the item. + * @param {Object} scope The scope (this reference) in which the callback is executed. + * Defaults to the item. + */ + onAvailable: function(id, fn, scope) { + var all = this.all, + item, callback; + if (all.containsKey(id)) { + item = all.get(id); + fn.call(scope || item, item); + } else { + callback = function(map, key, item) { + if (key == id) { + fn.call(scope || item, item); + all.un('add', callback); + } + }; + all.on('add', callback); + } + }, + /** + * Executes the specified function once for each item in the collection. + * @param {Function} fn The function to execute. + * @param {String} fn.key The key of the item + * @param {Number} fn.value The value of the item + * @param {Number} fn.length The total number of items in the collection + * @param {Boolean} fn.return False to cease iteration. + * @param {Object} scope The scope to execute in. Defaults to `this`. + */ + each: function(fn, scope) { + this.all.each(fn, scope || this); + }, + /** + * Gets the number of items in the collection. + * @return {Number} The number of items in the collection. + */ + getCount: function() { + return this.all.getCount(); + } +}); + +/* + Ext.promise.Consequence adapted from: + [DeftJS](https://github.com/deftjs/deftjs5) + Copyright (c) 2012-2013 [DeftJS Framework Contributors](http://deftjs.org) + Open source under the [MIT License](http://en.wikipedia.org/wiki/MIT_License). + */ +/** + * Consequences are used internally by a Deferred to capture and notify callbacks, and + * propagate their transformed results as fulfillment or rejection. + * + * Developers never directly interact with a Consequence. + * + * A Consequence forms a chain between two Deferreds, where the result of the first + * Deferred is transformed by the corresponding callback before being applied to the + * second Deferred. + * + * Each time a Deferred's `then` method is called, it creates a new Consequence that will + * be triggered once its originating Deferred has been fulfilled or rejected. A Consequence + * captures a pair of optional onFulfilled and onRejected callbacks. + * + * Each Consequence has its own Deferred (which in turn has a Promise) that is resolved or + * rejected when the Consequence is triggered. When a Consequence is triggered by its + * originating Deferred, it calls the corresponding callback and propagates the transformed + * result to its own Deferred; resolved with the callback return value or rejected with any + * error thrown by the callback. + * + * @since 6.0.0 + * @private + */ +Ext.define('Ext.promise.Consequence', function(Consequence) { + return { + /** + * @property {Ext.promise.Promise} + * Promise of the future value of this Consequence. + */ + promise: null, + /** + * @property {Ext.promise.Deferred} deferred Internal Deferred for this Consequence. + * + * @private + */ + deferred: null, + /** + * @property {Function} onFulfilled Callback to execute when this Consequence is triggered + * with a fulfillment value. + * + * @private + */ + onFulfilled: null, + /** + * @property {Function} onRejected Callback to execute when this Consequence is triggered + * with a rejection reason. + * + * @private + */ + onRejected: null, + /** + * @property {Function} onProgress Callback to execute when this Consequence is updated + * with a progress value. + * + * @private + */ + onProgress: null, + /** + * @param {Function} onFulfilled Callback to execute to transform a fulfillment value. + * @param {Function} onRejected Callback to execute to transform a rejection reason. + * @param {Function} onProgress Callback to execute to transform a progress value. + */ + constructor: function(onFulfilled, onRejected, onProgress) { + var me = this; + me.onFulfilled = onFulfilled; + me.onRejected = onRejected; + me.onProgress = onProgress; + me.deferred = new Ext.promise.Deferred(); + me.promise = me.deferred.promise; + }, + /** + * Trigger this Consequence with the specified action and value. + * + * @param {String} action Completion action (i.e. fulfill or reject). + * @param {Mixed} value Fulfillment value or rejection reason. + */ + trigger: function(action, value) { + var me = this, + deferred = me.deferred; + switch (action) { + case 'fulfill': + me.propagate(value, me.onFulfilled, deferred, deferred.resolve); + break; + case 'reject': + me.propagate(value, me.onRejected, deferred, deferred.reject); + break; + } + }, + /** + * Update this Consequence with the specified progress value. + * + * @param {Mixed} progress Progress value. + */ + update: function(progress) { + if (Ext.isFunction(this.onProgress)) { + progress = this.onProgress(progress); + } + this.deferred.update(progress); + }, + /** + * Transform and propagate the specified value using the + * optional callback and propagate the transformed result. + * + * @param {Mixed} value Value to transform and/or propagate. + * @param {Function} [callback] Callback to use to transform the value. + * @param {Function} deferred Deferred to use to propagate the value, if no callback + * was specified. + * @param {Function} deferredMethod Deferred method to call to propagate the value, + * if no callback was specified. + * + * @private + */ + propagate: function(value, callback, deferred, deferredMethod) { + if (Ext.isFunction(callback)) { + this.schedule(function() { + try { + deferred.resolve(callback(value)); + } catch (e) { + deferred.reject(e); + } + }); + } else { + deferredMethod.call(this.deferred, value); + } + }, + /** + * Schedules the specified callback function to be executed on the next turn of the + * event loop. + * + * @param {Function} callback Callback function. + * + * @private + */ + schedule: function(callback) { + var n = Consequence.queueSize++; + Consequence.queue[n] = callback; + if (!n) { + // if (queue was empty) + Ext.asap(Consequence.dispatch); + } + }, + statics: { + /** + * @property {Function[]} queue The queue of callbacks pending. This array is never + * shrunk to reduce GC thrash but instead its elements will be set to `null`. + * + * @private + */ + queue: new Array(10000), + /** + * @property {Number} queueSize The number of callbacks in the `queue`. + * + * @private + */ + queueSize: 0, + /** + * This method drains the callback queue and calls each callback in order. + * + * @private + */ + dispatch: function() { + var queue = Consequence.queue, + fn, i; + // The queue could grow on each call, so we cannot cache queueSize here. + for (i = 0; i < Consequence.queueSize; ++i) { + fn = queue[i]; + queue[i] = null; + // release our reference on the callback + fn(); + } + Consequence.queueSize = 0; + } + } + }; +}, function(Consequence) { + Consequence.dispatch.$skipTimerCheck = true; +}); + +/* + Ext.promise.Deferred adapted from: + [DeftJS](https://github.com/deftjs/deftjs5) + Copyright (c) 2012-2013 [DeftJS Framework Contributors](http://deftjs.org) + Open source under the [MIT License](http://en.wikipedia.org/wiki/MIT_License). + */ +/** + * Deferreds are the mechanism used to create new Promises. A Deferred has a single + * associated Promise that can be safely returned to external consumers to ensure they do + * not interfere with the resolution or rejection of the deferred operation. + * + * A Deferred is typically used within the body of a function that performs an asynchronous + * operation. When that operation succeeds, the Deferred should be resolved; if that + * operation fails, the Deferred should be rejected. + * + * Each Deferred has an associated Promise. A Promise delegates `then` calls to its + * Deferred's `then` method. In this way, access to Deferred operations are divided between + * producer (Deferred) and consumer (Promise) roles. + * + * When a Deferred's `resolve` method is called, it fulfills with the optionally specified + * value. If `resolve` is called with a then-able (i.e.a Function or Object with a `then` + * function, such as another Promise) it assimilates the then-able's result; the Deferred + * provides its own `resolve` and `reject` methods as the onFulfilled or onRejected + * arguments in a call to that then-able's `then` function. If an error is thrown while + * calling the then-able's `then` function (prior to any call back to the specified + * `resolve` or `reject` methods), the Deferred rejects with that error. If a Deferred's + * `resolve` method is called with its own Promise, it rejects with a TypeError. + * + * When a Deferred's `reject` method is called, it rejects with the optionally specified + * reason. + * + * Each time a Deferred's `then` method is called, it captures a pair of optional + * onFulfilled and onRejected callbacks and returns a Promise of the Deferred's future + * value as transformed by those callbacks. + * + * @private + * @since 6.0.0 + */ +Ext.define('Ext.promise.Deferred', { + requires: [ + 'Ext.promise.Consequence' + ], + /** + * @property {Ext.promise.Promise} promise Promise of the future value of this Deferred. + */ + promise: null, + /** + * @property {Ext.promise.Consequence[]} consequences Pending Consequences chained to this Deferred. + * + * @private + */ + consequences: [], + /** + * @property {Boolean} completed Indicates whether this Deferred has been completed. + * + * @private + */ + completed: false, + /** + * @property {String} completeAction The completion action (i.e. 'fulfill' or 'reject'). + * + * @private + */ + completionAction: null, + /** + * @property {Mixed} completionValue The completion value (i.e. resolution value or rejection error). + * + * @private + */ + completionValue: null, + constructor: function() { + var me = this; + me.promise = new Ext.promise.Promise(me); + me.consequences = []; + me.completed = false; + me.completionAction = null; + me.completionValue = null; + }, + /** + * Used to specify onFulfilled and onRejected callbacks that will be + * notified when the future value becomes available. + * + * Those callbacks can subsequently transform the value that was + * fulfilled or the error that was rejected. Each call to `then` + * returns a new Promise of that transformed value; i.e., a Promise + * that is fulfilled with the callback return value or rejected with + * any error thrown by the callback. + * + * @param {Function} [onFulfilled] Callback to execute to transform a fulfillment value. + * @param {Function} [onRejected] Callback to execute to transform a rejection reason. + * @param {Function} [onProgress] Callback to execute to transform a progress value. + * + * @return Promise that is fulfilled with the callback return value or rejected with + * any error thrown by the callback. + */ + then: function(onFulfilled, onRejected, onProgress) { + var me = this, + consequence = new Ext.promise.Consequence(onFulfilled, onRejected, onProgress); + if (me.completed) { + consequence.trigger(me.completionAction, me.completionValue); + } else { + me.consequences.push(consequence); + } + return consequence.promise; + }, + /** + * Resolve this Deferred with the (optional) specified value. + * + * If called with a then-able (i.e.a Function or Object with a `then` + * function, such as another Promise) it assimilates the then-able's + * result; the Deferred provides its own `resolve` and `reject` methods + * as the onFulfilled or onRejected arguments in a call to that + * then-able's `then` function. If an error is thrown while calling + * the then-able's `then` function (prior to any call back to the + * specified `resolve` or `reject` methods), the Deferred rejects with + * that error. If a Deferred's `resolve` method is called with its own + * Promise, it rejects with a TypeError. + * + * Once a Deferred has been fulfilled or rejected, it is considered to be complete + * and subsequent calls to `resolve` or `reject` are ignored. + * + * @param {Mixed} value Value to resolve as either a fulfillment value or rejection + * reason. + */ + resolve: function(value) { + var me = this, + isHandled, thenFn; + if (me.completed) { + return; + } + try { + if (value === me.promise) { + throw new TypeError('A Promise cannot be resolved with itself.'); + } + if (value != null && (typeof value === 'object' || Ext.isFunction(value)) && Ext.isFunction(thenFn = value.then)) { + isHandled = false; + try { + thenFn.call(value, function(value) { + if (!isHandled) { + isHandled = true; + me.resolve(value); + } + }, function(error) { + if (!isHandled) { + isHandled = true; + me.reject(error); + } + }); + } catch (e1) { + if (!isHandled) { + me.reject(e1); + } + } + } else { + me.complete('fulfill', value); + } + } catch (e2) { + me.reject(e2); + } + }, + /** + * Reject this Deferred with the specified reason. + * + * Once a Deferred has been rejected, it is considered to be complete + * and subsequent calls to `resolve` or `reject` are ignored. + * + * @param {Error} reason Rejection reason. + */ + reject: function(reason) { + if (this.completed) { + return; + } + this.complete('reject', reason); + }, + /** + * Updates progress for this Deferred, if it is still pending, triggering it to + * execute the `onProgress` callback and propagate the resulting transformed progress + * value to Deferreds that originate from this Deferred. + * + * @param {Mixed} progress The progress value. + */ + update: function(progress) { + var consequences = this.consequences, + consequence, i, len; + if (this.completed) { + return; + } + for (i = 0 , len = consequences.length; i < len; i++) { + consequence = consequences[i]; + consequence.update(progress); + } + }, + /** + * Complete this Deferred with the specified action and value. + * + * @param {String} action Completion action (i.e. 'fufill' or 'reject'). + * @param {Mixed} value Fulfillment value or rejection reason. + * + * @private + */ + complete: function(action, value) { + var me = this, + consequences = me.consequences, + consequence, i, len; + me.completionAction = action; + me.completionValue = value; + me.completed = true; + for (i = 0 , len = consequences.length; i < len; i++) { + consequence = consequences[i]; + consequence.trigger(me.completionAction, me.completionValue); + } + me.consequences = null; + } +}); + +/* + Ext.promise.Deferred adapted from: + [DeftJS](https://github.com/deftjs/deftjs5) + Copyright (c) 2012-2014 [DeftJS Framework Contributors](http://deftjs.org) + Open source under the [MIT License](http://en.wikipedia.org/wiki/MIT_License). + */ +/** + * Promises represent a future value; i.e., a value that may not yet be available. + * + * Users should **not** create instances of this class directly. Instead user code should + * use `new {@link Ext.Promise}()` or `new {@link Ext.Deferred}()` to create and manage + * promises. If the browser supports the standard `Promise` constructor, this class will + * not be used by `Ext.Promise`. This class will always be used by `Ext.Deferred` in order + * to provide enhanced capabilities beyond standard promises. + * + * A Promise's `{@link #then then()}` method is used to specify onFulfilled and onRejected + * callbacks that will be notified when the future value becomes available. Those callbacks + * can subsequently transform the value that was resolved or the reason that was rejected. + * Each call to `then` returns a new Promise of that transformed value; i.e., a Promise + * that is resolved with the callback return value or rejected with any error thrown by + * the callback. + * + * ## Basic Usage + * + * this.companyService.loadCompanies().then( + * function (records) { + * // Do something with result. + * }, + * function (error) { + * // Do something on failure. + * }). + * always(function () { + * // Do something whether call succeeded or failed + * }); + * + * The above code uses the `Promise` returned from the `companyService.loadCompanies()` + * method and uses `then()` to attach success and failure handlers. Finally, an `always()` + * method call is chained onto the returned promise. This specifies a callback function + * that will run whether the underlying call succeeded or failed. + * + * See `{@link Ext.Deferred}` for an example of using the returned Promise. + * + * [1]: http://wiki.ecmascript.org/doku.php?id=harmony:specification_drafts#april_14_2015_rev_38_final_draft + * + * @since 6.0.0 + */ +Ext.define('Ext.promise.Promise', function(ExtPromise) { + var Deferred; + return { + requires: [ + 'Ext.promise.Deferred' + ], + statics: { + /** + * @property CancellationError + * @static + * The type of `Error` propagated by the `{@link #method-cancel}` method. If + * the browser provides a native `CancellationError` then that type is used. If + * not, a basic `Error` type is used. + */ + CancellationError: Ext.global.CancellationError || Error, + _ready: function() { + // Our requires are met, so we can cache Ext.promise.Deferred + Deferred = Ext.promise.Deferred; + }, + /** + * Returns a new Promise that will only resolve once all the specified + * `promisesOrValues` have resolved. + * + * The resolution value will be an Array containing the resolution value of each + * of the `promisesOrValues`. + * + * The public API's to use instead of this method are `{@link Ext.Promise#all}` + * and `{@link Ext.Deferred#all}`. + * + * @param {Mixed[]/Ext.promise.Promise[]/Ext.promise.Promise} promisesOrValues An + * Array of values or Promises, or a Promise of an Array of values or Promises. + * @return {Ext.promise.Promise} A Promise of an Array of the resolved values. + * + * @static + * @private + */ + all: function(promisesOrValues) { + if (!(Ext.isArray(promisesOrValues) || ExtPromise.is(promisesOrValues))) { + Ext.raise('Invalid parameter: expected an Array or Promise of an Array.'); + } + return ExtPromise.when(promisesOrValues).then(function(promisesOrValues) { + var deferred = new Deferred(), + remainingToResolve = promisesOrValues.length, + results = new Array(remainingToResolve), + index, promiseOrValue, resolve, i, len; + if (!remainingToResolve) { + deferred.resolve(results); + } else { + resolve = function(item, index) { + return ExtPromise.when(item).then(function(value) { + results[index] = value; + if (!--remainingToResolve) { + deferred.resolve(results); + } + return value; + }, function(reason) { + return deferred.reject(reason); + }); + }; + for (index = i = 0 , len = promisesOrValues.length; i < len; index = ++i) { + promiseOrValue = promisesOrValues[index]; + if (index in promisesOrValues) { + resolve(promiseOrValue, index); + } else { + remainingToResolve--; + } + } + } + return deferred.promise; + }); + }, + /** + * Determines whether the specified value is a Promise (including third-party + * untrusted Promises or then()-ables), based on the Promises/A specification + * feature test. + * + * @param {Mixed} value A potential Promise. + * @return {Boolean} `true` if the given value is a Promise, otherwise `false`. + * @static + * @private + */ + is: function(value) { + return value != null && (typeof value === 'object' || Ext.isFunction(value)) && Ext.isFunction(value.then); + }, + /** + * Returns a promise that resolves or rejects as soon as one of the promises in the array resolves + * or rejects, with the value or reason from that promise. + * @param {Ext.promise.Promise[]} promises The promises. + * @return {Ext.promise.Promise} The promise to be resolved when the race completes. + * + * @private + * @static + * @since 6.5.0 + */ + race: function(promises) { + if (!Ext.isArray(promises)) { + Ext.raise('Invalid parameter: expected an Array.'); + } + var deferred = new Deferred(), + len = promises.length, + i; + for (i = 0; i < len; ++i) { + deferred.resolve(promises[i]); + } + return deferred.promise; + }, + /** + * Rethrows the specified Error on the next turn of the event loop. + * @static + * @private + */ + rethrowError: function(error) { + Ext.asap(function() { + throw error; + }); + }, + /** + * Returns a new Promise that either + * + * * Resolves immediately for the specified value, or + * * Resolves or rejects when the specified promise (or third-party Promise or + * then()-able) is resolved or rejected. + * + * The public API's to use instead of this method are `{@link Ext.Promise#resolve}` + * and `{@link Ext.Deferred#resolved}`. + * + * @param {Mixed} value A Promise (or third-party Promise or then()-able) + * or value. + * @return {Ext.Promise} A Promise of the specified Promise or value. + * + * @static + * @private + */ + when: function(value) { + var deferred = new Deferred(); + deferred.resolve(value); + return deferred.promise; + } + }, + /** + * @property {Ext.promise.Deferred} Reference to this promise's + * `{@link Ext.promise.Deferred Deferred}` instance. + * + * @readonly + * @private + */ + owner: null, + /** + * NOTE: {@link Ext.promise.Deferred Deferreds} are the mechanism used to create new + * Promises. + * @param {Ext.promise.Deferred} owner The owning `Deferred` instance. + * + * @private + */ + constructor: function(owner) { + this.owner = owner; + }, + /** + * Attaches onFulfilled and onRejected callbacks that will be notified when the future + * value becomes available. + * + * Those callbacks can subsequently transform the value that was fulfilled or the error + * that was rejected. Each call to `then` returns a new Promise of that transformed + * value; i.e., a Promise that is fulfilled with the callback return value or rejected + * with any error thrown by the callback. + * + * @param {Function} onFulfilled Optional callback to execute to transform a + * fulfillment value. + * @param {Function} onRejected Optional callback to execute to transform a rejection + * reason. + * @param {Function} onProgress Optional callback function to be called with progress + * updates. + * @param {Object} scope Optional scope for the callback(s). + * @return {Ext.promise.Promise} Promise that is fulfilled with the callback return + * value or rejected with any error thrown by the callback. + */ + then: function(onFulfilled, onRejected, onProgress, scope) { + var ref; + if (arguments.length === 1 && Ext.isObject(arguments[0])) { + ref = arguments[0]; + onFulfilled = ref.success; + onRejected = ref.failure; + onProgress = ref.progress; + scope = ref.scope; + } + if (scope) { + if (onFulfilled) { + onFulfilled = onFulfilled.bind(scope); + } + if (onRejected) { + onRejected = onRejected.bind(scope); + } + if (onProgress) { + onProgress = onProgress.bind(scope); + } + } + return this.owner.then(onFulfilled, onRejected, onProgress); + }, + /** + * Attaches an onRejected callback that will be notified if this Promise is rejected. + * + * The callback can subsequently transform the reason that was rejected. Each call to + * `otherwise` returns a new Promise of that transformed value; i.e., a Promise that + * is resolved with the original resolved value, or resolved with the callback return + * value or rejected with any error thrown by the callback. + * + * @param {Function} onRejected Callback to execute to transform a rejection reason. + * @param {Object} scope Optional scope for the callback. + * @return {Ext.promise.Promise} Promise of the transformed future value. + * + * @since 6.5.0 + */ + 'catch': function(onRejected, scope) { + var ref; + if (arguments.length === 1 && Ext.isObject(arguments[0])) { + ref = arguments[0]; + onRejected = ref.fn; + scope = ref.scope; + } + if (scope != null) { + onRejected = onRejected.bind(scope); + } + return this.owner.then(null, onRejected); + }, + /** + * An alias for the {@link #catch} method. To be used for browsers + * where catch cannot be used as a method name. + */ + otherwise: function(onRejected, scope) { + return this['catch'].apply(this, arguments); + }, + /** + * Attaches an onCompleted callback that will be notified when this Promise is completed. + * + * Similar to `finally` in `try... catch... finally`. + * + * NOTE: The specified callback does not affect the resulting Promise's outcome; any + * return value is ignored and any Error is rethrown. + * + * @param {Function} onCompleted Callback to execute when the Promise is resolved or + * rejected. + * @param {Object} scope Optional scope for the callback. + * @return {Ext.promise.Promise} A new "pass-through" Promise that is resolved with + * the original value or rejected with the original reason. + */ + always: function(onCompleted, scope) { + var ref; + if (arguments.length === 1 && Ext.isObject(arguments[0])) { + ref = arguments[0]; + onCompleted = ref.fn; + scope = ref.scope; + } + if (scope != null) { + onCompleted = onCompleted.bind(scope); + } + return this.owner.then(function(value) { + try { + onCompleted(); + } catch (e) { + ExtPromise.rethrowError(e); + } + return value; + }, function(reason) { + try { + onCompleted(); + } catch (e) { + ExtPromise.rethrowError(e); + } + throw reason; + }); + }, + /** + * Terminates a Promise chain, ensuring that unhandled rejections will be rethrown as + * Errors. + * + * One of the pitfalls of interacting with Promise-based APIs is the tendency for + * important errors to be silently swallowed unless an explicit rejection handler is + * specified. + * + * For example: + * + * promise.then(function () { + * // logic in your callback throws an error and it is interpreted as a + * // rejection. throw new Error("Boom!"); + * }); + * + * // The Error was not handled by the Promise chain and is silently swallowed. + * + * This problem can be addressed by terminating the Promise chain with the done() + * method: + * + * promise.then(function () { + * // logic in your callback throws an error and it is interpreted as a + * // rejection. throw new Error("Boom!"); + * }).done(); + * + * // The Error was not handled by the Promise chain and is rethrown by done() on + * // the next tick. + * + * The `done()` method ensures that any unhandled rejections are rethrown as Errors. + */ + done: function() { + this.owner.then(null, ExtPromise.rethrowError); + }, + /** + * Cancels this Promise if it is still pending, triggering a rejection with a + * `{@link #CancellationError}` that will propagate to any Promises originating from + * this Promise. + * + * NOTE: Cancellation only propagates to Promises that branch from the target Promise. + * It does not traverse back up to parent branches, as this would reject nodes from + * which other Promises may have branched, causing unintended side-effects. + * + * @param {Error} reason Cancellation reason. + */ + cancel: function(reason) { + if (reason == null) { + reason = null; + } + this.owner.reject(new this.self.CancellationError(reason)); + }, + /** + * Logs the resolution or rejection of this Promise with the specified category and + * optional identifier. Messages are logged via all registered custom logger functions. + * + * @param {String} identifier An optional identifier to incorporate into the + * resulting log entry. + * + * @return {Ext.promise.Promise} A new "pass-through" Promise that is resolved with + * the original value or rejected with the original reason. + */ + log: function(identifier) { + if (identifier == null) { + identifier = ''; + } + return this.owner.then(function(value) { + Ext.log("" + (identifier || 'Promise') + " resolved with value: " + value); + return value; + }, function(reason) { + Ext.log("" + (identifier || 'Promise') + " rejected with reason: " + reason); + throw reason; + }); + } + }; +}, function(ExtPromise) { + ExtPromise._ready(); +}); + +/** + * This class provides an API compatible implementation of the ECMAScript 6 Promises API + * (providing an implementation as necessary for browsers that do not natively support the + * `Promise` class). + * + * This class will use the native `Promise` implementation if one is available. The + * native implementation, while standard, does not provide all of the features of the + * Ext JS Promises implementation. + * + * To use the Ext JS enhanced Promises implementation, see `{@link Ext.Deferred}` for + * creating enhanced promises and additional static utility methods. + * + * Typical usage: + * + * function getAjax (url) { + * // The function passed to Ext.Promise() is called immediately to start + * // the asynchronous action. + * // + * return new Ext.Promise(function (resolve, reject) { + * Ext.Ajax.request({ + * url: url, + * + * success: function (response) { + * // Use the provided "resolve" method to deliver the result. + * // + * resolve(response.responseText); + * }, + * + * failure: function (response) { + * // Use the provided "reject" method to deliver error message. + * // + * reject(response.status); + * } + * }); + * }); + * } + * + * getAjax('http://stuff').then(function (content) { + * // content is responseText of ajax response + * }); + * + * To adapt the Ext JS `{@link Ext.data.Store store}` to use a Promise, you might do + * something like this: + * + * loadCompanies: function() { + * var companyStore = this.companyStore; + * + * return new Ext.Promise(function (resolve, reject) { + * companyStore.load({ + * callback: function(records, operation, success) { + * if (success) { + * // Use the provided "resolve" method to drive the promise: + * resolve(records); + * } + * else { + * // Use the provided "reject" method to drive the promise: + * reject("Error loading Companies."); + * } + * } + * }); + * }); + * } + * + * @since 6.0.0 + */ +Ext.define('Ext.Promise', function() { + var Polyfiller; + return { + requires: [ + 'Ext.promise.Promise' + ], + statics: { + _ready: function() { + // We can cache this now that our requires are met + Polyfiller = Ext.promise.Promise; + }, + /** + * Returns a new Promise that will only resolve once all the specified + * `promisesOrValues` have resolved. + * + * The resolution value will be an Array containing the resolution value of each + * of the `promisesOrValues`. + * + * @param {Mixed[]/Ext.Promise[]/Ext.Promise} promisesOrValues An Array of values + * or Promises, or a Promise of an Array of values or Promises. + * + * @return {Ext.Promise} A Promise of an Array of the resolved values. + * @static + */ + all: function() { + return Polyfiller.all.apply(Polyfiller, arguments); + }, + /** + * Returns a promise that resolves or rejects as soon as one of the promises in the array resolves + * or rejects, with the value or reason from that promise. + * @param {Ext.promise.Promise[]} promises The promises. + * @return {Ext.promise.Promise} The promise to be resolved when the race completes. + * + * @static + * @since 6.5.0 + */ + race: function() { + return Polyfiller.race.apply(Polyfiller, arguments); + }, + /** + * Convenience method that returns a new Promise rejected with the specified + * reason. + * + * @param {Error} reason Rejection reason. + * @return {Ext.Promise} The rejected Promise. + * @static + */ + reject: function(reason) { + var deferred = new Ext.promise.Deferred(); + deferred.reject(reason); + return deferred.promise; + }, + /** + * Returns a new Promise that either + * + * * Resolves immediately for the specified value, or + * * Resolves or rejects when the specified promise (or third-party Promise or + * then()-able) is resolved or rejected. + * + * @param {Mixed} value A Promise (or third-party Promise or then()-able) + * or value. + * @return {Ext.Promise} A Promise of the specified Promise or value. + * @static + */ + resolve: function(value) { + var deferred = new Ext.promise.Deferred(); + deferred.resolve(value); + return deferred.promise; + } + }, + constructor: function(action) { + var deferred = new Ext.promise.Deferred(); + action(deferred.resolve.bind(deferred), deferred.reject.bind(deferred)); + return deferred.promise; + } + }; +}, function(ExtPromise) { + var P = Ext.global.Promise; + if (P && P.resolve && !Ext.useExtPromises) { + Ext.Promise = P; + } else { + ExtPromise._ready(); + } +}); + +/* + Ext.Deferred adapted from: + [DeftJS](https://github.com/deftjs/deftjs5) + Copyright (c) 2012-2013 [DeftJS Framework Contributors](http://deftjs.org) + Open source under the [MIT License](http://en.wikipedia.org/wiki/MIT_License). + + when(), all(), any(), some(), map(), reduce(), delay() and timeout() + sequence(), parallel(), pipeline() + methods adapted from: [when.js](https://github.com/cujojs/when) + Copyright (c) B Cavalier & J Hann + Open source under the [MIT License](http://en.wikipedia.org/wiki/MIT_License). + */ +/** + * Deferreds are the mechanism used to create new Promises. A Deferred has a single + * associated Promise that can be safely returned to external consumers to ensure they do + * not interfere with the resolution or rejection of the deferred operation. + * + * This implementation of Promises is an extension of the ECMAScript 6 Promises API as + * detailed [here][1]. For a compatible, though less full featured, API see `{@link Ext.Promise}`. + * + * A Deferred is typically used within the body of a function that performs an asynchronous + * operation. When that operation succeeds, the Deferred should be resolved; if that + * operation fails, the Deferred should be rejected. + * + * Each Deferred has an associated Promise. A Promise delegates `then` calls to its + * Deferred's `then` method. In this way, access to Deferred operations are divided between + * producer (Deferred) and consumer (Promise) roles. + * + * ## Basic Usage + * + * In it's most common form, a method will create and return a Promise like this: + * + * // A method in a service class which uses a Store and returns a Promise + * // + * loadCompanies: function () { + * var deferred = new Ext.Deferred(); // create the Ext.Deferred object + * + * this.companyStore.load({ + * callback: function (records, operation, success) { + * if (success) { + * // Use "deferred" to drive the promise: + * deferred.resolve(records); + * } + * else { + * // Use "deferred" to drive the promise: + * deferred.reject("Error loading Companies."); + * } + * } + * }); + * + * return deferred.promise; // return the Promise to the caller + * } + * + * You can see this method first creates a `{@link Ext.Deferred Deferred}` object. It then + * returns its `Promise` object for use by the caller. Finally, in the asynchronous + * callback, it resolves the `deferred` object if the call was successful, and rejects the + * `deferred` if the call failed. + * + * When a Deferred's `resolve` method is called, it fulfills with the optionally specified + * value. If `resolve` is called with a then-able (i.e.a Function or Object with a `then` + * function, such as another Promise) it assimilates the then-able's result; the Deferred + * provides its own `resolve` and `reject` methods as the onFulfilled or onRejected + * arguments in a call to that then-able's `then` function. If an error is thrown while + * calling the then-able's `then` function (prior to any call back to the specified + * `resolve` or `reject` methods), the Deferred rejects with that error. If a Deferred's + * `resolve` method is called with its own Promise, it rejects with a TypeError. + * + * When a Deferred's `reject` method is called, it rejects with the optionally specified + * reason. + * + * Each time a Deferred's `then` method is called, it captures a pair of optional + * onFulfilled and onRejected callbacks and returns a Promise of the Deferred's future + * value as transformed by those callbacks. + * + * See `{@link Ext.promise.Promise}` for an example of using the returned Promise. + * + * @since 6.0.0 + */ +Ext.define('Ext.Deferred', function(Deferred) { + var ExtPromise, rejected, resolved, when; + return { + extend: 'Ext.promise.Deferred', + requires: [ + 'Ext.Promise' + ], + statics: { + _ready: function() { + // Our requires are met, so we can cache Ext.promise.Deferred + ExtPromise = Ext.promise.Promise; + when = Ext.Promise.resolve; + }, + /** + * Returns a new Promise that will only resolve once all the specified + * `promisesOrValues` have resolved. + * + * The resolution value will be an Array containing the resolution value of each + * of the `promisesOrValues`. + * + * @param {Mixed[]/Ext.promise.Promise[]/Ext.promise.Promise} promisesOrValues An + * Array of values or Promises, or a Promise of an Array of values or Promises. + * @return {Ext.promise.Promise} A Promise of an Array of the resolved values. + * @static + */ + all: function() { + return ExtPromise.all.apply(ExtPromise, arguments); + }, + /** + * Initiates a competitive race, returning a new Promise that will resolve when + * any one of the specified `promisesOrValues` have resolved, or will reject when + * all `promisesOrValues` have rejected or cancelled. + * + * The resolution value will the first value of `promisesOrValues` to resolve. + * + * @param {Mixed[]/Ext.promise.Promise[]/Ext.promise.Promise} promisesOrValues An + * Array of values or Promises, or a Promise of an Array of values or Promises. + * @return {Ext.promise.Promise} A Promise of the first resolved value. + * @static + */ + any: function(promisesOrValues) { + if (!(Ext.isArray(promisesOrValues) || ExtPromise.is(promisesOrValues))) { + Ext.raise('Invalid parameter: expected an Array or Promise of an Array.'); + } + return Deferred.some(promisesOrValues, 1).then(function(array) { + return array[0]; + }, function(error) { + if (error instanceof Error && error.message === 'Too few Promises were resolved.') { + Ext.raise('No Promises were resolved.'); + } else { + throw error; + } + }); + }, + /** + * Returns a new Promise that will automatically resolve with the specified + * Promise or value after the specified delay (in milliseconds). + * + * @param {Mixed} promiseOrValue A Promise or value. + * @param {Number} milliseconds A delay duration (in milliseconds). + * @return {Ext.promise.Promise} A Promise of the specified Promise or value that + * will resolve after the specified delay. + * @static + */ + delay: function(promiseOrValue, milliseconds) { + var deferred; + if (arguments.length === 1) { + milliseconds = promiseOrValue; + promiseOrValue = undefined; + } + milliseconds = Math.max(milliseconds, 1); + deferred = new Deferred(); + deferred.timeoutId = Ext.defer(function() { + delete deferred.timeoutId; + deferred.resolve(promiseOrValue); + }, milliseconds); + return deferred.promise; + }, + /** + * Get a shared cached rejected promise. Assumes Promises + * have been required. + * @return {Ext.Promise} + * + * @private + * @since 6.5.0 + */ + getCachedRejected: function() { + if (!rejected) { + // Prevent Cmd from requiring + rejected = Ext.Promise.reject(); + } + return rejected; + }, + /** + * Get a shared cached resolved promise. Assumes Promises + * have been required. + * @return {Ext.Promise} + * + * @private + * @since 6.5.0 + */ + getCachedResolved: function() { + if (!resolved) { + // Prevent Cmd from requiring + resolved = Ext.Promise.resolve(); + } + return resolved; + }, + /** + * Traditional map function, similar to `Array.prototype.map()`, that allows + * input to contain promises and/or values. + * + * The specified map function may return either a value or a promise. + * + * @param {Mixed[]/Ext.promise.Promise[]/Ext.promise.Promise} promisesOrValues An + * Array of values or Promises, or a Promise of an Array of values or Promises. + * @param {Function} mapFn A Function to call to transform each resolved value in + * the Array. + * @return {Ext.promise.Promise} A Promise of an Array of the mapped resolved + * values. + * @static + */ + map: function(promisesOrValues, mapFn) { + if (!(Ext.isArray(promisesOrValues) || ExtPromise.is(promisesOrValues))) { + Ext.raise('Invalid parameter: expected an Array or Promise of an Array.'); + } + if (!Ext.isFunction(mapFn)) { + Ext.raise('Invalid parameter: expected a function.'); + } + return Deferred.resolved(promisesOrValues).then(function(promisesOrValues) { + var deferred, index, promiseOrValue, remainingToResolve, resolve, results, i, len; + remainingToResolve = promisesOrValues.length; + results = new Array(promisesOrValues.length); + deferred = new Deferred(); + if (!remainingToResolve) { + deferred.resolve(results); + } else { + resolve = function(item, index) { + return Deferred.resolved(item).then(function(value) { + return mapFn(value, index, results); + }).then(function(value) { + results[index] = value; + if (!--remainingToResolve) { + deferred.resolve(results); + } + return value; + }, function(reason) { + return deferred.reject(reason); + }); + }; + for (index = i = 0 , len = promisesOrValues.length; i < len; index = ++i) { + promiseOrValue = promisesOrValues[index]; + if (index in promisesOrValues) { + resolve(promiseOrValue, index); + } else { + remainingToResolve--; + } + } + } + return deferred.promise; + }); + }, + /** + * Returns a new function that wraps the specified function and caches the + * results for previously processed inputs. + * + * Similar to {@link Ext.Function#memoize Ext.Function.memoize()}, except it + * allows for parameters that are Promises and/or values. + * + * @param {Function} fn A Function to wrap. + * @param {Object} scope An optional scope in which to execute the wrapped function. + * @param {Function} hashFn An optional function used to compute a hash key for + * storing the result, based on the arguments to the original function. + * @return {Function} The new wrapper function. + * @static + */ + memoize: function(fn, scope, hashFn) { + var memoizedFn = Ext.Function.memoize(fn, scope, hashFn); + return function() { + return Deferred.all(Ext.Array.slice(arguments)).then(function(values) { + return memoizedFn.apply(scope, values); + }); + }; + }, + /** + * Execute an Array (or {@link Ext.promise.Promise Promise} of an Array) of + * functions in parallel. + * + * The specified functions may optionally return their results as + * {@link Ext.promise.Promise Promises}. + * + * @param {Function[]/Ext.promise.Promise} fns The Array (or Promise of an Array) + * of functions to execute. + * @param {Object} scope Optional scope in which to execute the specified functions. + * @return {Ext.promise.Promise} Promise of an Array of results for each function + * call (in the same order). + * @static + */ + parallel: function(fns, scope) { + if (scope == null) { + scope = null; + } + var args = Ext.Array.slice(arguments, 2); + return Deferred.map(fns, function(fn) { + if (!Ext.isFunction(fn)) { + throw new Error('Invalid parameter: expected a function.'); + } + return fn.apply(scope, args); + }); + }, + /** + * Execute an Array (or {@link Ext.promise.Promise Promise} of an Array) of + * functions as a pipeline, where each function's result is passed to the + * subsequent function as input. + * + * The specified functions may optionally return their results as + * {@link Ext.promise.Promise Promises}. + * + * @param {Function[]/Ext.promise.Promise} fns The Array (or Promise of an Array) + * of functions to execute. + * @param {Object} initialValue Initial value to be passed to the first function + * in the pipeline. + * @param {Object} scope Optional scope in which to execute the specified functions. + * @return {Ext.promise.Promise} Promise of the result value for the final + * function in the pipeline. + * @static + */ + pipeline: function(fns, initialValue, scope) { + if (scope == null) { + scope = null; + } + return Deferred.reduce(fns, function(value, fn) { + if (!Ext.isFunction(fn)) { + throw new Error('Invalid parameter: expected a function.'); + } + return fn.call(scope, value); + }, initialValue); + }, + /** + * Returns a promise that resolves or rejects as soon as one of the promises in the array resolves + * or rejects, with the value or reason from that promise. + * @param {Ext.promise.Promise[]} promises The promises. + * @return {Ext.promise.Promise} The promise to be resolved when the race completes. + * + * @static + * @since 6.5.0 + */ + race: function() { + return ExtPromise.race.apply(ExtPromise, arguments); + }, + /** + * Traditional reduce function, similar to `Array.reduce()`, that allows input to + * contain promises and/or values. + * + * @param {Mixed[]/Ext.promise.Promise[]/Ext.promise.Promise} values An + * Array of values or Promises, or a Promise of an Array of values or Promises. + * @param {Function} reduceFn A Function to call to transform each successive + * item in the Array into the final reduced value. + * @param {Mixed} initialValue An initial Promise or value. + * @return {Ext.promise.Promise} A Promise of the reduced value. + * @static + */ + reduce: function(values, reduceFn, initialValue) { + if (!(Ext.isArray(values) || ExtPromise.is(values))) { + Ext.raise('Invalid parameter: expected an Array or Promise of an Array.'); + } + if (!Ext.isFunction(reduceFn)) { + Ext.raise('Invalid parameter: expected a function.'); + } + var initialValueSpecified = arguments.length === 3; + return Deferred.resolved(values).then(function(promisesOrValues) { + var reduceArguments = [ + promisesOrValues, + function(previousValueOrPromise, currentValueOrPromise, currentIndex) { + return Deferred.resolved(previousValueOrPromise).then(function(previousValue) { + return Deferred.resolved(currentValueOrPromise).then(function(currentValue) { + return reduceFn(previousValue, currentValue, currentIndex, promisesOrValues); + }); + }); + } + ]; + if (initialValueSpecified) { + reduceArguments.push(initialValue); + } + return Ext.Array.reduce.apply(Ext.Array, reduceArguments); + }); + }, + /** + * Convenience method that returns a new Promise rejected with the specified + * reason. + * + * @param {Error} reason Rejection reason. + * @return {Ext.promise.Promise} The rejected Promise. + * @static + */ + rejected: function(reason) { + var deferred = new Ext.Deferred(); + deferred.reject(reason); + return deferred.promise; + }, + /** + * Returns a new Promise that either + * + * * Resolves immediately for the specified value, or + * * Resolves or rejects when the specified promise (or third-party Promise or + * then()-able) is resolved or rejected. + * + * @param {Mixed} promiseOrValue A Promise (or third-party Promise or then()-able) + * or value. + * @return {Ext.promise.Promise} A Promise of the specified Promise or value. + * @static + */ + resolved: function(promiseOrValue) { + var deferred = new Ext.Deferred(); + deferred.resolve(promiseOrValue); + return deferred.promise; + }, + /** + * Execute an Array (or {@link Ext.promise.Promise Promise} of an Array) of + * functions sequentially. + * + * The specified functions may optionally return their results as {@link + * Ext.promise.Promise Promises}. + * + * @param {Function[]/Ext.promise.Promise} fns The Array (or Promise of an Array) + * of functions to execute. + * @param {Object} scope Optional scope in which to execute the specified functions. + * @return {Ext.promise.Promise} Promise of an Array of results for each function + * call (in the same order). + * @static + */ + sequence: function(fns, scope) { + if (scope == null) { + scope = null; + } + var args = Ext.Array.slice(arguments, 2); + return Deferred.reduce(fns, function(results, fn) { + if (!Ext.isFunction(fn)) { + throw new Error('Invalid parameter: expected a function.'); + } + return Deferred.resolved(fn.apply(scope, args)).then(function(result) { + results.push(result); + return results; + }); + }, []); + }, + /** + * Initiates a competitive race, returning a new Promise that will resolve when + * `howMany` of the specified `promisesOrValues` have resolved, or will reject + * when it becomes impossible for `howMany` to resolve. + * + * The resolution value will be an Array of the first `howMany` values of + * `promisesOrValues` to resolve. + * + * @param {Mixed[]/Ext.promise.Promise[]/Ext.promise.Promise} promisesOrValues An + * Array of values or Promises, or a Promise of an Array of values or Promises. + * @param {Number} howMany The expected number of resolved values. + * @return {Ext.promise.Promise} A Promise of the expected number of resolved + * values. + * @static + */ + some: function(promisesOrValues, howMany) { + if (!(Ext.isArray(promisesOrValues) || ExtPromise.is(promisesOrValues))) { + Ext.raise('Invalid parameter: expected an Array or Promise of an Array.'); + } + if (!Ext.isNumeric(howMany) || howMany <= 0) { + Ext.raise('Invalid parameter: expected a positive integer.'); + } + return Deferred.resolved(promisesOrValues).then(function(promisesOrValues) { + var deferred, index, onReject, onResolve, promiseOrValue, remainingToReject, remainingToResolve, values, i, len; + values = []; + remainingToResolve = howMany; + remainingToReject = (promisesOrValues.length - remainingToResolve) + 1; + deferred = new Deferred(); + if (promisesOrValues.length < howMany) { + deferred.reject(new Error('Too few Promises were resolved.')); + } else { + onResolve = function(value) { + if (remainingToResolve > 0) { + values.push(value); + } + remainingToResolve--; + if (remainingToResolve === 0) { + deferred.resolve(values); + } + return value; + }; + onReject = function(reason) { + remainingToReject--; + if (remainingToReject === 0) { + deferred.reject(new Error('Too few Promises were resolved.')); + } + return reason; + }; + for (index = i = 0 , len = promisesOrValues.length; i < len; index = ++i) { + promiseOrValue = promisesOrValues[index]; + if (index in promisesOrValues) { + Deferred.resolved(promiseOrValue).then(onResolve, onReject); + } + } + } + return deferred.promise; + }); + }, + /** + * Returns a new Promise that will automatically reject after the specified + * timeout (in milliseconds) if the specified promise has not resolved or + * rejected. + * + * @param {Mixed} promiseOrValue A Promise or value. + * @param {Number} milliseconds A timeout duration (in milliseconds). + * @return {Ext.promise.Promise} A Promise of the specified Promise or value that + * enforces the specified timeout. + * @static + */ + timeout: function(promiseOrValue, milliseconds) { + var deferred = new Deferred(), + timeoutId; + timeoutId = Ext.defer(function() { + if (timeoutId) { + deferred.reject(new Error('Promise timed out.')); + } + }, milliseconds); + Deferred.resolved(promiseOrValue).then(function(value) { + Ext.undefer(timeoutId); + timeoutId = null; + deferred.resolve(value); + }, function(reason) { + Ext.undefer(timeoutId); + timeoutId = null; + deferred.reject(reason); + }); + return deferred.promise; + } + } + }; +}, function(Deferred) { + Deferred._ready(); +}); + +// @define Ext.Factory +/** + * @class Ext.Factory + * Manages factories for families of classes (classes with a common `alias` prefix). The + * factory for a class family is a function stored as a `static` on `Ext.Factory`. These + * are created either by directly calling `Ext.Factory.define` or by using the + * `Ext.mixin.Factoryable` interface. + * + * To illustrate, consider the layout system's use of aliases. The `hbox` layout maps to + * the `"layout.hbox"` alias that one typically provides via the `layout` config on a + * Container. + * + * Under the covers this maps to a call like this: + * + * Ext.Factory.layout('hbox'); + * + * Or possibly: + * + * Ext.Factory.layout({ + * type: 'hbox' + * }); + * + * The value of the `layout` config is passed to the `Ext.Factory.layout` function. The + * exact signature of a factory method matches `{@link Ext.Factory#method!create}`. + * + * To define this factory directly, one could call `Ext.Factory.define` like so: + * + * Ext.Factory.define('layout', 'auto'); // "layout.auto" is the default type + * + * @since 5.0.0 + */ +Ext.Factory = function(type) { + var me = this; + me.aliasPrefix = type + '.'; + me.cache = {}; + me.name = type.replace(me.fixNameRe, me.fixNameFn); + me.type = type; + /** + * @cfg {String} [creator] + * The name of the method used to prepare config objects for creation. This defaults + * to `'create'` plus the capitalized name (e.g., `'createLayout'` for the 'laoyut' + * alias family). + */ + me.creator = 'create' + Ext.String.capitalize(me.name); +}; +Ext.Factory.prototype = { + /** + * @cfg {String} [aliasPrefix] + * The prefix to apply to `type` values to form a complete alias. This defaults to the + * proper value in most all cases and should not need to be specified. + * + * @since 5.0.0 + */ + /** + * @cfg {String} [defaultProperty="type"] + * The config property to set when the factory is given a config that is a string. + * + * @since 5.0.0 + */ + defaultProperty: 'type', + /** + * @cfg {String} [defaultType=null] + * An optional type to use if none is given to the factory at invocation. This is a + * suffix added to the `aliasPrefix`. For example, if `aliasPrefix="layout."` and + * `defaultType="hbox"` the default alias is `"layout.hbox"`. This is an alternative + * to `xclass` so only one should be provided. + * + * @since 5.0.0 + */ + /** + * @cfg {String} [instanceProp="isInstance"] + * The property that identifies an object as instance vs a config. + * + * @since 5.0.0 + */ + instanceProp: 'isInstance', + /** + * @cfg {String} [xclass=null] + * The full classname of the type of instance to create when none is provided to the + * factory. This is an alternative to `defaultType` so only one should be specified. + * + * @since 5.0.0 + */ + /** + * @property {Ext.Class} [defaultClass=null] + * The Class reference of the type of instance to create when none is provided to the + * factory. This property is set from `xclass` when the factory instance is created. + * @private + * @readonly + * + * @since 5.0.0 + */ + /** + * @cfg {String} [typeProperty="type"] + * The property from which to read the type alias suffix. + * @since 6.5.0 + */ + typeProperty: 'type', + /** + * Creates an instance of this class family given configuration options. + * + * @param {Object/String} [config] The configuration or instance (if an Object) or + * just the type (if a String) describing the instance to create. + * @param {String} [config.xclass] The full class name of the class to create. + * @param {String} [config.type] The type string to add to the alias prefix for this + * factory. + * @param {String/Object} [defaultType] The type to create if no type is contained in the + * `config`, or an object containing a default set of configs. + * @return {Object} The newly created instance. + * + * @since 5.0.0 + */ + create: function(config, defaultType) { + var me = this, + Manager = Ext.ClassManager, + cache = me.cache, + typeProperty = me.typeProperty, + alias, className, klass, suffix; + if (config) { + if (config[me.instanceProp]) { + return config; + } + if (typeof config === 'string') { + suffix = config; + config = {}; + config[me.defaultProperty] = suffix; + } + className = config.xclass; + suffix = config[typeProperty]; + } + if (defaultType && defaultType.constructor === Object) { + config = Ext.apply({}, config, defaultType); + defaultType = defaultType[typeProperty]; + } + if (className) { + if (!(klass = Manager.get(className))) { + return Manager.instantiate(className, config); + } + } else { + if (!(suffix = suffix || defaultType || me.defaultType)) { + klass = me.defaultClass; + } + if (!suffix && !klass) { + Ext.raise('No type specified for ' + me.type + '.create'); + } + if (!klass && !(klass = cache[suffix])) { + alias = me.aliasPrefix + suffix; + className = Manager.getNameByAlias(alias); + // this is needed to support demand loading of the class + if (!(klass = className && Manager.get(className))) { + return Manager.instantiateByAlias(alias, config); + } + cache[suffix] = klass; + } + } + return klass.isInstance ? klass : new klass(config); + }, + fixNameRe: /\.[a-z]/ig, + fixNameFn: function(match) { + return match.substring(1).toUpperCase(); + }, + clearCache: function() { + this.cache = {}; + this.instanceCache = {}; + }, + /** + * Sets a hook on the creation process. If the hook `fn` returns `undefined` then + * the original `create` method is called. + * + * @param {Function} fn The hook function to call when `create` is invoked. + * @param {Function} fn.original The original `create` method. + * @param {String/Object} fn.config See {@link #method!create create}. + * @param {String/Object} fn.defaultType See {@link #method!create create}. + * @private + * @since 6.5.0 + */ + hook: function(fn) { + var me = this, + original = me.create; + me.create = function(config, defaultType) { + var ret = fn.call(me, original, config, defaultType); + if (ret === undefined) { + ret = original.call(me, config, defaultType); + } + return ret; + }; + }, + /** + * This method accepts a `config` object and an existing `instance` if one exists + * (can be `null`). + * + * The details are best explained by example: + * + * config: { + * header: { + * xtype: 'itemheader' + * } + * }, + * + * applyHeader: function (header, oldHeader) { + * return Ext.Factory.widget.update(oldHeader, header, + * this, 'createHeader'); + * }, + * + * createHeader: function (header) { + * return Ext.apply({ + * xtype: 'itemheader', + * ownerCmp: this + * }, header); + * } + * + * Normally the `applyHeader` method would have to coordinate potential reuse of + * the `oldHeader` and perhaps call `setConfig` on it with the new `header` config + * options. If there was no `oldHeader`, of course, a new instance must be created + * instead. These details are handled by this method. If the `oldHeader` is not + * reused, it will be {@link Ext.Base#method!destroy destroyed}. + * + * For derived class flexibility, the pattern of calling out to a "creator" method + * that only returns the config object has become widely used in many components. + * This pattern is also covered in this method. The goal is to allow the derived + * class to `callParent` and yet not end up with an instantiated component (since + * the type may not yet be known). + * + * This mechanism should be used in favor of `Ext.factory()`. + * + * @param {Ext.Base} instance + * @param {Object/String} config The configuration (see {@link #method!create}). + * @param {Object} [creator] If passed, this object must provide the `creator` + * method or the `creatorMethod` parameter. + * @param {String} [creatorMethod] The name of a creation wrapper method on the + * given `creator` instance that "upgrades" the raw `config` object into a final + * form for creation. + * @param {String} [defaultsConfig] The name of a config property (on the provided + * `creator` instance) that contains defaults to be used to create instances. These + * defaults are present in the config object passed to the `creatorMethod`. + * @return {Object} The reconfigured `instance` or a newly created one. + * @since 6.5.0 + */ + update: function(instance, config, creator, creatorMethod, defaultsConfig) { + var me = this, + aliases, defaults, reuse, type; + // If config is falsy or a valid instance, destroy the current instance + // (if it exists) and replace with the new one + if (!config || config.isInstance) { + if (config && !config[me.instanceProp]) { + Ext.raise('Config instance failed ' + me.instanceProp + ' requirement'); + } + if (instance && instance !== config) { + instance.destroy(); + } + return config; + } + if (typeof config === 'string') { + type = config; + config = {}; + config[me.defaultProperty] = type; + } + // See if the existing instance can just be reconfigured: + if (instance) { + if (config === true) { + return instance; + } + if (!(type = config.xclass)) { + if (!(type = config.xtype)) { + type = config[me.typeProperty]; + if (type) { + // instance must have the right alias... + type = me.aliasPrefix + type; + aliases = instance.self.prototype; + // The alias for the class is on the prototype (derived + // classes do not really own their inherited aliases since + // they won't be created when using them): + if (aliases.hasOwnProperty('alias')) { + aliases = aliases.alias; + if (aliases) { + reuse = aliases === type || aliases.indexOf(type) > -1; + } + } + } + } else { + // config = { xtype: ... } + reuse = instance.isXType(type, /*shallow=*/ + true); + } + } else { + // config = { xclass: ... } so we're good if they match + reuse = instance.$className === type; + } + if (reuse) { + instance.setConfig(config); + return instance; + } + instance.destroy(); + } + if (config === true) { + config = {}; + } + if (creator) { + if (defaultsConfig) { + defaults = Ext.Config.map[defaultsConfig]; + defaults = creator[defaults.names.get](); + if (defaults) { + config = Ext.merge(Ext.clone(defaults), config); + } + } + creatorMethod = creatorMethod || me.creator; + if (creator[creatorMethod]) { + config = creator[creatorMethod](config); + if (!config) { + Ext.raise('Missing return value from ' + creatorMethod + ' on class ' + creator.$className); + } + } + } + return me.create(config); + } +}; +/** + * For example, the layout alias family could be defined like this: + * + * Ext.Factory.define('layout', { + * defaultType: 'auto' + * }); + * + * To define multiple families at once: + * + * Ext.Factory.define({ + * layout: { + * defaultType: 'auto' + * } + * }); + * + * @param {String} type The alias family (e.g., "layout"). + * @param {Object/String} [config] An object specifying the config for the `Ext.Factory` + * to be created. If a string is passed it is treated as the `defaultType`. + * @return {Function} + * @static + * @since 5.0.0 + */ +Ext.Factory.define = function(type, config) { + var Factory = Ext.Factory, + cacheable = config && config.cacheable, + defaultClass, factory, fn; + if (type.constructor === Object) { + Ext.Object.each(type, Factory.define, Factory); + } else { + factory = new Ext.Factory(type); + if (config) { + if (config.constructor === Object) { + Ext.apply(factory, config); + if (typeof (defaultClass = factory.xclass) === 'string') { + factory.defaultClass = Ext.ClassManager.get(defaultClass); + } + } else { + factory.defaultType = config; + } + } + /* + * layout = Ext.Factory.layout('hbox'); + */ + Factory[factory.name] = fn = function(config, defaultType) { + // maintain indirection through "create" name on instance to allow + // the hook() mechanism to replace it. + return factory.create(config, defaultType); + }; + if (cacheable) { + factory.instanceCache = {}; + factory.hook(function(original, config, defaultType) { + var cache = this.instanceCache, + v; + if (typeof config === 'string' && !(v = cache[config])) { + v = original.call(this, config, defaultType); + // Validator may have cacheable:false to force new instances each time, + // avoiding the cache + if (v.cacheable !== false) { + cache[config] = v; + // this should catch some improper modifications to the shared + // cached instance, during development but not in production. + Ext.Object.freeze(v); + } + } + return v; + }); + } + fn.instance = factory; + /* + * Typically called by an applier: + * + * applyLayout: function (layout, oldLayout) { + * return Ext.Factory.layout.update(oldLayout, layout, this); + * }, + * + * createLayout: function (config) { + * return Ext.apply({ + * //.. stuff + * }, config); + * } + */ + fn.update = function(instance, config, creator, creatorMethod, defaultsConfig) { + return factory.update(instance, config, creator, creatorMethod, defaultsConfig); + }; + } + return fn; +}; +Ext.Factory.clearCaches = function() { + var Factory = Ext.Factory, + key, item; + for (key in Factory) { + item = Factory[key]; + item = item.instance; + if (item) { + item.clearCache(); + } + } +}; +Ext.Factory.on = function(name, fn) { + Ext.Factory[name].instance.hook(fn); +}; +/** + * This mixin automates use of `Ext.Factory`. When mixed in to a class, the `alias` of the + * class is retrieved and combined with an optional `factoryConfig` property on that class + * to produce the configuration to pass to `Ext.Factory`. + * + * The factory method created by `Ext.Factory` is also added as a static method to the + * target class. + * + * Given a class declared like so: + * + * Ext.define('App.bar.Thing', { + * mixins: [ + * 'Ext.mixin.Factoryable' + * ], + * + * alias: 'bar.thing', // this is detected by Factoryable + * + * factoryConfig: { + * defaultType: 'thing', // this is the default deduced from the alias + * // other configs + * }, + * + * ... + * }); + * + * The produced factory function can be used to create instances using the following + * forms: + * + * var obj; + * + * obj = App.bar.Thing.create('thing'); // same as "new App.bar.Thing()" + * + * obj = App.bar.Thing.create({ + * type: 'thing' // same as above + * }); + * + * obj = App.bar.Thing.create({ + * xclass: 'App.bar.Thing' // same as above + * }); + * + * var obj2 = App.bar.Thing.create(obj); + * // obj === obj2 (passing an instance returns the instance) + * + * Alternatively the produced factory is available as a static method of `Ext.Factory`. + * + * @since 5.0.0 + */ +Ext.define('Ext.mixin.Factoryable', { + mixinId: 'factoryable', + onClassMixedIn: function(targetClass) { + var proto = targetClass.prototype, + factoryConfig = proto.factoryConfig, + alias = proto.alias, + config = {}, + dot, createFn; + alias = alias && alias.length && alias[0]; + if (alias && (dot = alias.lastIndexOf('.')) > 0) { + config.type = alias.substring(0, dot); + config.defaultType = alias.substring(dot + 1); + } + if (factoryConfig) { + delete proto.factoryConfig; + Ext.apply(config, factoryConfig); + } + createFn = Ext.Factory.define(config.type, config); + if (targetClass.create === Ext.Base.create) { + // allow targetClass to override the create method + targetClass.create = createFn; + } + } +}); +/** + * @property {Object} [factoryConfig] + * If this property is specified by the target class of this mixin its properties are + * used to configure the created `Ext.Factory`. + */ + +/** + * This class manages a pending Ajax request. Instances of this type are created by the + * `{@link Ext.data.Connection#request}` method. + * @since 6.0.0 + */ +Ext.define('Ext.data.request.Base', { + requires: [ + 'Ext.Deferred' + ], + mixins: [ + 'Ext.mixin.Factoryable' + ], + // Since this class is abstract, we don't have an alias of our own for Factoryable + // to use. + factoryConfig: { + type: 'request', + defaultType: 'ajax' + }, + // this is the default deduced from the alias + result: null, + success: null, + timer: null, + constructor: function(config) { + var me = this; + // ownerConfig contains default values for config options + // applicable to every Request spawned by that owner; + // however the values can be overridden in the options + // object passed to owner's request() method. + Ext.apply(me, config.options || {}, config.ownerConfig); + me.id = ++Ext.data.Connection.requestId; + me.owner = config.owner; + me.options = config.options; + me.requestOptions = config.requestOptions; + }, + /** + * Start the request. + */ + start: function() { + var me = this, + timeout = me.getTimeout(); + if (timeout && me.async) { + me.timer = Ext.defer(me.onTimeout, timeout, me); + } + }, + abort: function() { + var me = this; + me.clearTimer(); + if (!me.timedout) { + me.aborted = true; + } + me.abort = Ext.emptyFn; + }, + createDeferred: function() { + var me = this, + result = me.result, + d = new Ext.Deferred(); + if (me.completed) { + if (me.success) { + d.resolve(result); + } else { + d.reject(result); + } + } + me.deferred = d; + return d; + }, + getDeferred: function() { + return this.deferred || this.createDeferred(); + }, + getPromise: function() { + return this.getDeferred().promise; + }, + /** + * @method then + * Returns a new promise resolving to the value of the called method. + * @param {Function} success Called when the Promise is fulfilled. + * @param {Function} failure Called when the Promise is rejected. + * @returns {Ext.promise.Promise} + */ + then: function() { + var promise = this.getPromise(); + return promise.then.apply(promise, arguments); + }, + /** + * @method isLoading + * Determines whether this request is in progress. + * + * @return {Boolean} `true` if this request is in progress, `false` if complete. + */ + onComplete: function() { + var me = this, + deferred = me.deferred, + result = me.result; + me.clearTimer(); + if (deferred) { + if (me.success) { + deferred.resolve(result); + } else { + deferred.reject(result); + } + } + me.completed = true; + }, + onTimeout: function() { + var me = this; + me.timedout = true; + me.timer = null; + me.abort(true); + }, + getTimeout: function() { + return this.timeout; + }, + clearTimer: function() { + this.timer = Ext.undefer(this.timer); + }, + destroy: function() { + var me = this; + me.abort(); + me.owner = me.options = me.requestOptions = me.result = null; + me.callParent(); + }, + privates: { + /** + * Creates the exception object + * @param {Object} request + * @private + */ + createException: function() { + var me = this, + result; + result = { + request: me, + requestId: me.id, + status: me.aborted ? -1 : 0, + statusText: me.aborted ? 'transaction aborted' : 'communication failure', + getResponseHeader: me._getHeader, + getAllResponseHeaders: me._getHeaders + }; + if (me.aborted) { + result.aborted = true; + } + if (me.timedout) { + result.timedout = true; + } + return result; + }, + _getHeader: function(name) { + var headers = this.headers; + return headers && headers[name.toLowerCase()]; + }, + _getHeaders: function() { + return this.headers; + } + } +}); + +/** + * + * Simulates an XMLHttpRequest object's methods and properties as returned + * form the flash polyfill plugin. Used in submitting binary data in browsers that do + * not support doing so from JavaScript. + * NOTE: By default this will look for the flash object in the ext directory. When packaging and deploying the app, copy the ext/plugins directory and its contents to your root directory. For custom deployments where just the FlashPlugin.swf file gets copied (e.g. to /resources/FlashPlugin.swf), make sure to notify the framework of the location of the plugin before making the first attempt to post binary data, e.g. in the launch method of your app do: + *

+Ext.flashPluginPath="/resources/FlashPlugin.swf";
+ 
+ * + * @private + */ +Ext.define('Ext.data.flash.BinaryXhr', { + statics: { + /** + * Called by the flash plugin once it's installed and open for business. + * @private + */ + flashPluginActivated: function() { + Ext.data.flash.BinaryXhr.flashPluginActive = true; + Ext.data.flash.BinaryXhr.flashPlugin = document.getElementById("ext-flash-polyfill"); + Ext.GlobalEvents.fireEvent("flashready"); + }, + // let all pending connections know + /** + * Set to trut once the plugin registers and is active. + * @private + */ + flashPluginActive: false, + /** + * Flag to avoid installing the plugin twice. + * @private + */ + flashPluginInjected: false, + /** + * Counts IDs for new connections. + * @private + */ + connectionIndex: 1, + /** + * Placeholder for active connections. + * @private + */ + liveConnections: {}, + /** + * Reference to the actual plugin, once activated. + * @private + */ + flashPlugin: null, + /** + * Called by the flash plugin once the state of one of the active connections changes. + * @param {Number/number} javascriptId the ID of the connection. + * @param {number} state the state of the connection. Equivalent to readyState numbers in XHR. + * @param {Object} data optional object containing the returned data, error and status codes. + * @private + */ + onFlashStateChange: function(javascriptId, state, data) { + var connection; + // Identify the request this is for + connection = this.liveConnections[Number(javascriptId)]; + // Make sure its a native number + if (connection) { + connection.onFlashStateChange(state, data); + } else { + Ext.warn.log("onFlashStateChange for unknown connection ID: " + javascriptId); + } + }, + /** + * Adds the BinaryXhr object to the tracked connection list and assigns it an ID + * @param {Ext.data.flash.BinaryXhr} conn the connection to register + * @return {Number} id + * @private + */ + registerConnection: function(conn) { + var i = this.connectionIndex; + this.conectionIndex = this.connectionIndex + 1; + this.liveConnections[i] = conn; + return i; + }, + /** + * Injects the flash polyfill plugin to allow posting binary data. + * This is done in two steps: First we load the javascript loader for flash objects, then we call it to inject the flash object. + * @private + */ + injectFlashPlugin: function() { + var me = this, + flashLoaderPath, flashObjectPath; + // Generate the following HTML set of tags: + // + '
' + // + '

To view this page ensure that Adobe Flash Player version 11.1.0 or greater is installed, and that the FlashPlugin.swf file was correctly placed in the /resources directory.

' + //+ 'Get Adobe Flash player' + //+ '
' + me.flashPolyfillEl = Ext.getBody().appendChild({ + id: 'ext-flash-polyfill', + cn: [ + { + tag: 'p', + html: 'To view this page ensure that Adobe Flash Player version 11.1.0 or greater is installed.' + }, + { + tag: 'a', + href: 'http://www.adobe.com/go/getflashplayer', + cn: [ + { + tag: 'img', + src: window.location.protocol + '//www.adobe.com/images/shared/download_buttons/get_flash_player.gif', + alt: 'Get Adobe Flash player' + } + ] + } + ] + }); + // Now load the flash-loading script + flashLoaderPath = [ + Ext.Loader.getPath('Ext.data.Connection'), + '../../../plugins/flash/swfobject.js' + ].join('/'); + flashObjectPath = "/plugins/flash/FlashPlugin.swf"; + flashObjectPath = [ + Ext.Loader.getPath('Ext.data.Connection'), + '../../plugins/flash/FlashPlugin.swf' + ].join('/'); + if (Ext.flashPluginPath) { + flashObjectPath = Ext.flashPluginPath; + } + //console.log('LOADING Flash plugin from: ' + flashObjectPath); + Ext.Loader.loadScript({ + url: flashLoaderPath, + onLoad: function() { + // For version detection, set to min. required Flash Player version, or 0 (or 0.0.0), for no version detection. + var swfVersionStr = "11.4.0"; + // To use express install, set to playerProductInstall.swf, otherwise the empty string. + var xiSwfUrlStr = "playerProductInstall.swf"; + var flashvars = {}; + var params = {}; + params.quality = "high"; + params.bgcolor = "#ffffff"; + params.allowscriptaccess = "sameDomain"; + params.allowfullscreen = "true"; + var attributes = {}; + attributes.id = "ext-flash-polyfill"; + attributes.name = "polyfill"; + attributes.align = "middle"; + swfobject.embedSWF(flashObjectPath, "ext-flash-polyfill", "0", "0", // no size so it's not visible. + swfVersionStr, xiSwfUrlStr, flashvars, params, attributes); + }, + onError: function() { + Ext.raise("Could not load flash-loader file swfobject.js from " + flashLoader); + }, + scope: me + }); + Ext.data.flash.BinaryXhr.flashPluginInjected = true; + } + }, + /** + * @property {number} readyState The connection's simulated readyState. Note that the only supported values are 0, 1 and 4. States 2 and 3 will never be reported. + */ + readyState: 0, + /** + * @property {number} status Connection status code returned by flash or the server. + */ + status: 0, + /** + * Status text (if any) returned by flash or the server. + */ + statusText: "", + /** + * @property {Array} responseBytes The binary bytes returned. + */ + responseBytes: null, + /** + * An ID representing this connection with flash. + * @private + */ + javascriptId: null, + /** + * Creates a new instance of BinaryXhr. + */ + constructor: function(config) { + // first, make sure flash is loading if needed + if (!Ext.data.flash.BinaryXhr.flashPluginInjected) { + Ext.data.flash.BinaryXhr.injectFlashPlugin(); + } + var me = this; + Ext.apply(me, config); + me.requestHeaders = {}; + }, + /** + * Abort this connection. Sets its readyState to 4. + */ + abort: function() { + var me = this; + // if complete, nothing to abort + if (me.readyState == 4) { + Ext.warn.log("Aborting a connection that's completed its transfer: " + this.url); + return; + } + // Mark as aborted + me.aborted = true; + // Remove ourselves from the listeners if flash isn't active yet + if (!Ext.data.flash.BinaryXhr.flashPluginActive) { + Ext.GlobalEvents.removeListener("flashready", me.onFlashReady, me); + return; + } + // Flash is already live, so we should have a javascriptID and should have called flash to get the request going. Cancel: + Ext.data.flash.BinaryXhr.flashPlugin.abortRequest(me.javascriptId); + // remove from list + delete Ext.data.flash.BinaryXhr.liveConnections[me.javascriptId]; + }, + /** + * As in XMLHttpRequest. + */ + getAllResponseHeaders: function() { + var headers = []; + Ext.Object.each(this.responseHeaders, function(name, value) { + headers.push(name + ': ' + value); + }); + return headers.join('\r\n'); + }, + /** + * As in XMLHttpRequest. + */ + getResponseHeader: function(header) { + var headers = this.responseHeaders; + return (headers && headers[header]) || null; + }, + /** + * As in XMLHttpRequest. + */ + open: function(method, url, async, user, password) { + var me = this; + me.method = method; + me.url = url; + me.async = async !== false; + me.user = user; + me.password = password; + if (!me.async) { + Ext.raise("Binary posts are only supported in async mode: " + url); + } + if (me.method != "POST") { + Ext.log.warn("Binary data can only be sent as a POST request: " + url); + } + }, + /** + * As in XMLHttpRequest. + */ + overrideMimeType: function(mimeType) { + this.mimeType = mimeType; + }, + /** + * Initiate the request. + * @param {Array} body an array of byte values to send. + */ + send: function(body) { + var me = this; + me.body = body; + if (!Ext.data.flash.BinaryXhr.flashPluginActive) { + Ext.GlobalEvents.addListener("flashready", me.onFlashReady, me); + } else { + this.onFlashReady(); + } + }, + /** + * Called by send, or once flash is loaded, to actually send the bytes. + * @private + */ + onFlashReady: function() { + var me = this, + req, status; + me.javascriptId = Ext.data.flash.BinaryXhr.registerConnection(me); + // Create the request object we're sending to flash + req = { + method: me.method, + // ignored since we always POST binary data + url: me.url, + user: me.user, + password: me.password, + mimeType: me.mimeType, + requestHeaders: me.requestHeaders, + body: me.body, + javascriptId: me.javascriptId + }; + status = Ext.data.flash.BinaryXhr.flashPlugin.postBinary(req); + }, + /** + * Updates readyState and notifies listeners. + * @private + */ + setReadyState: function(state) { + var me = this; + if (me.readyState != state) { + me.readyState = state; + me.onreadystatechange(); + } + }, + /** + * As in XMLHttpRequest. + */ + setRequestHeader: function(header, value) { + this.requestHeaders[header] = value; + }, + /** + * @method + * As in XMLHttpRequest. + */ + onreadystatechange: Ext.emptyFn, + /** + * Parses data returned from flash once a connection is done. + * @param {Object} data the data object send from Flash. + * @private + */ + parseData: function(data) { + var me = this; + // parse data and set up variables so that listeners can use this XHR + this.status = data.status || 0; + // we get back no response headers, so fake what we know: + me.responseHeaders = {}; + if (me.mimeType) { + me.responseHeaders["content-type"] = me.mimeType; + } + if (data.reason == "complete") { + // Transfer complete and data received + this.responseBytes = data.data; + me.responseHeaders["content-length"] = data.data.length; + } else if (data.reason == "error" || data.reason == "securityError") { + this.statusText = data.text; + me.responseHeaders["content-length"] = 0; + } else // we don't get the error response data + { + Ext.raise("Unkown reason code in data: " + data.reason); + } + }, + /** + * Called once flash calls back with updates about the connection + * @param {Number} state the readyState of the connection. + * @param {Object} data optional data object. + * @private + */ + onFlashStateChange: function(state, data) { + var me = this; + if (state == 4) { + // parse data and prepare for handing back to initiator + me.parseData(data); + // remove from list + delete Ext.data.flash.BinaryXhr.liveConnections[me.javascriptId]; + } + me.setReadyState(state); + } +}); +// notify all listeners + +/** + * This class manages a pending Ajax request. Instances of this type are created by the + * `{@link Ext.data.Connection#request}` method. + * @since 6.0.0 + */ +Ext.define('Ext.data.request.Ajax', { + extend: 'Ext.data.request.Base', + alias: 'request.ajax', + requires: [ + 'Ext.data.flash.BinaryXhr' + ], + statics: { + /** + * Checks if the response status was successful + * @param {Number} status The status code + * @param {Object} response The Response object + * @return {Object} An object containing success/status state + * @private + */ + parseStatus: function(status, response) { + var len; + if (response) { + //We have to account for binary response type + if (response.responseType === 'arraybuffer') { + len = response.byteLength; + } else if (response.responseText) { + len = response.responseText.length; + } + } + // see: https://prototype.lighthouseapp.com/projects/8886/tickets/129-ie-mangles-http-response-status-code-204-to-1223 + status = status == 1223 ? 204 : status; + var success = (status >= 200 && status < 300) || status == 304 || (status == 0 && Ext.isNumber(len)), + isException = false; + if (!success) { + switch (status) { + case 12002: + case 12029: + case 12030: + case 12031: + case 12152: + case 13030: + isException = true; + break; + } + } + return { + success: success, + isException: isException + }; + } + }, + start: function(data) { + var me = this, + options = me.options, + requestOptions = me.requestOptions, + isXdr = me.isXdr, + xhr, headers; + xhr = me.xhr = me.openRequest(options, requestOptions, me.async, me.username, me.password); + // XDR doesn't support setting any headers + if (!isXdr) { + headers = me.setupHeaders(xhr, options, requestOptions.data, requestOptions.params); + } + if (me.async) { + if (!isXdr) { + xhr.onreadystatechange = me.bindStateChange(); + } + } + if (isXdr) { + me.processXdrRequest(me, xhr); + } + // Parent will set the timeout if needed + me.callParent([ + data + ]); + // start the request! + xhr.send(data); + if (!me.async) { + return me.onComplete(); + } + return me; + }, + /** + * Aborts an active request. + */ + abort: function(force) { + var me = this, + xhr = me.xhr; + if (force || me.isLoading()) { + /* + * Clear out the onreadystatechange here, this allows us + * greater control, the browser may/may not fire the function + * depending on a series of conditions. + */ + try { + xhr.onreadystatechange = null; + } catch (e) { + // Setting onreadystatechange to null can cause problems in IE, see + // http://www.quirksmode.org/blog/archives/2005/09/xmlhttp_notes_a_1.html + xhr.onreadystatechange = Ext.emptyFn; + } + xhr.abort(); + me.callParent([ + force + ]); + me.onComplete(); + me.cleanup(); + } + }, + /** + * Cleans up any left over information from the request + */ + cleanup: function() { + this.xhr = null; + delete this.xhr; + }, + isLoading: function() { + var me = this, + xhr = me.xhr, + state = xhr && xhr.readyState, + C = Ext.data.flash && Ext.data.flash.BinaryXhr; + if (!xhr || me.aborted || me.timedout) { + return false; + } + // if there is a connection and readyState is not 0 or 4, or in case of + // BinaryXHR, not 4 + if (C && xhr instanceof C) { + return state !== 4; + } + return state !== 0 && state !== 4; + }, + /** + * Creates and opens an appropriate XHR transport for a given request on this browser. + * This logic is contained in an individual method to allow for overrides to process all + * of the parameters and options and return a suitable, open connection. + * @private + */ + openRequest: function(options, requestOptions, async, username, password) { + var me = this, + xhr = me.newRequest(options); + if (username) { + xhr.open(requestOptions.method, requestOptions.url, async, username, password); + } else { + if (me.isXdr) { + xhr.open(requestOptions.method, requestOptions.url); + } else { + xhr.open(requestOptions.method, requestOptions.url, async); + } + } + if (options.binary || me.binary) { + if (window.Uint8Array) { + xhr.responseType = 'arraybuffer'; + } else if (xhr.overrideMimeType) { + // In some older non-IE browsers, e.g. ff 3.6, that do not + // support Uint8Array, a mime type override is required so that + // the unprocessed binary data can be read from the responseText + // (see createResponse()) + xhr.overrideMimeType('text/plain; charset=x-user-defined'); + } else if (!Ext.isIE) { + Ext.log.warn("Your browser does not support loading binary data using Ajax."); + } + } + if (options.withCredentials || me.withCredentials) { + xhr.withCredentials = true; + } + return xhr; + }, + /** + * Creates the appropriate XHR transport for a given request on this browser. On IE + * this may be an `XDomainRequest` rather than an `XMLHttpRequest`. + * @private + */ + newRequest: function(options) { + var me = this, + xhr; + if (options.binaryData) { + // This is a binary data request. Handle submission differently for differnet browsers + if (window.Uint8Array) { + // On browsers that support this, use the native XHR object + xhr = me.getXhrInstance(); + } else { + // catch all for all other browser types + xhr = new Ext.data.flash.BinaryXhr(); + } + } else if (me.cors && Ext.isIE9m) { + xhr = me.getXdrInstance(); + me.isXdr = true; + } else { + xhr = me.getXhrInstance(); + me.isXdr = false; + } + return xhr; + }, + /** + * Setup all the headers for the request + * @private + * @param {Object} xhr The xhr object + * @param {Object} options The options for the request + * @param {Object} data The data for the request + * @param {Object} params The params for the request + */ + setupHeaders: function(xhr, options, data, params) { + var me = this, + headers = Ext.apply({}, options.headers || {}, me.defaultHeaders), + contentType = me.defaultPostHeader, + jsonData = options.jsonData, + xmlData = options.xmlData, + type = 'Content-Type', + useHeader = me.useDefaultXhrHeader, + key, header; + if (!headers.hasOwnProperty(type) && (data || params)) { + if (data) { + if (options.rawData) { + contentType = 'text/plain'; + } else { + if (xmlData && Ext.isDefined(xmlData)) { + contentType = 'text/xml'; + } else if (jsonData && Ext.isDefined(jsonData)) { + contentType = 'application/json'; + } + } + } + headers[type] = contentType; + } + if (useHeader && !headers['X-Requested-With']) { + headers['X-Requested-With'] = me.defaultXhrHeader; + } + // If undefined/null, remove it and don't set the header. + // Allow the browser to do so. + if (headers[type] === undefined || headers[type] === null) { + delete headers[type]; + } + // set up all the request headers on the xhr object + try { + for (key in headers) { + if (headers.hasOwnProperty(key)) { + header = headers[key]; + xhr.setRequestHeader(key, header); + } + } + } catch (e) { + // TODO Request shouldn't fire events from its owner + me.owner.fireEvent('exception', key, header); + } + return headers; + }, + /** + * Creates the appropriate XDR transport for this browser. + * - IE 7 and below don't support CORS + * - IE 8 and 9 support CORS with native XDomainRequest object + * - IE 10 (and above?) supports CORS with native XMLHttpRequest object + * @private + */ + getXdrInstance: function() { + var xdr; + if (Ext.ieVersion >= 8) { + xdr = new XDomainRequest(); + } else { + Ext.raise({ + msg: 'Your browser does not support CORS' + }); + } + return xdr; + }, + /** + * Creates the appropriate XHR transport for this browser. + * @private + */ + getXhrInstance: (function() { + var options = [ + function() { + return new XMLHttpRequest(); + }, + function() { + return new ActiveXObject('MSXML2.XMLHTTP.3.0'); + }, + // jshint ignore:line + function() { + return new ActiveXObject('MSXML2.XMLHTTP'); + }, + // jshint ignore:line + function() { + return new ActiveXObject('Microsoft.XMLHTTP'); + } + ], + // jshint ignore:line + i = 0, + len = options.length, + xhr; + for (; i < len; ++i) { + try { + xhr = options[i]; + xhr(); + break; + } catch (e) {} + } + return xhr; + }()), + processXdrRequest: function(request, xhr) { + var me = this; + // Mutate the request object as per XDR spec. + delete request.headers; + request.contentType = request.options.contentType || me.defaultXdrContentType; + xhr.onload = me.bindStateChange(true); + xhr.onerror = xhr.ontimeout = me.bindStateChange(false); + }, + processXdrResponse: function(response, xhr) { + // Mutate the response object as per XDR spec. + response.getAllResponseHeaders = function() { + return []; + }; + response.getResponseHeader = function() { + return ''; + }; + response.contentType = xhr.contentType || this.defaultXdrContentType; + }, + bindStateChange: function(xdrResult) { + var me = this; + return function() { + Ext.elevate(function() { + me.onStateChange(xdrResult); + }); + }; + }, + onStateChange: function(xdrResult) { + var me = this, + xhr = me.xhr; + // Using CORS with IE doesn't support readyState so we fake it. + if ((xhr && xhr.readyState == 4) || me.isXdr) { + me.clearTimer(); + me.onComplete(xdrResult); + me.cleanup(); + } + }, + /** + * To be called when the request has come back from the server + * @param {Object} xdrResult + * @return {Object} The response + * @private + */ + onComplete: function(xdrResult) { + var me = this, + owner = me.owner, + options = me.options, + xhr = me.xhr, + failure = { + success: false, + isException: false + }, + result, success, response; + if (!xhr || me.destroyed) { + return me.result = failure; + } + try { + result = Ext.data.request.Ajax.parseStatus(xhr.status, xhr); + if (result.success) { + // This is quite difficult to reproduce, however if we abort a request + // just before it returns from the server, occasionally the status will be + // returned correctly but the request is still yet to be complete. + result.success = xhr.readyState === 4; + } + } catch (e) { + // In some browsers we can't access the status if the readyState is not 4, + // so the request has failed + result = failure; + } + success = me.success = me.isXdr ? xdrResult : result.success; + if (success) { + response = me.createResponse(xhr); + if (owner.hasListeners.requestcomplete) { + owner.fireEvent('requestcomplete', owner, response, options); + } + if (options.success) { + Ext.callback(options.success, options.scope, [ + response, + options + ]); + } + } else { + if (result.isException || me.aborted || me.timedout) { + response = me.createException(xhr); + } else { + response = me.createResponse(xhr); + } + if (owner.hasListeners.requestexception) { + owner.fireEvent('requestexception', owner, response, options); + } + if (options.failure) { + Ext.callback(options.failure, options.scope, [ + response, + options + ]); + } + } + me.result = response; + if (options.callback) { + Ext.callback(options.callback, options.scope, [ + options, + success, + response + ]); + } + owner.onRequestComplete(me); + me.callParent([ + xdrResult + ]); + return response; + }, + /** + * Creates the response object + * @param {Object} xhr + * @private + */ + createResponse: function(xhr) { + var me = this, + isXdr = me.isXdr, + headers = {}, + lines = isXdr ? [] : xhr.getAllResponseHeaders().replace(/\r\n/g, '\n').split('\n'), + count = lines.length, + line, index, key, response, byteArray; + while (count--) { + line = lines[count]; + index = line.indexOf(':'); + if (index >= 0) { + key = line.substr(0, index).toLowerCase(); + if (line.charAt(index + 1) == ' ') { + ++index; + } + headers[key] = line.substr(index + 1); + } + } + response = { + request: me, + requestId: me.id, + status: xhr.status, + statusText: xhr.statusText, + getResponseHeader: function(header) { + return headers[header.toLowerCase()]; + }, + getAllResponseHeaders: function() { + return headers; + } + }; + if (isXdr) { + me.processXdrResponse(response, xhr); + } + if (me.binary) { + response.responseBytes = me.getByteArray(xhr); + } else { + // an error is thrown when trying to access responseText or responseXML + // on an xhr object with responseType of 'arraybuffer', so only attempt + // to set these properties in the response if we're not dealing with + // binary data + response.responseText = xhr.responseText; + response.responseXML = xhr.responseXML; + } + return response; + }, + destroy: function() { + this.xhr = null; + this.callParent(); + }, + privates: { + /** + * Gets binary data from the xhr response object and returns it as a byte array + * @param {Object} xhr the xhr response object + * @return {Uint8Array/Array} + * @private + */ + getByteArray: function(xhr) { + var response = xhr.response, + responseBody = xhr.responseBody, + Cls = Ext.data.flash && Ext.data.flash.BinaryXhr, + byteArray, responseText, len, i; + if (xhr instanceof Cls) { + // If this was a BinaryXHR request via flash, we already have the bytes ready + byteArray = xhr.responseBytes; + } else if (window.Uint8Array) { + // Modern browsers (including IE10) have a native byte array + // which can be created by passing the ArrayBuffer (returned as + // the xhr.response property) to the Uint8Array constructor. + byteArray = response ? new Uint8Array(response) : []; + } else if (Ext.isIE9p) { + // In IE9 and below the responseBody property contains a byte array + // but it is not directly accessible using javascript. + // In IE9p we can get the bytes by constructing a VBArray + // using the responseBody and then converting it to an Array. + try { + byteArray = new VBArray(responseBody).toArray(); + } // jshint ignore:line + catch (e) { + // If the binary response is empty, the VBArray constructor will + // choke on the responseBody. We can't simply do a null check + // on responseBody because responseBody is always falsy when it + // contains binary data. + byteArray = []; + } + } else if (Ext.isIE) { + // IE8 and below also have a VBArray constructor, but throw a + // "VBArray Expected" error if you try to pass the responseBody to + // the VBArray constructor. + // http://msdn.microsoft.com/en-us/library/ye3x9by3%28v=vs.71%29.aspx + // so we have to use vbscript injection to access the bytes + if (!this.self.vbScriptInjected) { + this.injectVBScript(); + } + getIEByteArray(xhr.responseBody, byteArray = []); + } else // jshint ignore:line + { + // in other older browsers make a best-effort attempt to read the + // bytes from responseText + byteArray = []; + responseText = xhr.responseText; + len = responseText.length; + for (i = 0; i < len; i++) { + // Some characters have an extra byte 0xF7 in the high order + // position. Throw away the high order byte and then push the + // result onto the byteArray. + byteArray.push(responseText.charCodeAt(i) & 255); + } + } + return byteArray; + }, + /** + * Injects a vbscript tag containing a 'getIEByteArray' method for reading + * binary data from an xhr response in IE8 and below. + * @private + */ + injectVBScript: function() { + var scriptTag = document.createElement('script'); + scriptTag.type = 'text/vbscript'; + scriptTag.text = [ + 'Function getIEByteArray(byteArray, out)', + 'Dim len, i', + 'len = LenB(byteArray)', + 'For i = 1 to len', + 'out.push(AscB(MidB(byteArray, i, 1)))', + 'Next', + 'End Function' + ].join('\n'); + Ext.getHead().dom.appendChild(scriptTag); + this.self.vbScriptInjected = true; + } + } +}); + +/** + * This class manages a pending form submit. Instances of this type are created by the + * `{@link Ext.data.Connection#request}` method. + * @since 6.0.0 + */ +Ext.define('Ext.data.request.Form', { + extend: 'Ext.data.request.Base', + alias: 'request.form', + start: function(data) { + var me = this, + options = me.options, + requestOptions = me.requestOptions; + // Parent will set the timeout + me.callParent([ + data + ]); + me.form = me.upload(options.form, requestOptions.url, requestOptions.data, options); + return me; + }, + abort: function(force) { + var me = this, + frame; + if (me.isLoading()) { + try { + frame = me.frame.dom; + if (frame.stop) { + frame.stop(); + } else { + frame.document.execCommand('Stop'); + } + } catch (e) {} + } + // ignore + me.callParent([ + force + ]); + me.onComplete(); + me.cleanup(); + }, + /* + * Clean up any left over information from the form submission. + */ + cleanup: function() { + var me = this, + frame = me.frame; + if (frame) { + // onComplete hasn't fired yet if frame != null so need to clean up + frame.un('load', me.onComplete, me); + Ext.removeNode(frame); + } + me.frame = me.form = null; + }, + isLoading: function() { + return !!this.frame; + }, + /** + * Uploads a form using a hidden iframe. + * @param {String/HTMLElement/Ext.dom.Element} form The form to upload + * @param {String} url The url to post to + * @param {String} params Any extra parameters to pass + * @param {Object} options The initial options + * @private + */ + upload: function(form, url, params, options) { + form = Ext.getDom(form); + options = options || {}; + var frameDom = document.createElement('iframe'), + frame = Ext.get(frameDom), + id = frame.id, + hiddens = [], + encoding = 'multipart/form-data', + buf = { + target: form.target, + method: form.method, + encoding: form.encoding, + enctype: form.enctype, + action: form.action + }, + addField = function(name, value) { + hiddenItem = document.createElement('input'); + Ext.fly(hiddenItem).set({ + type: 'hidden', + value: value, + name: name + }); + form.appendChild(hiddenItem); + hiddens.push(hiddenItem); + }, + hiddenItem, obj, value, name, vLen, v, hLen, h; + /* + * Originally this behaviour was modified for Opera 10 to apply the secure URL after + * the frame had been added to the document. It seems this has since been corrected in + * Opera so the behaviour has been reverted, the URL will be set before being added. + */ + frame.set({ + name: id, + cls: Ext.baseCSSPrefix + 'hidden-display', + src: Ext.SSL_SECURE_URL, + tabIndex: -1 + }); + document.body.appendChild(frameDom); + document.body.appendChild(form); + // This is required so that IE doesn't pop the response up in a new window. + if (document.frames) { + document.frames[id].name = id; + } + Ext.fly(form).set({ + target: id, + method: 'POST', + enctype: encoding, + encoding: encoding, + action: url || buf.action + }); + // add dynamic params + if (params) { + obj = Ext.Object.fromQueryString(params) || {}; + for (name in obj) { + if (obj.hasOwnProperty(name)) { + value = obj[name]; + if (Ext.isArray(value)) { + vLen = value.length; + for (v = 0; v < vLen; v++) { + addField(name, value[v]); + } + } else { + addField(name, value); + } + } + } + } + this.frame = frame; + frame.on({ + load: this.onComplete, + scope: this, + // Opera introduces multiple 'load' events, so account for extras as well + single: !Ext.isOpera + }); + form.submit(); + document.body.removeChild(form); + // Restore form to previous settings + Ext.fly(form).set(buf); + for (hLen = hiddens.length , h = 0; h < hLen; h++) { + Ext.removeNode(hiddens[h]); + } + return form; + }, + getDoc: function() { + var frame = this.frame.dom; + return (frame && (frame.contentWindow.document || frame.contentDocument)) || (window.frames[frame.id] || {}).document; + }, + getTimeout: function() { + // For a form post, since it can include large file uploads, we do not use the + // default timeout from the owner. Only explicit timeouts passed in the options + // are meaningful here. + return this.options.timeout; + }, + /** + * Callback handler for the upload function. After we've submitted the form via the + * iframe this creates a bogus response object to simulate an XHR and populates its + * responseText from the now-loaded iframe's document body (or a textarea inside the + * body). We then clean up by removing the iframe. + * @private + */ + onComplete: function() { + var me = this, + frame = me.frame, + owner = me.owner, + options = me.options, + callback, doc, success, contentNode, response; + // Nulled out frame means onComplete was fired already + if (!frame) { + return; + } + if (me.aborted || me.timedout) { + me.result = response = me.createException(); + response.responseXML = null; + response.responseText = Ext.encode({ + success: false, + message: Ext.String.trim(response.statusText) + }); + response.request = me; + callback = options.failure; + success = false; + } else { + try { + doc = me.getDoc(); + // bogus response object + me.result = response = { + responseText: '', + responseXML: null, + request: me + }; + // Opera will fire an extraneous load event on about:blank + // We want to ignore this since the load event will be fired twice + if (doc) { + //TODO: See if this still applies vs Current opera-webkit releases + if (Ext.isOpera && doc.location == Ext.SSL_SECURE_URL) { + return; + } + if (doc.body) { + // Response sent as Content-Type: text/json or text/plain. + // Browser will embed it in a
 element.
+                        // Note: The statement below tests the result of an assignment.
+                        if ((contentNode = doc.body.firstChild) && /pre/i.test(contentNode.tagName)) {
+                            response.responseText = contentNode.textContent || contentNode.innerText;
+                        }
+                        // Response sent as Content-Type: text/html. We must still support
+                        // JSON response wrapped in textarea.
+                        // Note: The statement below tests the result of an assignment.
+                        else if ((contentNode = doc.getElementsByTagName('textarea')[0])) {
+                            response.responseText = contentNode.value;
+                        } else // Response sent as Content-Type: text/html with no wrapping. Scrape
+                        // JSON response out of text
+                        {
+                            response.responseText = doc.body.textContent || doc.body.innerText;
+                        }
+                    }
+                    //in IE the document may still have a body even if returns XML.
+                    // TODO What is this about?
+                    response.responseXML = doc.XMLDocument || doc;
+                    callback = options.success;
+                    success = true;
+                    response.status = 200;
+                } else {
+                    Ext.raise("Could not acquire a suitable connection for the file upload service.");
+                }
+            } catch (e) {
+                me.result = response = me.createException();
+                // Report any error in the message property
+                response.status = 400;
+                response.statusText = (e.message || e.description) + '';
+                response.responseText = Ext.encode({
+                    success: false,
+                    message: Ext.String.trim(response.statusText)
+                });
+                response.responseXML = null;
+                callback = options.failure;
+                success = false;
+            }
+        }
+        me.frame = null;
+        me.success = success;
+        owner.fireEvent(success ? 'requestcomplete' : 'requestexception', owner, response, options);
+        Ext.callback(callback, options.scope, [
+            response,
+            options
+        ]);
+        Ext.callback(options.callback, options.scope, [
+            options,
+            success,
+            response
+        ]);
+        owner.onRequestComplete(me);
+        // Must defer slightly to permit full exit from load event before destruction
+        Ext.asap(frame.destroy, frame);
+        me.callParent();
+    },
+    destroy: function() {
+        this.cleanup();
+        this.callParent();
+    }
+});
+
+/**
+ * The Connection class encapsulates a connection to the page's originating domain, allowing requests to be made either
+ * to a configured URL, or to a URL specified at request time.
+ *
+ * Requests made by this class are asynchronous, and will return immediately. No data from the server will be available
+ * to the statement immediately following the {@link #request} call. To process returned data, use a success callback
+ * in the request options object, or an {@link #requestcomplete event listener}.
+ *
+ * # File Uploads
+ *
+ * File uploads are not performed using normal "Ajax" techniques, that is they are not performed using XMLHttpRequests.
+ * Instead the form is submitted in the standard manner with the DOM <form> element temporarily modified to have its
+ * target set to refer to a dynamically generated, hidden <iframe> which is inserted into the document but removed
+ * after the return data has been gathered.
+ *
+ * The server response is parsed by the browser to create the document for the IFRAME. If the server is using JSON to
+ * send the return object, then the Content-Type header must be set to "text/html" in order to tell the browser to
+ * insert the text unchanged into the document body.
+ *
+ * Characters which are significant to an HTML parser must be sent as HTML entities, so encode `<` as `<`, `&` as
+ * `&` etc.
+ *
+ * The response text is retrieved from the document, and a fake XMLHttpRequest object is created containing a
+ * responseText property in order to conform to the requirements of event handlers and callbacks.
+ *
+ * Be aware that file upload packets are sent with the content type multipart/form and some server technologies
+ * (notably JEE) may require some custom processing in order to retrieve parameter names and parameter values from the
+ * packet content.
+ *
+ * Also note that it's not possible to check the response code of the hidden iframe, so the success handler will ALWAYS fire.
+ *
+ * # Binary Posts
+ *
+ * The class supports posting binary data to the server by using native browser capabilities, or a flash polyfill plugin in browsers that do not support native binary posting (e.g. Internet Explorer version 9 or less). A number of limitations exist when the polyfill is used:
+ *
+ * - Only asynchronous connections are supported.
+ * - Only the POST method can be used.
+ * - The return data can only be binary for now. Set the {@link Ext.data.Connection#binary binary} parameter to true.
+ * - Only the 0, 1 and 4 (complete) readyState values will be reported to listeners.
+ * - The flash object will be injected at the bottom of the document and should be invisible.
+ * - Important: See note about packaing the flash plugin with the app in the documenetation of {@link Ext.data.flash.BinaryXhr BinaryXhr}.
+ *
+ */
+Ext.define('Ext.data.Connection', {
+    mixins: {
+        observable: 'Ext.mixin.Observable'
+    },
+    requires: [
+        'Ext.data.request.Ajax',
+        'Ext.data.request.Form',
+        'Ext.data.flash.BinaryXhr',
+        'Ext.Deferred'
+    ],
+    statics: {
+        requestId: 0
+    },
+    enctypeRe: /multipart\/form-data/i,
+    config: {
+        /**
+         * @cfg {String} url
+         * The URL for this connection.
+         */
+        url: null,
+        /**
+         * @cfg {Boolean} async
+         * `true` if this request should run asynchronously. Setting this to `false` should generally
+         * be avoided, since it will cause the UI to be blocked, the user won't be able to interact
+         * with the browser until the request completes.
+         */
+        async: true,
+        /**
+         * @cfg {String} username
+         * The username to pass when using {@link #withCredentials}.
+         */
+        username: '',
+        /**
+         * @cfg {String} password
+         * The password to pass when using {@link #withCredentials}.
+         */
+        password: '',
+        /**
+         * @cfg {Boolean} disableCaching
+         * True to add a unique cache-buster param to GET requests.
+         */
+        disableCaching: true,
+        /**
+         * @cfg {Boolean} withCredentials
+         * True to set `withCredentials = true` on the XHR object
+         */
+        withCredentials: false,
+        /**
+         * @cfg {Boolean} binary
+         * True if the response should be treated as binary data.  If true, the binary
+         * data will be accessible as a "responseBytes" property on the response object.
+         */
+        binary: false,
+        /**
+         * @cfg {Boolean} cors
+         * True to enable CORS support on the XHR object. Currently the only effect of this option
+         * is to use the XDomainRequest object instead of XMLHttpRequest if the browser is IE8 or above.
+         */
+        cors: false,
+        isXdr: false,
+        defaultXdrContentType: 'text/plain',
+        /**
+         * @cfg {String} disableCachingParam
+         * Change the parameter which is sent went disabling caching through a cache buster.
+         */
+        disableCachingParam: '_dc',
+        /**
+         * @cfg {Number} [timeout=30000] The timeout in milliseconds to be used for
+         * requests.
+         * Defaults to 30000 milliseconds (30 seconds).
+         *
+         * When a request fails due to timeout the XMLHttpRequest response object will
+         * contain:
+         *
+         *     timedout: true
+         */
+        timeout: 30000,
+        /**
+         * @cfg {Object} [extraParams] Any parameters to be appended to the request.
+         */
+        extraParams: null,
+        /**
+         * @cfg {Boolean} [autoAbort=false]
+         * Whether this request should abort any pending requests.
+         */
+        autoAbort: false,
+        /**
+         * @cfg {String} method
+         * The default HTTP method to be used for requests.
+         *
+         * If not set, but {@link #request} params are present, POST will be used;
+         * otherwise, GET will be used.
+         */
+        method: null,
+        /**
+         * @cfg {Object} defaultHeaders
+         * An object containing request headers which are added to each request made by this object.
+         */
+        defaultHeaders: null,
+        /**
+         * @cfg {String} defaultPostHeader
+         * The default header to be sent out with any post request.
+         */
+        defaultPostHeader: 'application/x-www-form-urlencoded; charset=UTF-8',
+        /**
+         * @cfg {Boolean} useDefaultXhrHeader
+         * `true` to send the {@link #defaultXhrHeader} along with any request.
+         */
+        useDefaultXhrHeader: true,
+        /**
+         * @cfg {String}
+         * The header to send with Ajax requests. Also see {@link #useDefaultXhrHeader}.
+         */
+        defaultXhrHeader: 'XMLHttpRequest'
+    },
+    /**
+     * @event beforerequest
+     * @preventable
+     * Fires before a network request is made to retrieve a data object.
+     * @param {Ext.data.Connection} conn This Connection object.
+     * @param {Object} options The options config object passed to the {@link #request} method.
+     */
+    /**
+     * @event requestcomplete
+     * Fires if the request was successfully completed.
+     * @param {Ext.data.Connection} conn This Connection object.
+     * @param {Object} response The XHR object containing the response data.
+     * See [The XMLHttpRequest Object](http://www.w3.org/TR/XMLHttpRequest/) for details.
+     * @param {Object} options The options config object passed to the {@link #request} method.
+     */
+    /**
+     * @event requestexception
+     * Fires if an error HTTP status was returned from the server. This event may also
+     * be listened to in the event that a request has timed out or has been aborted.
+     * See [HTTP Status Code Definitions](http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html)
+     * for details of HTTP status codes.
+     * @param {Ext.data.Connection} conn This Connection object.
+     * @param {Object} response The XHR object containing the response data.
+     * See [The XMLHttpRequest Object](http://www.w3.org/TR/XMLHttpRequest/) for details.
+     * @param {Object} options The options config object passed to the {@link #request} method.
+     */
+    constructor: function(config) {
+        // Will call initConfig
+        this.mixins.observable.constructor.call(this, config);
+        this.requests = {};
+    },
+    /**
+     * @method request
+     * Sends an HTTP (Ajax) request to a remote server.
+     *
+     * **Important:** Ajax server requests are asynchronous, and this call will
+     * return before the response has been received.
+     *
+     * Instead, process any returned data using a promise:
+     *
+     *      Ext.Ajax.request({
+     *          url: 'ajax_demo/sample.json'
+     *      }).then(function(response, opts) {
+     *          var obj = Ext.decode(response.responseText);
+     *          console.dir(obj);
+     *      },
+     *      function(response, opts) {
+     *          console.log('server-side failure with status code ' + response.status);
+     *      });
+     *
+     * Or in callback functions:
+     *
+     *      Ext.Ajax.request({
+     *          url: 'ajax_demo/sample.json',
+     *
+     *          success: function(response, opts) {
+     *              var obj = Ext.decode(response.responseText);
+     *              console.dir(obj);
+     *          },
+     *
+     *          failure: function(response, opts) {
+     *              console.log('server-side failure with status code ' + response.status);
+     *          }
+     *      });
+     *
+     * To execute a callback function in the correct scope, use the `scope` option.
+     *
+     * @param {Object} options An object which may contain the following properties:
+     *
+     * (The options object may also contain any other property which might be needed to perform
+     * postprocessing in a callback because it is passed to callback functions.)
+     *
+     * @param {String/Function} options.url The URL to which to send the request, or a function
+     * to call which returns a URL string. The scope of the function is specified by the `scope` option.
+     * Defaults to the configured `url`.
+     *
+     * @param {Boolean} options.async `true` if this request should run asynchronously.
+     * Setting this to `false` should generally be avoided, since it will cause the UI to be
+     * blocked, the user won't be able to interact with the browser until the request completes.
+     * Defaults to `true`.
+     *
+     * @param {Object/String/Function} options.params An object containing properties which are
+     * used as parameters to the request, a url encoded string or a function to call to get either. The scope
+     * of the function is specified by the `scope` option.
+     *
+     * @param {String} options.method The HTTP method to use
+     * for the request. Defaults to the configured method, or if no method was configured,
+     * "GET" if no parameters are being sent, and "POST" if parameters are being sent.  Note that
+     * the method name is case-sensitive and should be all caps.
+     *
+     * @param {Function} options.callback The function to be called upon receipt of the HTTP response.
+     * The callback is called regardless of success or failure and is passed the following parameters:
+     * @param {Object} options.callback.options The parameter to the request call.
+     * @param {Boolean} options.callback.success True if the request succeeded.
+     * @param {Object} options.callback.response The XMLHttpRequest object containing the response data.
+     * See [www.w3.org/TR/XMLHttpRequest/](http://www.w3.org/TR/XMLHttpRequest/) for details about
+     * accessing elements of the response.
+     *
+     * @param {Function} options.success The function to be called upon success of the request.
+     * The callback is passed the following parameters:
+     * @param {Object} options.success.response The XMLHttpRequest object containing the response data.
+     * @param {Object} options.success.options The parameter to the request call.
+     *
+     * @param {Function} options.failure The function to be called upon failure of the request.
+     * The callback is passed the following parameters:
+     * @param {Object} options.failure.response The XMLHttpRequest object containing the response data.
+     * @param {Object} options.failure.options The parameter to the request call.
+     *
+     * @param {Object} options.scope The scope in which to execute the callbacks: The "this" object for
+     * the callback function. If the `url`, or `params` options were specified as functions from which to
+     * draw values, then this also serves as the scope for those function calls. Defaults to the browser
+     * window.
+     *
+     * @param {Number} options.timeout The timeout in milliseconds to be used for this
+     * request.
+     * Defaults to 30000 milliseconds (30 seconds).
+     *
+     * When a request fails due to timeout the XMLHttpRequest response object will
+     * contain:
+     *
+     *     timedout: true
+     *
+     * @param {Ext.Element/HTMLElement/String} options.form The `
` Element or the id of the `` + * to pull parameters from. + * + * @param {Boolean} options.isUpload **Only meaningful when used with the `form` option.** + * + * True if the form object is a file upload (will be set automatically if the form was configured + * with **`enctype`** `"multipart/form-data"`). + * + * File uploads are not performed using normal "Ajax" techniques, that is they are **not** + * performed using XMLHttpRequests. Instead the form is submitted in the standard manner with the + * DOM `<form>` element temporarily modified to have its + * [target](https://developer.mozilla.org/en-US/docs/Web/API/HTMLFormElement/target) + * set to refer to a dynamically generated, hidden `<iframe>` which is inserted + * into the document but removed after the return data has been gathered. + * + * The server response is parsed by the browser to create the document for the IFRAME. If the + * server is using JSON to send the return object, then the + * [Content-Type](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Type) + * header must be set to "text/html" in order to tell the browser to insert the text + * unchanged into the document body. + * + * The response text is retrieved from the document, and a fake XMLHttpRequest object is created + * containing a `responseText` property in order to conform to the requirements of event handlers + * and callbacks. + * + * Be aware that file upload packets are sent with the content type + * [multipart/form](https://tools.ietf.org/html/rfc7233#section-4.1) and some server + * technologies (notably JEE) may require some custom processing in order to retrieve parameter names + * and parameter values from the packet content. + * + * - [target](http://www.w3.org/TR/REC-html40/present/frames.html#adef-target) + * - [Content-Type](http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.17) + * - [multipart/form](http://www.faqs.org/rfcs/rfc2388.html) + * + * @param {Object} options.headers Request headers to set for the request. + * The XHR will attempt to set an appropriate Content-Type based on the params/data passed + * to the request. To prevent this, setting the Content-Type header to `null` or `undefined` + * will not attempt to set any Content-Type and it will be left to the browser. + * + * @param {Object} options.xmlData XML document to use for the post. Note: This will be used instead + * of params for the post data. Any params will be appended to the URL. + * + * @param {Object/String} options.jsonData JSON data to use as the post. Note: This will be used + * instead of params for the post data. Any params will be appended to the URL. + * + * @param {String} options.rawData A raw string to use as the post. Note: This will be used + * instead of params for the post data. Any params will be appended to the URL. + * + * @param {Array} options.binaryData An array of bytes to submit in binary form. Any params will be appended to the URL. If binaryData is present, you must set {@link Ext.data.Connection#binary binary} to true and options.method to POST. + * + * @param {Boolean} options.disableCaching True to add a unique cache-buster param to GET requests. + * + * @param {Boolean} options.withCredentials True to add the withCredentials property to the XHR object + * + * @param {String} options.username The username to pass when using `withCredentials`. + * + * @param {String} options.password The password to pass when using `withCredentials`. + * + * @param {Boolean} options.binary True if the response should be treated as binary data. If true, the binary + * data will be accessible as a "responseBytes" property on the response object. + * + * @return {Ext.data.request.Base} The request object. This may be used to abort the + * request. + */ + request: function(options) { + options = options || {}; + var me = this, + requestOptions, request; + if (me.fireEvent('beforerequest', me, options) !== false) { + requestOptions = me.setOptions(options, options.scope || Ext.global); + request = me.createRequest(options, requestOptions); + return request.start(requestOptions.data); + } + // Reusing for response + request = { + status: -1, + statusText: 'Request cancelled in beforerequest event handler' + }; + Ext.callback(options.callback, options.scope, [ + options, + false, + request + ]); + return Ext.Deferred.rejected([ + options, + false, + request + ]); + }, + createRequest: function(options, requestOptions) { + var me = this, + type = options.type || requestOptions.type, + request; + // If request type is not specified we have to deduce it + if (!type) { + type = me.isFormUpload(options) ? 'form' : 'ajax'; + } + // if autoabort is set, cancel the current transactions + if (options.autoAbort || me.getAutoAbort()) { + me.abort(); + } + // It is possible for the original options object to be mutated if somebody + // had overridden Connection.setOptions method; it is also possible that such + // override would do a sensible thing and mutate outgoing requestOptions instead. + // So we have to pass *both* to the Request constructor, along with the set + // of defaults potentially set on the Connection instance. + // If it looks ridiculous, that's because it is; things we have to do for + // backward compatibility... + request = Ext.Factory.request({ + type: type, + owner: me, + options: options, + requestOptions: requestOptions, + ownerConfig: me.getConfig() + }); + me.requests[request.id] = request; + me.latestId = request.id; + return request; + }, + /** + * Detects whether the form is intended to be used for an upload. + * @private + */ + isFormUpload: function(options) { + var form = this.getForm(options); + if (form) { + return options.isUpload || this.enctypeRe.test(form.getAttribute('enctype')); + } + return false; + }, + /** + * Gets the form object from options. + * @private + * @param {Object} options The request options + * @return {HTMLElement} The form, null if not passed + */ + getForm: function(options) { + return Ext.getDom(options.form); + }, + /** + * Sets various options such as the url, params for the request + * @param {Object} options The initial options + * @param {Object} scope The scope to execute in + * @return {Object} The params for the request + */ + setOptions: function(options, scope) { + var me = this, + params = options.params || {}, + extraParams = me.getExtraParams(), + urlParams = options.urlParams, + url = options.url || me.getUrl(), + cors = options.cors, + jsonData = options.jsonData, + method, disableCache, data; + if (cors !== undefined) { + me.setCors(cors); + } + // allow params to be a method that returns the params object + if (Ext.isFunction(params)) { + params = params.call(scope, options); + } + // allow url to be a method that returns the actual url + if (Ext.isFunction(url)) { + url = url.call(scope, options); + } + url = this.setupUrl(options, url); + if (!url) { + Ext.raise({ + options: options, + msg: 'No URL specified' + }); + } + // check for xml or json data, and make sure json data is encoded + data = options.rawData || options.binaryData || options.xmlData || jsonData || null; + if (jsonData && !Ext.isPrimitive(jsonData)) { + data = Ext.encode(data); + } + // Check for binary data. Transform if needed + if (options.binaryData) { + if (!Ext.isArray(options.binaryData)) { + Ext.log.warn("Binary submission data must be an array of byte values! Instead got " + typeof (options.binaryData)); + } + if (me.nativeBinaryPostSupport()) { + data = (new Uint8Array(options.binaryData)); + if ((Ext.isChrome && Ext.chromeVersion < 22) || Ext.isSafari || Ext.isGecko) { + data = data.buffer; + } + } + } + // send the underlying buffer, not the view, since that's not supported on versions of chrome older than 22 + // make sure params are a url encoded string and include any extraParams if specified + if (Ext.isObject(params)) { + params = Ext.Object.toQueryString(params); + } + if (Ext.isObject(extraParams)) { + extraParams = Ext.Object.toQueryString(extraParams); + } + params = params + ((extraParams) ? ((params) ? '&' : '') + extraParams : ''); + urlParams = Ext.isObject(urlParams) ? Ext.Object.toQueryString(urlParams) : urlParams; + params = this.setupParams(options, params); + // decide the proper method for this request + method = (options.method || me.getMethod() || ((params || data) ? 'POST' : 'GET')).toUpperCase(); + this.setupMethod(options, method); + disableCache = options.disableCaching !== false ? (options.disableCaching || me.getDisableCaching()) : false; + // if the method is get append date to prevent caching + if (method === 'GET' && disableCache) { + url = Ext.urlAppend(url, (options.disableCachingParam || me.getDisableCachingParam()) + '=' + (new Date().getTime())); + } + // if the method is get or there is json/xml data append the params to the url + if ((method == 'GET' || data) && params) { + url = Ext.urlAppend(url, params); + params = null; + } + // allow params to be forced into the url + if (urlParams) { + url = Ext.urlAppend(url, urlParams); + } + return { + url: url, + method: method, + data: data || params || null + }; + }, + /** + * Template method for overriding url + * @private + * @param {Object} options + * @param {String} url + * @return {String} The modified url + */ + setupUrl: function(options, url) { + var form = this.getForm(options); + if (form) { + url = url || form.action; + } + return url; + }, + /** + * Template method for overriding params + * @private + * @param {Object} options + * @param {String} params + * @return {String} The modified params + */ + setupParams: function(options, params) { + var form = this.getForm(options), + serializedForm; + if (form && !this.isFormUpload(options)) { + serializedForm = Ext.Element.serializeForm(form); + params = params ? (params + '&' + serializedForm) : serializedForm; + } + return params; + }, + /** + * Template method for overriding method + * @private + * @param {Object} options + * @param {String} method + * @return {String} The modified method + */ + setupMethod: function(options, method) { + if (this.isFormUpload(options)) { + return 'POST'; + } + return method; + }, + /** + * Determines whether this object has a request outstanding. + * + * @param {Object} [request] Defaults to the last transaction + * + * @return {Boolean} True if there is an outstanding request. + */ + isLoading: function(request) { + if (!request) { + request = this.getLatest(); + } + return request ? request.isLoading() : false; + }, + /** + * Aborts an active request. + * @param {Ext.ajax.Request} [request] Defaults to the last request + */ + abort: function(request) { + if (!request) { + request = this.getLatest(); + } + if (request && request.isLoading()) { + request.abort(); + } + }, + /** + * Aborts all active requests + */ + abortAll: function() { + var requests = this.requests, + id; + for (id in requests) { + this.abort(requests[id]); + } + }, + /** + * Gets the most recent request + * @return {Object} The request. Null if there is no recent request + * @private + */ + getLatest: function() { + var id = this.latestId, + request; + if (id) { + request = this.requests[id]; + } + return request || null; + }, + /** + * Clears the timeout on the request + * @param {Object} request The request + * @private + */ + clearTimeout: function(request) { + if (!request) { + request = this.getLatest(); + } + if (request) { + request.clearTimer(); + } + }, + onRequestComplete: function(request) { + delete this.requests[request.id]; + }, + /** + * @return {Boolean} `true` if the browser can natively post binary data. + * @private + */ + nativeBinaryPostSupport: function() { + return Ext.isChrome || (Ext.isSafari && Ext.isDefined(window.Uint8Array)) || (Ext.isGecko && Ext.isDefined(window.Uint8Array)); + } +}); + +/** + * A singleton instance of an `{@link Ext.data.Connection}`. This class is used to + * communicate with your server side code. It can be used as follows: + * + * Ext.Ajax.request({ + * url: 'ajax_demo/sample.json', + * + * success: function(response, opts) { + * var obj = Ext.decode(response.responseText); + * console.dir(obj); + * }, + * + * failure: function(response, opts) { + * console.log('server-side failure with status code ' + response.status); + * } + * }); + * + * Default options for all requests can be set by changing a property on the Ext.Ajax class: + * + * Ext.Ajax.setTimeout(60000); // 60 seconds + * + * Any options specified in the request method for the Ajax request will override any + * defaults set on the `Ext.Ajax` singleton. In the code sample below, the timeout for the + * request will be 60 seconds. + * + * Ext.Ajax.setTimeout(120000); // 120 seconds + * + * Ext.Ajax.request({ + * url: 'page.aspx', + * timeout: 60000 + * }); + * + * In general, this class will be used for all Ajax requests in your application. The main + * reason for creating a separate `{@link Ext.data.Connection}` is for a series of + * requests that share common settings that are different to all other requests in the + * application. + */ +Ext.define('Ext.Ajax', { + extend: 'Ext.data.Connection', + singleton: true, + /** + * @cfg {Object} extraParams + * @hide + */ + /** + * @cfg {Object} defaultHeaders + * @hide + */ + /** + * @cfg {String} method + * @hide + */ + /** + * @cfg {Number} timeout + * @hide + */ + /** + * @cfg {Boolean} autoAbort + * @hide + */ + /** + * @cfg {Boolean} disableCaching + * @hide + */ + /** + * @property {Boolean} disableCaching + * True to add a unique cache-buster param to GET requests. Defaults to true. + */ + /** + * @property {String} url + * The default URL to be used for requests to the server. + * If the server receives all requests through one URL, setting this once is easier than + * entering it on every request. + */ + /** + * @property {Object} extraParams + * An object containing properties which are used as extra parameters to each request made + * by this object. Session information and other data that you need + * to pass with each request are commonly put here. + */ + /** + * @property {Object} defaultHeaders + * An object containing request headers which are added to each request made by this object. + */ + /** + * @property {String} method + * The default HTTP method to be used for requests. Note that this is case-sensitive and + * should be all caps (if not set but params are present will use `POST`, otherwise will + * use `GET`.) + */ + /** + * @property {Number} timeout + * The timeout in milliseconds to be used for requests. Defaults to 30000. + * + * When a request fails due to timeout the XMLHttpRequest response object will + * contain: + * + * timedout: true + */ + /** + * @property {Boolean} autoAbort + * Whether a new request should abort any pending requests. + */ + autoAbort: false +}); + +/** + * @private + */ +Ext.define('Ext.AnimationQueue', { + singleton: true, + constructor: function() { + var me = this; + me.queue = []; + me.taskQueue = []; + me.runningQueue = []; + me.idleQueue = []; + me.isRunning = false; + me.isIdle = true; + me.run = me.run.bind(me); + // iOS has a nasty bug which causes pending requestAnimationFrame to not release + // the callback when the WebView is switched back and forth from / to being background process + // We use a watchdog timer to workaround this, and restore the pending state correctly if this happens + // This timer has to be set as an interval from the very beginning and we have to keep it running for + // as long as the app lives, setting it later doesn't seem to work. + // The watchdog timer must be accessible for environments to cancel. + if (Ext.os.is.iOS) { + me.watch.$skipTimerCheck = true; + me.watchdogTimer = Ext.interval(me.watch, 500, me); + } + }, + /** + * + * @param {Function} fn + * @param {Object} [scope] + * @param {Object} [args] + */ + start: function(fn, scope, args) { + var me = this; + me.queue.push(arguments); + if (!me.isRunning) { + if (me.hasOwnProperty('idleTimer')) { + Ext.undefer(me.idleTimer); + delete me.idleTimer; + } + if (me.hasOwnProperty('idleQueueTimer')) { + Ext.undefer(me.idleQueueTimer); + delete me.idleQueueTimer; + } + me.isIdle = false; + me.isRunning = true; + me.startCountTime = Ext.now(); + me.count = 0; + me.doStart(); + } + }, + clear: function() { + var me = this; + Ext.undefer(me.idleTimer); + Ext.undefer(me.idleQueueTimer); + Ext.unraf(me.animationFrameId); + me.idleTimer = me.idleQueueTimer = me.animationFrameId = null; + me.queue.length = me.taskQueue.length = me.runningQueue.length = me.idleQueue.length = 0; + me.isRunning = false; + me.isIdle = true; + me.startCountTime = Ext.now(); + me.count = 0; + }, + watch: function() { + if (this.isRunning && Ext.now() - this.lastRunTime >= 500) { + this.run(); + } + }, + run: function() { + var me = this, + item, element; + // When asked to start or iterate, it will now create a new one + me.animationFrameId = null; + if (!me.isRunning) { + return; + } + var queue = me.runningQueue, + now = Ext.now(), + i, ln; + me.lastRunTime = now; + me.frameStartTime = now; + // We are doing cleanup here for any destroyed elements + // this is temporary until we fix CssTransition to properly + // inform an element that it is being animated + // then the element, during destruction, will need to cleanup + // the animation (see Ext.fx.runner.CssTransition#run) + i = me.queue.length; + while (i--) { + item = me.queue[i]; + element = item[1] && item[1].getElement && item[1].getElement(); + if (element && element.destroyed) { + me.queue.splice(i, 1); + } + } + queue.push.apply(queue, me.queue); + // take a snapshot of the current queue and run it + for (i = 0 , ln = queue.length; i < ln; i++) { + me.invoke(queue[i]); + } + queue.length = 0; + var elapse = me.frameStartTime - me.startCountTime, + count = ++me.count; + if (elapse >= 200) { + me.onFpsChanged(count * 1000 / elapse, count, elapse); + me.startCountTime = me.frameStartTime; + me.count = 0; + } + if (!me.queue.length) { + me.stop(); + } + // Could have been stopped while invoking handlers + if (me.isRunning) { + me.doIterate(); + } + }, + onFpsChanged: Ext.emptyFn, + onStop: Ext.emptyFn, + doStart: function() { + if (!this.animationFrameId) { + this.animationFrameId = Ext.raf(this.run); + } + this.lastRunTime = Ext.now(); + }, + doIterate: function() { + if (!this.animationFrameId) { + this.animationFrameId = Ext.raf(this.run); + } + }, + doStop: function() { + if (this.animationFrameId) { + Ext.unraf(this.animationFrameId); + } + this.animationFrameId = null; + }, + /** + * + * @param {Function} fn + * @param {Object} [scope] + * @param {Object} [args] + */ + stop: function(fn, scope, args) { + var me = this; + if (!me.isRunning) { + return; + } + var queue = me.queue, + ln = queue.length, + i, item; + for (i = 0; i < ln; i++) { + item = queue[i]; + if (item[0] === fn && item[1] === scope && item[2] === args) { + queue.splice(i, 1); + i--; + ln--; + } + } + if (ln === 0) { + me.doStop(); + me.onStop(); + me.isRunning = false; + if (me.idleQueue.length && !me.idleTimer) { + me.idleTimer = Ext.defer(me.whenIdle, 100, me); + } + } + }, + onIdle: function(fn, scope, args) { + var me = this, + listeners = me.idleQueue, + i, ln, listener; + for (i = 0 , ln = listeners.length; i < ln; i++) { + listener = listeners[i]; + if (fn === listener[0] && scope === listener[1] && args === listener[2]) { + return; + } + } + listeners.push(arguments); + if (me.isIdle) { + me.processIdleQueue(); + } else if (!me.idleTimer) { + me.idleTimer = Ext.defer(me.whenIdle, 100, me); + } + }, + unIdle: function(fn, scope, args) { + var me = this, + listeners = me.idleQueue, + i, ln, listener; + for (i = 0 , ln = listeners.length; i < ln; i++) { + listener = listeners[i]; + if (fn === listener[0] && scope === listener[1] && args === listener[2]) { + listeners.splice(i, 1); + return true; + } + } + if (!listeners.length && me.idleTimer) { + Ext.undefer(me.idleTimer); + delete me.idleTimer; + } + if (!listeners.length && me.idleQueueTimer) { + Ext.undefer(me.idleQueueTimer); + delete me.idleQueueTimer; + } + return false; + }, + queueTask: function(fn, scope, args) { + this.taskQueue.push(arguments); + this.processTaskQueue(); + }, + dequeueTask: function(fn, scope, args) { + var listeners = this.taskQueue, + i, ln, listener; + for (i = 0 , ln = listeners.length; i < ln; i++) { + listener = listeners[i]; + if (fn === listener[0] && scope === listener[1] && args === listener[2]) { + listeners.splice(i, 1); + i--; + ln--; + } + } + }, + invoke: function(listener) { + var fn = listener[0], + scope = listener[1], + args = listener[2]; + fn = (typeof fn == 'string' ? scope[fn] : fn); + if (Ext.isArray(args)) { + fn.apply(scope, args); + } else { + fn.call(scope, args); + } + }, + whenIdle: function() { + delete this.idleTimer; + this.isIdle = true; + this.processIdleQueue(); + }, + processIdleQueue: function() { + if (!this.hasOwnProperty('idleQueueTimer')) { + this.idleQueueTimer = Ext.defer(this.processIdleQueueItem, 1, this); + } + }, + processIdleQueueItem: function() { + delete this.idleQueueTimer; + if (!this.isIdle) { + return; + } + var listeners = this.idleQueue, + listener; + if (listeners.length > 0) { + listener = listeners.shift(); + this.invoke(listener); + this.processIdleQueue(); + } + }, + processTaskQueue: function() { + if (!this.hasOwnProperty('taskQueueTimer')) { + this.taskQueueTimer = Ext.defer(this.processTaskQueueItem, 15, this); + } + }, + processTaskQueueItem: function() { + delete this.taskQueueTimer; + var listeners = this.taskQueue, + listener; + if (listeners.length > 0) { + listener = listeners.shift(); + this.invoke(listener); + this.processTaskQueue(); + } + }, + /** + * + * @param {Number} fps Frames per second. + * @param {Number} count Actual number of frames rendered during interval. + * @param {Number} interval Interval duration. + */ + showFps: function() { + var styleTpl = { + color: 'white', + 'background-color': 'black', + 'text-align': 'center', + 'font-family': 'sans-serif', + 'font-size': '8px', + 'font-weight': 'normal', + 'font-style': 'normal', + 'line-height': '20px', + '-webkit-font-smoothing': 'antialiased', + 'zIndex': 100000, + position: 'absolute' + }; + Ext.getBody().append([ + // --- Average --- + { + style: Ext.applyIf({ + bottom: '50px', + left: 0, + width: '50px', + height: '20px' + }, styleTpl), + html: 'Average' + }, + { + style: Ext.applyIf({ + 'background-color': 'red', + 'font-size': '18px', + 'line-height': '50px', + bottom: 0, + left: 0, + width: '50px', + height: '50px' + }, styleTpl), + id: '__averageFps', + html: '0' + }, + // --- Min --- + { + style: Ext.applyIf({ + bottom: '50px', + left: '50px', + width: '50px', + height: '20px' + }, styleTpl), + html: 'Min (Last 1k)' + }, + { + style: Ext.applyIf({ + 'background-color': 'orange', + 'font-size': '18px', + 'line-height': '50px', + bottom: 0, + left: '50px', + width: '50px', + height: '50px' + }, styleTpl), + id: '__minFps', + html: '0' + }, + // --- Max --- + { + style: Ext.applyIf({ + bottom: '50px', + left: '100px', + width: '50px', + height: '20px' + }, styleTpl), + html: 'Max (Last 1k)' + }, + { + style: Ext.applyIf({ + 'background-color': 'maroon', + 'font-size': '18px', + 'line-height': '50px', + bottom: 0, + left: '100px', + width: '50px', + height: '50px' + }, styleTpl), + id: '__maxFps', + html: '0' + }, + // --- Current --- + { + style: Ext.applyIf({ + bottom: '50px', + left: '150px', + width: '50px', + height: '20px' + }, styleTpl), + html: 'Current' + }, + { + style: Ext.applyIf({ + 'background-color': 'green', + 'font-size': '18px', + 'line-height': '50px', + bottom: 0, + left: '150px', + width: '50px', + height: '50px' + }, styleTpl), + id: '__currentFps', + html: '0' + } + ]); + Ext.AnimationQueue.resetFps(); + }, + resetFps: function() { + var currentFps = Ext.get('__currentFps'), + averageFps = Ext.get('__averageFps'), + minFps = Ext.get('__minFps'), + maxFps = Ext.get('__maxFps'), + min = 1000, + max = 0, + count = 0, + sum = 0; + if (!currentFps) { + return; + } + Ext.AnimationQueue.onFpsChanged = function(fps) { + count++; + if (!(count % 10)) { + min = 1000; + max = 0; + } + sum += fps; + min = Math.min(min, fps); + max = Math.max(max, fps); + currentFps.setHtml(Math.round(fps)); + // All-time average since last reset. + averageFps.setHtml(Math.round(sum / count)); + minFps.setHtml(Math.round(min)); + maxFps.setHtml(Math.round(max)); + }; + } +}, function() { + /* + Global FPS indicator. Add ?showfps to use in any application. Note that this REQUIRES true requestAnimationFrame + to be accurate. + */ + var paramsString = window.location.search.substr(1), + paramsArray = paramsString.split("&"); + if (Ext.Array.contains(paramsArray, "showfps")) { + Ext.onReady(this.showFps.bind(this)); + } +}); + +/** + * This class makes buffered methods simple and also handles cleanup on `destroy`. + * + * Ext.define('Foo', { + * mixins: [ + * 'Ext.mixin.Bufferable' + * ], + * + * bufferableMethods: { + * // Provides a "foobar" method that calls "doFoobar" with the + * // most recent arguments but delayed by 50ms from the last + * // call. Calls to "foobar" made during the 50ms wait restart + * // the timer and replace the arguments. + * + * foobar: 50 + * }, + * + * method: function () { + * this.foobar(42); // call doFoobar in 50ms + * + * if (this.isFoobarPending) { + * // test if "foobar" is pending + * } + * + * this.flushFoobar(); // actually, call it now + * + * this.cancelFoobar(); // or never mind + * }, + * + * doFoobar: function () { + * // time to do the "foobar" thing + * } + * }); + * + * @since 6.5.0 + * @private + */ +Ext.define('Ext.mixin.Bufferable', function(Bufferable) { + return { + extend: 'Ext.Mixin', + mixinConfig: { + id: 'bufferable', + before: { + destroy: 'cancelAllCalls' + }, + extended: function(baseClass, derivedClass, classBody) { + var bufferableMethods = classBody.bufferableMethods; + if (bufferableMethods) { + delete classBody.bufferableMethods; + Bufferable.processClass(derivedClass, bufferableMethods); + } + } + }, + afterClassMixedIn: function(targetClass) { + Bufferable.processClass(targetClass); + }, + privates: { + /** + * Cancel all pending `bufferableMethod` calls on this object. + * @since 6.5.0 + * @private + */ + cancelAllCalls: function() { + var bufferables = this.bufferables, + name; + if (bufferables) { + for (name in bufferables) { + bufferables[name].cancel(); + delete bufferables[name]; + } + } + }, + /** + * Cancel a specific pending `bufferableMethod` call on this object. + * @param {String} name The name of the buffered method to cancel. + * @param {Boolean} invoke (private) + * @return {Boolean} Returns `true` if a cancellation occurred. + * @since 6.5.0 + * @private + */ + cancelBufferedCall: function(name, invoke) { + var bufferables = this.bufferables, + timer = bufferables && bufferables[name]; + if (timer) { + timer[invoke ? 'invoke' : 'cancel'](); + } + return !!timer; + }, + /** + * Flushes a specific pending `bufferableMethod` call on this object if one is + * pending. + * @param {String} name The name of the buffered method to cancel. + * @return {Boolean} Returns `true` if a flush occurred. + * @since 6.5.0 + * @private + */ + flushBufferedCall: function(name) { + return this.cancelBufferedCall(name, true); + }, + /** + * This method initializes an instance when the first bufferable method is called. + * It merges an instance-level `bufferableMethods` config if present. This allows + * an instance to change the buffer timeouts, even to 0 to disable buffering. + * + * Ext.create({ + * ... + * bufferableMethods: { + * foobar: 0 + * } + * }); + * + * Note, this method cannot effect unbuffered methods. The `bufferableMethods` + * config only instruments buffered methods when used on a class declaration. + * + * @return {Object} + * @since 6.5.0 + * @private + */ + initBufferables: function() { + var me = this, + methods = me.hasOwnProperty('bufferableMethods') && me.bufferableMethods, + classMethods; + if (methods) { + Bufferable._canonicalize(methods); + classMethods = me.self.prototype.bufferableMethods; + me.bufferableMethods = Ext.merge(Ext.clone(classMethods), methods); + } + return (me.bufferables = {}); + }, + /** + * Returns `true` if a specific `bufferableMethod` is pending. + * @param {String} name The name of the buffered method to cancel. + * @return {Boolean} + * @since 6.5.0 + * @private + */ + isCallPending: function(name) { + var bufferables = this.bufferables, + timer = bufferables && bufferables[name]; + return !!timer; + }, + statics: { + SINGLE: { + single: true + }, + _canonicalize: function(methods) { + var t, def, s, name; + for (name in methods) { + s = Ext.String.capitalize(name); + def = methods[name]; + t = typeof def; + if (t === 'number' || t === 'string') { + // method: 50 + // method: 'asap' + // method: 'idle' + // method: 'raf' + methods[name] = def = { + delay: def + }; + } + if (typeof (t = def.delay) === 'string') { + // method: { + // delay: 'asap' + // } + def[t] = true; + delete def.delay; + } + def.capitalized = s; + def.name = name; + if (!def.fn) { + def.fn = 'do' + s; + } + if (!def.flag) { + def.flag = 'is' + s + 'Pending'; + } + } + }, + _canceller: function() { + var timer = this, + // this fn is "cancel()" on timer instances + id = timer.id; + if (id) { + if (timer.delay) { + Ext.undefer(id); + } else if (timer.asap) { + Ext.unasap(id); + } else if (timer.idle) { + Ext.un('idle', id, null, Bufferable.SINGLE); + } else if (timer.raf) { + Ext.unraf(id); + } + timer.id = null; + } + timer.args = null; + timer.target[timer.flag] = false; + }, + _invoker: function() { + var timer = this, + // this fn is "invoke()" on timer instances + args = timer.args || Ext.emptyArray, + target = timer.target; + ++timer.invokes; + timer.cancel(); + target[timer.fn].apply(target, args); + }, + delayCall: function(target, def, args) { + var bufferables = target.bufferables || target.initBufferables(), + name = def.name, + timer = bufferables[name] || (bufferables[name] = Ext.apply({ + calls: 0, + invokes: 0, + args: null, + cancel: Bufferable._canceller, + id: null, + target: target, + invoke: Bufferable._invoker + }, def)), + delay = def.delay, + exec = function() { + if (timer.id) { + timer.id = null; + timer.invoke(); + } + }; + if (timer.id) { + timer.cancel(); + } + timer.args = args; + ++timer.calls; + target[timer.flag] = true; + if (delay) { + timer.id = Ext.defer(exec, delay); + } else if (def.asap) { + timer.id = Ext.asap(exec); + } else if (def.idle) { + timer.id = exec; + Ext.on('idle', exec, null, Bufferable.SINGLE); + } else if (def.raf) { + timer.id = Ext.raf(exec); + } else { + // allow bufferableMethods: { foo: 0 } to force immediate call + timer.invoke(); + } + }, + processClass: function(cls, bufferableMethods) { + var proto = cls.prototype, + inherited = proto.bufferableMethods, + def, name; + if (bufferableMethods) { + // if (derived class) + Bufferable._canonicalize(bufferableMethods); + if (inherited) { + // If we have a derived class, it could be just adjusting the + // configuration, not introducing new properties, so clone the + // inherited config and merge on the one from the classBody. + inherited = Ext.merge(Ext.clone(inherited), bufferableMethods); + } + proto.bufferableMethods = inherited || bufferableMethods; + } else { + // else we are being mixed in, so the bufferableMethods on the + // prototype almost certainly belong to the immediate user class + // that is mixing us in... (leave the config on the prototype) + bufferableMethods = inherited; + Bufferable._canonicalize(bufferableMethods); + // prevent shape change + proto.bufferables = null; + } + if (bufferableMethods) { + for (name in bufferableMethods) { + if (!proto[name]) { + def = bufferableMethods[name]; + Bufferable.processMethod(proto, def, Array.prototype.slice); + } + } + } + }, + processMethod: function(proto, def, slice) { + var name = def.name, + cap = def.capitalized; + proto[name] = function() { + return Bufferable.delayCall(this, def, slice.call(arguments)); + }; + proto['cancel' + cap] = function() { + return this.cancelBufferedCall(name); + }; + proto['flush' + cap] = function() { + return this.flushBufferedCall(name); + }; + } + } + } + }; +}); +// statics +// privates + +/** + * Provides a registry of all Components (instances of {@link Ext.Component} or any subclass + * thereof) on a page so that they can be easily accessed by {@link Ext.Component component} + * {@link Ext.Component#id id} (see {@link #get}, or the convenience method + * {@link Ext#getCmp Ext.getCmp}). + * + * This object also provides a registry of available Component *classes* indexed by a + * mnemonic code known as the Component's {@link Ext.Component#xtype xtype}. The `xtype` + * provides a way to avoid instantiating child Components when creating a full, nested + * config object for a complete Ext page. + * + * A child Component may be specified simply as a *config object* as long as the correct + * `{@link Ext.Component#xtype xtype}` is specified so that if and when the Component + * needs rendering, the correct type can be looked up for lazy instantiation. + * + * @singleton + */ +Ext.define('Ext.ComponentManager', { + alternateClassName: 'Ext.ComponentMgr', + singleton: true, + mixins: [ + 'Ext.mixin.Bufferable' + ], + count: 0, + referencesDirty: true, + referenceRepairs: 0, + typeName: 'xtype', + bufferableMethods: { + handleDocumentMouseDown: 'asap' + }, + /** + * @private + */ + constructor: function(config) { + var me = this; + Ext.apply(me, config); + me.all = {}; + me.byInstanceId = {}; + me.holders = {}; + me.names = {}; + me.references = {}; + me.onAvailableCallbacks = {}; + }, + /** + * Creates a new Component from the specified config object using the config object's + * `xtype` to determine the class to instantiate. + * + * @param {Object} config A configuration object for the Component you wish to create. + * @param {String} [defaultType] The `xtype` to use if the config object does not + * contain a `xtype`. (Optional if the config contains a `xtype`). + * @return {Ext.Component} The newly instantiated Component. + */ + create: function(config, defaultType) { + if (typeof config === 'string') { + return Ext.widget(config); + } + if (config.isComponent) { + return config; + } + if ('xclass' in config) { + return Ext.create(config.xclass, config); + } + return Ext.widget(config.xtype || defaultType, config); + }, + /** + * Returns an item by id. + * @param {String} id The id of the item + * @return {Object} The item, undefined if not found. + */ + get: function(id) { + return this.all[id]; + }, + register: function(component) { + var me = this, + id = component.getId(), + onAvailableCallbacks = me.onAvailableCallbacks; + if (id === undefined) { + Ext.raise('Component id is undefined. Please ensure the component has an id.'); + } + if (id in me.all) { + Ext.raise('Duplicate component id "' + id + '"'); + } + if (component.$iid in me.byInstanceId) { + Ext.raise('Duplicate component instance id "' + component.$iid + '"'); + } + me.all[id] = component; + me.byInstanceId[component.$iid] = component; + if (component.reference) { + me.references[id] = component; + } + if (component.name && component.nameable) { + me.names[id] = component; + } + if (component.nameHolder || component.referenceHolder) { + me.holders[id] = component; + } + ++me.count; + if (!me.hasFocusListener) { + me.installFocusListener(); + } + onAvailableCallbacks = onAvailableCallbacks && onAvailableCallbacks[id]; + if (onAvailableCallbacks && onAvailableCallbacks.length) { + me.notifyAvailable(component); + } + }, + unregister: function(component) { + var me = this, + all = me.all, + byInstanceId = me.byInstanceId, + holders = me.holders, + references = me.references, + names = me.names, + id = component.getId(); + if (id in holders) { + // Helps IE since delete may just mark the entry as "free" and not + // release the object by clearing the entry value. + // TODO find out when IE fixed this + holders[id] = null; + delete holders[id]; + } + if (id in names) { + names[id] = null; + delete names[id]; + } + if (id in references) { + references[id] = null; + delete references[id]; + } + all[id] = null; + delete all[id]; + id = component.$iid; + byInstanceId[id] = null; + delete byInstanceId[id]; + --me.count; + }, + markReferencesDirty: function() { + var me = this, + holders = me.holders, + key; + if (!me.referencesDirty) { + // Clear all collections (no stale entries) + for (key in holders) { + holders[key].refs = holders[key].nameRefs = null; + } + me.referencesDirty = true; + } + }, + fixReferences: function() { + var me = this, + references = me.references, + names = me.names, + key; + if (me.referencesDirty) { + ++me.referenceRepairs; + for (key in references) { + references[key]._fixReference(); + } + for (key in names) { + names[key]._fixName(); + } + me.referencesDirty = false; + } + }, + /** + * Registers a function that will be called (a single time) when an item with the specified id is added to the manager. + * This will happen on instantiation. + * @param {String} id The item id + * @param {Function} fn The callback function. Called with a single parameter, the item. + * @param {Object} scope The scope ('this' reference) in which the callback is executed. + * Defaults to the item. + */ + onAvailable: function(id, fn, scope) { + var me = this, + callbacks = me.onAvailableCallbacks, + all = me.all, + item; + if (id in all) { + //if already an instance, callback immediately + item = all[id]; + fn.call(scope || item, item); + } else if (id) { + // otherwise, queue for dispatch + if (!Ext.isArray(callbacks[id])) { + callbacks[id] = []; + } + callbacks[id].push(function(item) { + fn.call(scope || item, item); + }); + } + }, + /** + * @private + */ + notifyAvailable: function(item) { + var callbacks = this.onAvailableCallbacks[item && item.getId()] || []; + while (callbacks.length) { + (callbacks.shift())(item); + } + }, + /** + * Executes the specified function once for each item in the collection. + * @param {Function} fn The function to execute. + * @param {String} fn.key The key of the item + * @param {Number} fn.value The value of the item + * @param {Number} fn.length The total number of items in the collection ** Removed + * in 5.0 ** + * @param {Boolean} fn.return False to cease iteration. + * @param {Object} scope The scope to execute in. Defaults to `this`. + */ + each: function(fn, scope) { + Ext.Object.each(this.all, fn, scope); + }, + /** + * Gets the number of items in the collection. + * @return {Number} The number of items in the collection. + */ + getCount: function() { + return this.count; + }, + /** + * Returns an array of all components + * @return {Array} + */ + getAll: function() { + return Ext.Object.getValues(this.all); + }, + /** + * Return the currently active (focused) Component + * + * @return {Ext.Component/null} Active Component, or null + * @private + */ + getActiveComponent: function() { + return Ext.Component.from(Ext.dom.Element.getActiveElement()); + }, + // Deliver focus events to Component + onGlobalFocus: function(e) { + var me = this, + event = e.event, + toComponent = event.toComponent = e.toComponent = Ext.Component.from(e.toElement), + fromComponent = event.fromComponent = e.fromComponent = Ext.Component.from(e.fromElement), + commonAncestor = me.getCommonAncestor(fromComponent, toComponent), + targetComponent; + // Focus moves *within* a component should not cause component focus leave/enter + if (toComponent !== fromComponent) { + if (fromComponent && !fromComponent.destroyed && !fromComponent.isDestructing()) { + if (fromComponent.handleBlurEvent) { + fromComponent.handleBlurEvent(e); + } + // Call onFocusLeave on the component axis from which focus is exiting + for (targetComponent = fromComponent; targetComponent && targetComponent !== commonAncestor; targetComponent = targetComponent.getRefOwner()) { + if (!(targetComponent.destroyed || targetComponent.destroying)) { + e.type = 'focusleave'; + targetComponent.onFocusLeave(event); + } + } + } + if (toComponent && !toComponent.destroyed && !toComponent.isDestructing()) { + if (toComponent.handleFocusEvent) { + toComponent.handleFocusEvent(e); + } + // Call onFocusEnter on the component axis to which focus is entering + for (targetComponent = toComponent; targetComponent && targetComponent !== commonAncestor; targetComponent = targetComponent.getRefOwner()) { + e.type = 'focusenter'; + targetComponent.onFocusEnter(event); + } + } + } + for (targetComponent = commonAncestor; targetComponent; targetComponent = targetComponent.getRefOwner()) { + if (!(targetComponent.destroying || targetComponent.destroyed)) { + targetComponent.onFocusMove(e); + } + } + }, + getCommonAncestor: function(compA, compB) { + if (compA === compB) { + return compA; + } + while (compA && !(compA.isAncestor(compB) || compA === compB)) { + compA = compA.getRefOwner(); + } + return compA; + }, + privates: { + /** + * This method reorders the DOM structure of floated components to arrange that the + * clicked element is last of its siblings, and therefore on the visual "top" of + * the floated component stack. + * + * This is a Bufferable ASAP method invoked directly from Ext.GlobalEvents. + * + * We need to use ASAP, not a low priority listener because we need it + * to run *after* the browser's default response to the event has been + * processed, ie focus consequences. + * For example, a Dialog contains a picker field, and the picker field has + * its floated picker open and focused. + * The user mousedowns on another field in the dialog. The resulting + * immediate DOM shuffle to bring the dialog above the picker results + * in focus being silently lost. + * @param {type} e The mousedown event + * @private + */ + doHandleDocumentMouseDown: function(e) { + var floatedSelector = Ext.Widget.prototype.floatedSelector, + targetFloated; + // If mousedown/pointerdown/touchstart is on a floated Component, ask it to sync + // its place in the hierarchy. + if (floatedSelector) { + targetFloated = Ext.Component.from(e.getTarget(floatedSelector, Ext.getBody())); + // If the mousedown is in a floated, move it to top. + if (targetFloated) { + targetFloated.toFront(true); + } + } + }, + installFocusListener: function() { + var me = this; + Ext.on('focus', me.onGlobalFocus, me); + me.hasFocusListener = true; + }, + clearAll: function() { + this.all = {}; + this.names = {}; + this.references = {}; + this.onAvailableCallbacks = {}; + }, + /** + * Find the Widget or Component to which the given Element belongs. + * + * @param {Ext.dom.Element/HTMLElement} el The element from which to start to find + * an owning Component. + * @param {Ext.dom.Element/HTMLElement} [limit] The element at which to stop upward + * searching for an owning Component, or the number of Components to traverse before + * giving up. Defaults to the document's HTML element. + * @param {String} [selector] An optional {@link Ext.ComponentQuery} selector to + * filter the target. + * @return {Ext.Widget/Ext.Component} The widget, component or `null`. + * + * @private + * @since 6.5.0 + */ + from: function(el, limit, selector) { + if (el && el.isEvent) { + el = el.target; + } + var target = Ext.getDom(el), + cache = this.all, + depth = 0, + topmost, cmpId, cmp; + if (typeof limit !== 'number') { + topmost = Ext.getDom(limit); + limit = Number.MAX_VALUE; + } + while (target && target.nodeType === 1 && depth < limit && target !== topmost) { + cmpId = target.getAttribute('data-componentid') || target.id; + if (cmpId) { + cmp = cache[cmpId]; + if (cmp && (!selector || Ext.ComponentQuery.is(cmp, selector))) { + return cmp; + } + // Increment depth on every *Component* found, not Element + depth++; + } + target = target.parentNode; + } + return null; + } + } +}, function() { + var ComponentManager = Ext.ComponentManager; + // Backwards compat + ComponentManager.fromElement = ComponentManager.from; + /** + * This is shorthand reference to {@link Ext.ComponentManager#get}. + * Looks up an existing {@link Ext.Component Component} by {@link Ext.Component#id id} + * + * @method getCmp + * @param {String} id The component {@link Ext.Component#id id} + * @return {Ext.Component} The Component, `undefined` if not found, or `null` if a + * Class was found. + * @member Ext + */ + Ext.getCmp = function(id) { + return ComponentManager.get(id); + }; + Ext.iidToCmp = function(iid) { + return ComponentManager.byInstanceId[iid] || null; + }; + Ext.doEv = function(node, e) { + var cmp, method, event; + // The event here is a raw browser event, so don't pass the event directly + // since from expects an Ext.event.Event + cmp = Ext.Component.from(e.target); + if (cmp && !cmp.destroying && !cmp.destroyed && cmp.getEventHandlers) { + method = cmp.getEventHandlers()[e.type]; + if (method && cmp[method]) { + event = new Ext.event.Event(e); + return cmp[method](event); + } + } + return true; + }; +}); + +/** + * This class defines the operators that are shared by DomQuery and ComponentQuery + * @class Ext.util.Operators + * @private + */ +Ext.ns('Ext.util').Operators = { + // @define Ext.util.Operators + "=": function(a, v) { + return a == v; + }, + "!=": function(a, v) { + return a != v; + }, + "^=": function(a, v) { + return a && a.substr(0, v.length) == v; + }, + "$=": function(a, v) { + return a && a.substr(a.length - v.length) == v; + }, + "*=": function(a, v) { + return a && a.indexOf(v) !== -1; + }, + "%=": function(a, v) { + return (a % v) === 0; + }, + "|=": function(a, v) { + return a && (a == v || a.substr(0, v.length + 1) == v + '-'); + }, + "~=": function(a, v) { + return a && (' ' + a + ' ').indexOf(' ' + v + ' ') != -1; + } +}; + +/** + * @private + * @class Ext.util.LruCache + * @extend Ext.util.HashMap + * A linked {@link Ext.util.HashMap HashMap} implementation which maintains most recently accessed + * items at the end of the list, and purges the cache down to the most recently accessed {@link #maxSize} items + * upon add. + */ +Ext.define('Ext.util.LruCache', { + extend: 'Ext.util.HashMap', + config: { + /** + * @cfg {Number} maxSize + * The maximum size the cache is allowed to grow to before further additions + * cause removal of the least recently used entry. + */ + maxSize: null + }, + /** + * @method add + * @inheritdoc + */ + add: function(key, newValue) { + var me = this, + entry, last; + me.removeAtKey(key); + last = me.last; + entry = { + prev: last, + next: null, + key: key, + value: newValue + }; + if (last) { + // If the list is not empty, update the last entry + last.next = entry; + } else { + // List is empty + me.first = entry; + } + me.last = entry; + me.callParent([ + key, + entry + ]); + me.prune(); + return newValue; + }, + /** + * @private + */ + insertBefore: function(key, newValue, sibling) { + var me = this, + existingKey, entry; + // NOT an assignment. + // If there is a following sibling + if (sibling = this.map[this.findKey(sibling)]) { + existingKey = me.findKey(newValue); + // "new" value is in the list. + if (existingKey) { + me.unlinkEntry(entry = me.map[existingKey]); + } else // Genuinely new: create an entry for it. + { + entry = { + prev: sibling.prev, + next: sibling, + key: key, + value: newValue + }; + } + if (sibling.prev) { + entry.prev.next = entry; + } else { + me.first = entry; + } + entry.next = sibling; + sibling.prev = entry; + me.prune(); + return newValue; + } else // No following sibling, it's just an add. + { + return me.add(key, newValue); + } + }, + /** + * @method get + * @inheritdoc + */ + get: function(key) { + var entry = this.map[key]; + if (entry) { + // If it's not the end, move to end of list on get + if (entry.next) { + this.moveToEnd(entry); + } + return entry.value; + } + }, + /** + * @private + */ + removeAtKey: function(key) { + this.unlinkEntry(this.map[key]); + return this.callParent(arguments); + }, + /** + * @method clear + * @inheritdoc + * @param initial (private) + */ + clear: function(initial) { + this.first = this.last = null; + return this.callParent([ + initial + ]); + }, + /** + * @private + */ + unlinkEntry: function(entry) { + // Stitch the list back up. + if (entry) { + if (entry.next) { + entry.next.prev = entry.prev; + } else { + this.last = entry.prev; + } + if (entry.prev) { + entry.prev.next = entry.next; + } else { + this.first = entry.next; + } + entry.prev = entry.next = null; + } + }, + /** + * @private + */ + moveToEnd: function(entry) { + this.unlinkEntry(entry); + // NOT an assignment. + // If the list is not empty, update the last entry + if (entry.prev = this.last) { + this.last.next = entry; + } else // List is empty + { + this.first = entry; + } + this.last = entry; + }, + /** + * @private + */ + getArray: function(isKey) { + var arr = [], + entry = this.first; + while (entry) { + arr.push(isKey ? entry.key : entry.value); + entry = entry.next; + } + return arr; + }, + /** + * Executes the specified function once for each item in the cache. + * Returning false from the function will cease iteration. + * + * By default, iteration is from least recently used to most recent. + * + * The paramaters passed to the function are: + *
    + *
  • key : String

    The key of the item

  • + *
  • value : Number

    The value of the item

  • + *
  • length : Number

    The total number of items in the hash

  • + *
+ * @param {Function} fn The function to execute. + * @param {Object} scope The scope (this reference) to execute in. Defaults to this LruCache. + * @param {Boolean} [reverse=false] Pass true to iterate the list in reverse (most recent first) order. + * @return {Ext.util.LruCache} this + */ + each: function(fn, scope, reverse) { + var me = this, + entry = reverse ? me.last : me.first, + length = me.length; + scope = scope || me; + while (entry) { + if (fn.call(scope, entry.key, entry.value, length) === false) { + break; + } + entry = reverse ? entry.prev : entry.next; + } + return me; + }, + /** + * @private + */ + findKey: function(value) { + var key, + map = this.map; + for (key in map) { + // Attention. Differs from subclass in that this compares the value property + // of the entry. + if (map.hasOwnProperty(key) && map[key].value === value) { + return key; + } + } + return undefined; + }, + /** + * Performs a shallow copy on this haLruCachesh. + * @return {Ext.util.HashMap} The new hash object. + */ + clone: function() { + var newCache = new this.self(this.initialConfig), + map = this.map, + key; + newCache.suspendEvents(); + for (key in map) { + if (map.hasOwnProperty(key)) { + newCache.add(key, map[key].value); + } + } + newCache.resumeEvents(); + return newCache; + }, + /** + * Purge the least recently used entries if the maxSize has been exceeded. + */ + prune: function() { + var me = this, + max = me.getMaxSize(), + purgeCount = max ? (me.length - max) : 0; + if (purgeCount > 0) { + for (; me.first && purgeCount; purgeCount--) { + me.removeAtKey(me.first.key); + } + } + } +}); +/** + * @method containsKey + * @private + */ +/** + * @method contains + * @private + */ +/** + * @method getKeys + * @private + */ +/** + * @method getValues + * @private + */ + +/** + * Provides searching of Components within Ext.ComponentManager (globally) or a specific + * Ext.container.Container on the document with a similar syntax to a CSS selector. + * Returns Array of matching Components, or empty Array. + * + * ## Basic Component lookup + * + * Components can be retrieved by using their {@link Ext.Component xtype}: + * + * - `component` + * - `gridpanel` + * + * Matching by `xtype` matches inherited types, so in the following code, the previous field + * *of any type which inherits from `TextField`* will be found: + * + * prevField = myField.previousNode('textfield'); + * + * To match only the exact type, pass the "shallow" flag by adding `(true)` to xtype + * (See Component's {@link Ext.Component#isXType isXType} method): + * + * prevTextField = myField.previousNode('textfield(true)'); + * + * You can search Components by their `id` or `itemId` property, prefixed with a #: + * + * #myContainer + * + * Component `xtype` and `id` or `itemId` can be used together to avoid possible + * id collisions between Components of different types: + * + * panel#myPanel + * + * When Component's `id` or `xtype` contains dots, you can escape them in your selector: + * + * my\.panel#myPanel + * + * Keep in mind that JavaScript treats the backslash character in a special way, so you + * need to escape it, too, in the actual code: + * + * var myPanel = Ext.ComponentQuery.query('my\\.panel#myPanel'); + * + * ## Traversing Component tree + * + * Components can be found by their relation to other Components. There are several + * relationship operators, mostly taken from CSS selectors: + * + * - **`E F`** All descendant Components of E that match F + * - **`E > F`** All direct children Components of E that match F + * - **`E ^ F`** All parent Components of E that match F + * + * Expressions between relationship operators are matched left to right, i.e. leftmost + * selector is applied first, then if one or more matches are found, relationship operator + * itself is applied, then next selector expression, etc. It is possible to combine + * relationship operators in complex selectors: + * + * window[title="Input form"] textfield[name=login] ^ form > button[action=submit] + * + * That selector can be read this way: Find a window with title "Input form", in that + * window find a TextField with name "login" at any depth (including subpanels and/or + * FieldSets), then find an `Ext.form.Panel` that is a parent of the TextField, and in + * that form find a direct child that is a button with custom property `action` set to + * value "submit". + * + * Whitespace on both sides of `^` and `>` operators is non-significant, i.e. can be + * omitted, but usually is used for clarity. + * + * ## Searching by Component attributes + * + * Components can be searched by their object property values (attributes). To do that, + * use attribute matching expression in square brackets: + * + * - `component[disabled]` - matches any Component that has `disabled` property with + * any truthy (non-empty, not `false`) value. + * - `panel[title="Test"]` - matches any Component that has `title` property set to + * "Test". Note that if the value does not contain spaces, the quotes are optional. + * + * Attributes can use any of the following operators to compare values: + * `=`, `!=`, `^=`, `$=`, `*=`, `%=`, `|=` and `~=`. + * + * Prefixing the attribute name with an at sign `@` means that the property must be + * the object's `ownProperty`, not a property from the prototype chain. + * + * Specifications like `[propName]` check that the property is a truthy value. To check + * that the object has an `ownProperty` of a certain name, regardless of the value use + * the form `[?propName]`. + * + * The specified value is coerced to match the type of the property found in the + * candidate Component using {@link Ext#coerce}. + * + * If you need to find Components by their `itemId` property, use the `#id` form; it will + * do the same as `[itemId=id]` but is easier to read. + * + * If you need to include a metacharacter like (, ), [, ], etc., in the query, escape it + * by prefixing it with a backslash: + * + * var component = Ext.ComponentQuery.query('[myProperty=\\[foo\\]]'); + * + * ## Attribute matching operators + * + * The '=' operator will return the results that **exactly** match the + * specified object property (attribute): + * + * Ext.ComponentQuery.query('panel[cls=my-cls]'); + * + * Will match the following Component: + * + * Ext.create('Ext.window.Window', { + * cls: 'my-cls' + * }); + * + * But will not match the following Component, because 'my-cls' is one value + * among others: + * + * Ext.create('Ext.panel.Panel', { + * cls: 'foo-cls my-cls bar-cls' + * }); + * + * You can use the '~=' operator instead, it will return Components with + * the property that **exactly** matches one of the whitespace-separated + * values. This is also true for properties that only have *one* value: + * + * Ext.ComponentQuery.query('panel[cls~=my-cls]'); + * + * Will match both Components: + * + * Ext.create('Ext.panel.Panel', { + * cls: 'foo-cls my-cls bar-cls' + * }); + * + * Ext.create('Ext.window.Window', { + * cls: 'my-cls' + * }); + * + * Generally, '=' operator is more suited for object properties other than + * CSS classes, while '~=' operator will work best with properties that + * hold lists of whitespace-separated CSS classes. + * + * The '^=' operator will return Components with specified attribute that + * start with the passed value: + * + * Ext.ComponentQuery.query('panel[title^=Sales]'); + * + * Will match the following Component: + * + * Ext.create('Ext.panel.Panel', { + * title: 'Sales estimate for Q4' + * }); + * + * The '$=' operator will return Components with specified properties that + * end with the passed value: + * + * Ext.ComponentQuery.query('field[fieldLabel$=name]'); + * + * Will match the following Component: + * + * Ext.create('Ext.form.field.Text', { + * fieldLabel: 'Enter your name' + * }); + * + * The '/=' operator will return Components with specified properties that + * match the passed regular expression: + * + * Ext.ComponentQuery.query('button[action/="edit|save"]'); + * + * Will match the following Components with a custom `action` property: + * + * Ext.create('Ext.button.Button', { + * action: 'edit' + * }); + * + * Ext.create('Ext.button.Button', { + * action: 'save' + * }); + * + * When you need to use meta characters like [], (), etc. in your query, make sure + * to escape them with back slashes: + * + * Ext.ComponentQuery.query('panel[title="^Sales for Q\\[1-4\\]"]'); + * + * The following test will find panels with their `ownProperty` collapsed being equal to + * `false`. It will **not** match a collapsed property from the prototype chain. + * + * Ext.ComponentQuery.query('panel[@collapsed=false]'); + * + * Member expressions from candidate Components may be tested. If the expression returns + * a *truthy* value, the candidate Component will be included in the query: + * + * var disabledFields = myFormPanel.query("{isDisabled()}"); + * + * Such expressions are executed in Component's context, and the above expression is + * similar to running this snippet for every Component in your application: + * + * if (component.isDisabled()) { + * matches.push(component); + * } + * + * It is important to use only methods that are available in **every** Component instance + * to avoid run time exceptions. If you need to match your Components with a custom + * condition formula, you can augment `Ext.Component` to provide custom matcher that + * will return `false` by default, and override it in your custom classes: + * + * Ext.define('My.Component', { + * override: 'Ext.Component', + * myMatcher: function() { return false; } + * }); + * + * Ext.define('My.Panel', { + * extend: 'Ext.panel.Panel', + * requires: ['My.Component'], // Ensure that Component override is applied + * myMatcher: function(selector) { + * return selector === 'myPanel'; + * } + * }); + * + * After that you can use a selector with your custom matcher to find all instances + * of `My.Panel`: + * + * Ext.ComponentQuery.query("{myMatcher('myPanel')}"); + * + * However if you really need to use a custom matcher, you may find it easier to implement + * a custom Pseudo class instead (see below). + * + * ## Conditional matching + * + * Attribute matchers can be combined to select only Components that match **all** + * conditions (logical AND operator): + * + * Ext.ComponentQuery.query('panel[cls~=my-cls][floating=true][title$="sales data"]'); + * + * E.g., the query above will match only a Panel-descended Component that has 'my-cls' + * CSS class *and* is floating *and* with a title that ends with "sales data". + * + * Expressions separated with commas will match any Component that satisfies + * *either* expression (logical OR operator): + * + * Ext.ComponentQuery.query('field[fieldLabel^=User], field[fieldLabel*=password]'); + * + * E.g., the query above will match any field with field label starting with "User", + * *or* any field that has "password" in its label. + * + * If you need to include a comma in an attribute matching expression, escape it with a + * backslash: + * + * Ext.ComponentQuery.query('field[fieldLabel^="User\\, foo"], field[fieldLabel*=password]'); + * + * ## Pseudo classes + * + * Pseudo classes may be used to filter results in the same way as in + * {@link Ext.dom.Query}. There are five default pseudo classes: + * + * * `not` Negates a selector. + * * `first` Filters out all except the first matching item for a selector. + * * `last` Filters out all except the last matching item for a selector. + * * `focusable` Filters out all except Components which by definition and configuration are + * potentially able to receieve focus, and can be focused at this time. Component can be + * focused when it is rendered, visible, and not disabled. Some Components can be focusable + * even when disabled (e.g. Menu items) via their parent Container configuration. + * Containers such as Panels generally are not focusable by themselves but can use + * focus delegation (`defaultFocus` config). Some Containers such as Menus and Windows + * are focusable by default. + * * `canfocus` Filters out all except Components which are curently able to receieve focus. + * That is, they are defined and configured focusable, and they are also visible and enabled. + * Note that this selector intentionally bypasses some checks done by `focusable` selector + * and works in a subtly different way. It is used internally by the framework and is not + * a replacement for `:focusable` selector. + * * `nth-child` Filters Components by ordinal position in the selection. + * * `scrollable` Filters out all except Components which are scrollable. + * * `visible` Filters out hidden Components. May test deep visibility using `':visible(true)'` + * + * These pseudo classes can be used with other matchers or without them: + * + * // Select first direct child button in any panel + * Ext.ComponentQuery.query('panel > button:first'); + * + * // Select last field in Profile form + * Ext.ComponentQuery.query('form[title=Profile] field:last'); + * + * // Find first focusable Component in a panel and focus it + * panel.down(':canfocus').focus(); + * + * // Select any field that is not hidden in a form + * form.query('field:not(hiddenfield)'); + * + * // Find last scrollable Component and reset its scroll positions. + * tabpanel.down(':scrollable[hideMode=display]:last').getScrollable().scrollTo(0, 0); + * + * Pseudo class `nth-child` can be used to find any child Component by its + * position relative to its siblings. This class' handler takes one argument + * that specifies the selection formula as `Xn` or `Xn+Y`: + * + * // Find every odd field in a form + * form.query('field:nth-child(2n+1)'); // or use shortcut: :nth-child(odd) + * + * // Find every even field in a form + * form.query('field:nth-child(2n)'); // or use shortcut: :nth-child(even) + * + * // Find every 3rd field in a form + * form.query('field:nth-child(3n)'); + * + * **Note:** The `nth-child` selector returns 1-based result sets. + * + * Pseudo classes can be combined to further filter the results, e.g., in the + * form example above we can modify the query to exclude hidden fields: + * + * // Find every 3rd non-hidden field in a form + * form.query('field:not(hiddenfield):nth-child(3n)'); + * + * Note that when combining pseudo classes, whitespace is significant, i.e. + * there should be no spaces between pseudo classes. This is a common mistake; + * if you accidentally type a space between `field` and `:not`, the query + * will not return any result because it will mean "find *field's children + * Components* that are not hidden fields...". + * + * ## Custom pseudo classes + * + * It is possible to define your own custom pseudo classes. In fact, a + * pseudo class is just a property in `Ext.ComponentQuery.pseudos` object + * that defines pseudo class name (property name) and pseudo class handler + * (property value): + * + * // Function receives array and returns a filtered array. + * Ext.ComponentQuery.pseudos.invalid = function(items) { + * var i = 0, l = items.length, c, result = []; + * for (; i < l; i++) { + * if (!(c = items[i]).isValid()) { + * result.push(c); + * } + * } + * return result; + * }; + * + * var invalidFields = myFormPanel.query('field:invalid'); + * if (invalidFields.length) { + * invalidFields[0].getEl().scrollIntoView(myFormPanel.body); + * for (var i = 0, l = invalidFields.length; i < l; i++) { + * invalidFields[i].getEl().frame("red"); + * } + * } + * + * Pseudo class handlers can be even more flexible, with a selector + * argument used to define the logic: + * + * // Handler receives array of itmes and selector in parentheses + * Ext.ComponentQuery.pseudos.titleRegex = function(components, selector) { + * var i = 0, l = components.length, c, result = [], regex = new RegExp(selector); + * for (; i < l; i++) { + * c = components[i]; + * if (c.title && regex.test(c.title)) { + * result.push(c); + * } + * } + * return result; + * } + * + * var salesTabs = tabPanel.query('panel:titleRegex("sales\\s+for\\s+201[123]")'); + * + * Be careful when using custom pseudo classes with MVC Controllers: when + * you use a pseudo class in Controller's `control` or `listen` component + * selectors, the pseudo class' handler function will be called very often + * and may slow down your application significantly. A good rule of thumb + * is to always specify Component xtype with the pseudo class so that the + * handlers are only called on Components that you need, and try to make + * the condition checks as cheap in terms of execution time as possible. + * Note how in the example above, handler function checks that Component + * *has* a title first, before running regex test on it. + * + * ## Query examples + * + * Queries return an array of Components. Here are some example queries: + * + * // retrieve all Ext.Panels in the document by xtype + * var panelsArray = Ext.ComponentQuery.query('panel'); + * + * // retrieve all Ext.Panels within the container with an id myCt + * var panelsWithinmyCt = Ext.ComponentQuery.query('#myCt panel'); + * + * // retrieve all direct children which are Ext.Panels within myCt + * var directChildPanel = Ext.ComponentQuery.query('#myCt > panel'); + * + * // retrieve all grids or trees + * var gridsAndTrees = Ext.ComponentQuery.query('gridpanel, treepanel'); + * + * // Focus first Component + * myFormPanel.child(':canfocus').focus(); + * + * // Retrieve every odd text field in a form + * myFormPanel.query('textfield:nth-child(odd)'); + * + * // Retrieve every even field in a form, excluding hidden fields + * myFormPanel.query('field:not(hiddenfield):nth-child(even)'); + * + * // Retrieve every scrollable in a tabpanel + * tabpanel.query(':scrollable'); + * + * For easy access to queries based from a particular Container see the + * {@link Ext.container.Container#query}, {@link Ext.container.Container#down} and + * {@link Ext.container.Container#child} methods. Also see + * {@link Ext.Component#up}. + */ +Ext.define('Ext.ComponentQuery', { + singleton: true, + requires: [ + 'Ext.ComponentManager', + 'Ext.util.Operators', + 'Ext.util.LruCache' + ] +}, function() { + var cq = this, + queryOperators = Ext.util.Operators, + nthRe = /(\d*)n\+?(\d*)/, + nthRe2 = /\D/, + stripLeadingSpaceRe = /^(\s)+/, + unescapeRe = /\\(.)/g, + regexCache = new Ext.util.LruCache({ + maxSize: 100 + }), + // A function source code pattern with a placeholder which accepts an expression which yields a truth value when applied + // as a member on each item in the passed array. + filterFnPattern = [ + 'var r = [],', + 'i = 0,', + 'it = items,', + 'l = it.length,', + 'c;', + 'for (; i < l; i++) {', + 'c = it[i];', + 'if (c.{0}) {', + 'r.push(c);', + '}', + '}', + 'return r;' + ].join(''), + filterItems = function(items, operation) { + // Argument list for the operation is [ itemsArray, operationArg1, operationArg2...] + // The operation's method loops over each item in the candidate array and + // returns an array of items which match its criteria + return operation.method.apply(this, [ + items + ].concat(operation.args)); + }, + getItems = function(items, mode) { + var result = [], + i = 0, + length = items.length, + candidate, + deep = mode !== '>'; + for (; i < length; i++) { + candidate = items[i]; + if (candidate.getRefItems) { + result = result.concat(candidate.getRefItems(deep)); + } + } + return result; + }, + getAncestors = function(items) { + var result = [], + i = 0, + length = items.length, + candidate; + for (; i < length; i++) { + candidate = items[i]; + while (!!(candidate = candidate.getRefOwner())) { + result.push(candidate); + } + } + return result; + }, + // Filters the passed candidate array and returns only items which match the passed xtype + filterByXType = function(items, xtype, shallow) { + if (xtype === '*') { + return items.slice(); + } else { + var result = [], + i = 0, + length = items.length, + candidate; + for (; i < length; i++) { + candidate = items[i]; + if (!candidate.destroyed && candidate.isXType(xtype, shallow)) { + result.push(candidate); + } + } + return result; + } + }, + // Filters the passed candidate array and returns only items which have the specified property match + filterByAttribute = function(items, property, operator, compareTo) { + var result = [], + i = 0, + length = items.length, + mustBeOwnProperty, presenceOnly, candidate, propValue, j, propLen, config; + // Prefixing property name with an @ means that the property must be in the candidate, not in its prototype + if (property.charAt(0) === '@') { + mustBeOwnProperty = true; + property = property.substr(1); + } + if (property.charAt(0) === '?') { + mustBeOwnProperty = true; + presenceOnly = true; + property = property.substr(1); + } + for (; i < length; i++) { + candidate = items[i]; + // If the candidate is a product of the Ext class system, then + // use the configurator to call getters to access the property. + // CQ can be used to filter raw Objects. + config = candidate.self && candidate.self.getConfigurator && candidate.self.$config.configs[property]; + if (config) { + propValue = candidate[config.names.get](); + } else if (mustBeOwnProperty && !candidate.hasOwnProperty(property)) { + + continue; + } else { + propValue = candidate[property]; + } + if (presenceOnly) { + result.push(candidate); + } + // implies property is an array, and we must compare value against each element. + else if (operator === '~=') { + if (propValue) { + //We need an array + if (!Ext.isArray(propValue)) { + propValue = propValue.split(' '); + } + for (j = 0 , propLen = propValue.length; j < propLen; j++) { + if (queryOperators[operator](Ext.coerce(propValue[j], compareTo), compareTo)) { + result.push(candidate); + break; + } + } + } + } else if (operator === '/=') { + if (propValue != null && compareTo.test(propValue)) { + result.push(candidate); + } + } else if (!compareTo ? !!propValue : queryOperators[operator](Ext.coerce(propValue, compareTo), compareTo)) { + result.push(candidate); + } + } + return result; + }, + // Filters the passed candidate array and returns only items which have the specified itemId or id + filterById = function(items, id, idOnly) { + var result = [], + i = 0, + length = items.length, + candidate, check; + for (; i < length; i++) { + candidate = items[i]; + check = idOnly ? candidate.id : candidate.getItemId(); + if (check === id) { + result.push(candidate); + } + } + return result; + }, + // Filters the passed candidate array and returns only items which the named pseudo class matcher filters in + filterByPseudo = function(items, name, value) { + return cq.pseudos[name](items, value); + }, + // Determines leading mode + // > for direct child, and ^ to switch to ownerCt axis + modeRe = /^(\s?([>\^])\s?|\s|$)/, + // Matches a token with possibly (true|false) appended for the "shallow" parameter + tokenRe = /^(#)?((?:\\\.|[\w\-])+|\*)(?:\((true|false)\))?/, + matchers = [ + { + // Checks for .xtype with possibly (true|false) appended for the "shallow" parameter + re: /^\.((?:\\\.|[\w\-])+)(?:\((true|false)\))?/, + method: filterByXType, + argTransform: function(args) { + var selector = args[0]; + Ext.log.warn('"' + selector + '" ComponentQuery selector style is deprecated,' + ' use "' + selector.replace(/^\./, '') + '" without the leading dot instead'); + if (args[1] !== undefined) { + args[1] = args[1].replace(unescapeRe, '$1'); + } + return args.slice(1); + } + }, + { + // Allow [@attribute] to check truthy ownProperty + // Allow [?attribute] to check for presence of ownProperty + // Allow [$attribute] + // Checks for @|?|$ -> word/hyphen chars -> any special attribute selector characters before + // the '=', etc. It strips out whitespace. + // For example: + // [attribute=value], [attribute^=value], [attribute$=value], [attribute*=value], + // [attribute~=value], [attribute%=value], [attribute!=value] + re: /^(?:\[((?:[@?$])?[\w\-]*)\s*(?:([\^$*~%!\/]?=)\s*(['"])?((?:\\\]|.)*?)\3)?(?!\\)\])/, + method: filterByAttribute, + argTransform: function(args) { + var selector = args[0], + property = args[1], + operator = args[2], + //quote = args[3], + compareTo = args[4], + compareRe; + // Unescape the attribute value matcher first + if (compareTo !== undefined) { + compareTo = compareTo.replace(unescapeRe, '$1'); + var format = Ext.String.format, + msg = "ComponentQuery selector '{0}' has an unescaped ({1}) character at the {2} " + "of the attribute value pattern. Usually that indicates an error " + "where the opening quote is not followed by the closing quote. " + "If you need to match a ({1}) character at the {2} of the attribute " + "value, escape the quote character in your pattern: (\\{1})", + match; + if (match = /^(['"]).*?[^'"]$/.exec(compareTo)) { + // jshint ignore:line + Ext.log.warn(format(msg, selector, match[1], 'beginning')); + } else if (match = /^[^'"].*?(['"])$/.exec(compareTo)) { + // jshint ignore:line + Ext.log.warn(format(msg, selector, match[1], 'end')); + } + } + if (operator === '/=') { + compareRe = regexCache.get(compareTo); + if (compareRe) { + compareTo = compareRe; + } else { + compareTo = regexCache.add(compareTo, new RegExp(compareTo)); + } + } + return [ + property, + operator, + compareTo + ]; + } + }, + { + // checks for #cmpItemId + re: /^#((?:\\\.|[\w\-])+)/, + method: filterById + }, + { + // checks for :() + re: /^\:([\w\-]+)(?:\(((?:\{[^\}]+\})|(?:(?!\{)[^\s>\/]*?(?!\})))\))?/, + method: filterByPseudo, + argTransform: function(args) { + if (args[2] !== undefined) { + args[2] = args[2].replace(unescapeRe, '$1'); + } + return args.slice(1); + } + }, + { + // checks for {} + re: /^(?:\{([^\}]+)\})/, + method: filterFnPattern + } + ]; + // Internal class Ext.ComponentQuery.Query + cq.Query = Ext.extend(Object, { + constructor: function(cfg) { + cfg = cfg || {}; + Ext.apply(this, cfg); + }, + // Executes this Query upon the selected root. + // The root provides the initial source of candidate Component matches which are progressively + // filtered by iterating through this Query's operations cache. + // If no root is provided, all registered Components are searched via the ComponentManager. + // root may be a Container who's descendant Components are filtered + // root may be a Component with an implementation of getRefItems which provides some nested Components such as the + // docked items within a Panel. + // root may be an array of candidate Components to filter using this Query. + execute: function(root) { + var operations = this.operations, + result = [], + op, i, len; + for (i = 0 , len = operations.length; i < len; i++) { + op = operations[i]; + result = result.concat(this._execute(root, op)); + } + return result; + }, + _execute: function(root, operations) { + var i = 0, + length = operations.length, + operation, workingItems; + // no root, use all Components in the document + if (!root) { + workingItems = Ext.ComponentManager.getAll(); + } + // Root is an iterable object like an Array, or system Collection, eg HtmlCollection + else if (Ext.isIterable(root)) { + workingItems = root; + } + // Root is a MixedCollection + else if (root.isMixedCollection) { + workingItems = root.items; + } + // We are going to loop over our operations and take care of them + // one by one. + for (; i < length; i++) { + operation = operations[i]; + // The mode operation requires some custom handling. + // All other operations essentially filter down our current + // working items, while mode replaces our current working + // items by getting children from each one of our current + // working items. The type of mode determines the type of + // children we get. (e.g. > only gets direct children) + if (operation.mode === '^') { + workingItems = getAncestors(workingItems || [ + root + ]); + } else if (operation.mode) { + workingItems = getItems(workingItems || [ + root + ], operation.mode); + } else { + workingItems = filterItems(workingItems || getItems([ + root + ]), operation); + } + // If this is the last operation, it means our current working + // items are the final matched items. Thus return them! + if (i === length - 1) { + return workingItems; + } + } + return []; + }, + is: function(component, root) { + var operations = this.operations, + result = false, + len = operations.length, + op, i; + if (len === 0) { + return true; + } + for (i = 0; i < len; i++) { + op = operations[i]; + result = this._is(component, root, op); + if (result) { + return result; + } + } + return false; + }, + _is: function(component, root, operations) { + var len = operations.length, + active = [ + component + ], + operation, i, j, mode, items, item; + // Loop backwards, since we're going up the hierarchy + for (i = len - 1; i >= 0; --i) { + operation = operations[i]; + mode = operation.mode; + // Traversing hierarchy + if (mode) { + if (mode === '^') { + active = getItems(active, ' '); + } else if (mode === '>') { + items = []; + for (j = 0 , len = active.length; j < len; ++j) { + item = active[j].getRefOwner(); + if (item) { + items.push(item); + } + } + active = items; + } else { + active = getAncestors(active); + } + } else { + active = filterItems(active, operation); + } + // After traversing the hierarchy, if we have no items, jump out + if (active.length === 0) { + return false; + } + } + // We don't push these on as operations because we don't want to mutate the + // array, but this is essentially a continuation of the loop above. + if (root) { + if (!mode) { + // Last operation wasn't a mode operation, so navigate up to find + // ancestors + active = getAncestors(active); + } + if (active.length > 0) { + // If we have active items, check the root exists there to ensure we're + // part of the tree + active = filterItems(active, { + method: filterById, + args: [ + root.id, + true + ] + }); + } + if (active.length === 0) { + return false; + } + } + return true; + }, + getMatches: function(components, operations) { + var len = operations.length, + i; + for (i = 0; i < len; ++i) { + components = filterItems(components, operations[i]); + // Performance enhancement, if we have nothing, we can + // never add anything new, so jump out + if (components.length === 0) { + break; + } + } + return components; + }, + isMultiMatch: function() { + return this.operations.length > 1; + } + }); + Ext.apply(cq, { + /** + * @private + * Cache of selectors and matching ComponentQuery.Query objects + */ + cache: new Ext.util.LruCache({ + maxSize: 100 + }), + /** + * @private + * Cache of pseudo class filter functions + */ + pseudos: { + not: function(components, selector) { + var i = 0, + length = components.length, + results = [], + index = -1, + component; + for (; i < length; ++i) { + component = components[i]; + if (!cq.is(component, selector)) { + results[++index] = component; + } + } + return results; + }, + first: function(components) { + var ret = []; + if (components.length > 0) { + ret.push(components[0]); + } + return ret; + }, + last: function(components) { + var len = components.length, + ret = []; + if (len > 0) { + ret.push(components[len - 1]); + } + return ret; + }, + // This filters for components which by definition and configuration are + // theoretically focusable. It does not take into account the current app state. + focusable: function(cmps) { + var len = cmps.length, + results = [], + i = 0, + c; + for (; i < len; i++) { + c = cmps[i]; + if (c.isFocusable && c.isFocusable()) { + results.push(c); + } + } + return results; + }, + // This filters for components which are currently able to recieve focus. + canfocus: function(cmps, value) { + var len = cmps.length, + results = [], + i = 0, + c; + for (; i < len; i++) { + c = cmps[i]; + if (c.canFocus && c.canFocus(false, value)) { + results.push(c); + } + } + return results; + }, + "nth-child": function(c, a) { + var result = [], + m = nthRe.exec(a === "even" && "2n" || a === "odd" && "2n+1" || !nthRe2.test(a) && "n+" + a || a), + f = (m[1] || 1) - 0, + len = m[2] - 0, + i, n, nodeIndex; + for (i = 0; n = c[i]; i++) { + // jshint ignore:line + nodeIndex = i + 1; + if (f === 1) { + if (len === 0 || nodeIndex === len) { + result.push(n); + } + } else if ((nodeIndex + len) % f === 0) { + result.push(n); + } + } + return result; + }, + scrollable: function(cmps) { + var len = cmps.length, + results = [], + i = 0, + c; + for (; i < len; i++) { + c = cmps[i]; + // Note that modern toolkit prefixes with an underscore. + if (c.scrollable || c._scrollable) { + results.push(c); + } + } + return results; + }, + visible: function(cmps, deep) { + deep = deep === 'true'; + var len = cmps.length, + results = [], + i = 0, + c; + for (; i < len; i++) { + c = cmps[i]; + // Note that modern toolkit prefixes with an underscore. + if (c.isVisible(deep)) { + results.push(c); + } + } + return results; + } + }, + /** + * Returns an array of matched Components from within the passed root object. + * + * This method filters returned Components in a similar way to how CSS selector based DOM + * queries work using a textual selector string. + * + * See class summary for details. + * + * @param {String} selector The selector string to filter returned Components. + * @param {Ext.container.Container} [root] The Container within which to perform the query. + * If omitted, all Components within the document are included in the search. + * + * This parameter may also be an array of Components to filter according to the selector. + * @return {Ext.Component[]} The matched Components. + * + * @member Ext.ComponentQuery + */ + query: function(selector, root) { + // An empty query will match every Component + if (!selector) { + return Ext.ComponentManager.getAll(); + } + var results = [], + noDupResults = [], + dupMatcher = {}, + query = cq.cache.get(selector), + resultsLn, cmp, i; + if (!query) { + query = cq.cache.add(selector, cq.parse(selector)); + } + results = query.execute(root); + // multiple selectors, potential to find duplicates + // lets filter them out. + if (query.isMultiMatch()) { + resultsLn = results.length; + for (i = 0; i < resultsLn; i++) { + cmp = results[i]; + if (!dupMatcher[cmp.id]) { + noDupResults.push(cmp); + dupMatcher[cmp.id] = true; + } + } + results = noDupResults; + } + return results; + }, + /** + * Traverses the tree rooted at the passed root in pre-order mode, calling the passed function on the nodes at each level. + * That is the function is called upon each node **before** being called on its children). + * + * For an object to be queryable, it must implement the `getRefItems` method which returns all + * immediate child items. + * + * This method is used at each level down the cascade. Currently {@link Ext.Component Component}s + * and {@link Ext.data.TreeModel TreeModel}s are queryable. + * + * If you have tree-structured data, you can make your nodes queryable, and use ComponentQuery on them. + * + * @param {Object} selector A ComponentQuery selector used to filter candidate nodes before calling the function. + * An empty string matches any node. + * @param {String} root The root queryable object to start from. + * @param {Function} fn The function to call. Return `false` to abort the traverse. + * @param {Object} fn.node The node being visited. + * @param {Object} [scope] The context (`this` reference) in which the function is executed. + * @param {Array} [extraArgs] A set of arguments to be appended to the function's argument list to pass down extra data known to the caller + * **after** the node being visited. + */ + visitPreOrder: function(selector, root, fn, scope, extraArgs) { + cq._visit(true, selector, root, fn, scope, extraArgs); + }, + /** + * Traverses the tree rooted at the passed root in post-order mode, calling the passed function on the nodes at each level. + * That is the function is called upon each node **after** being called on its children). + * + * For an object to be queryable, it must implement the `getRefItems` method which returns all + * immediate child items. + * + * This method is used at each level down the cascade. Currently {@link Ext.Component Component}s + * and {@link Ext.data.TreeModel TreeModel}s are queryable. + * + * If you have tree-structured data, you can make your nodes queryable, and use ComponentQuery on them. + * + * @param {Object} selector A ComponentQuery selector used to filter candidate nodes before calling the function. + * An empty string matches any node. + * @param {String} root The root queryable object to start from. + * @param {Function} fn The function to call. Return `false` to abort the traverse. + * @param {Object} fn.node The node being visited. + * @param {Object} [scope] The context (`this` reference) in which the function is executed. + * @param {Array} [extraArgs] A set of arguments to be appended to the function's argument list to pass down extra data known to the caller + * **after** the node being visited. + */ + visitPostOrder: function(selector, root, fn, scope, extraArgs) { + cq._visit(false, selector, root, fn, scope, extraArgs); + }, + /** + * @private + * Visit implementation which handles both preOrder and postOrder modes. + */ + _visit: function(preOrder, selector, root, fn, scope, extraArgs) { + var query = cq.cache.get(selector), + callArgs = [ + root + ], + children, + len = 0, + i, rootMatch; + if (!query) { + query = cq.cache.add(selector, cq.parse(selector)); + } + rootMatch = query.is(root); + if (root.getRefItems) { + children = root.getRefItems(); + len = children.length; + } + // append optional extraArgs + if (extraArgs) { + Ext.Array.push(callArgs, extraArgs); + } + if (preOrder) { + if (rootMatch) { + if (fn.apply(scope || root, callArgs) === false) { + return false; + } + } + } + for (i = 0; i < len; i++) { + if (cq._visit.call(cq, preOrder, selector, children[i], fn, scope, extraArgs) === false) { + return false; + } + } + if (!preOrder) { + if (rootMatch) { + if (fn.apply(scope || root, callArgs) === false) { + return false; + } + } + } + }, + /** + * Tests whether the passed Component matches the selector string. + * An empty selector will always match. + * + * @param {Ext.Component} component The Component to test + * @param {String/Function} selector The selector string to test against. + * Or a filter function which returns `true` if the component matches. + * @param {Ext.Component} [root=null] The root component. + * @return {Boolean} True if the Component matches the selector. + * @member Ext.ComponentQuery + */ + is: function(component, selector, root) { + if (!selector) { + return true; + } + if (typeof selector === 'function') { + return selector(component); + } else { + var query = cq.cache.get(selector); + if (!query) { + query = cq.cache.add(selector, cq.parse(selector)); + } + return query.is(component, root); + } + }, + parse: function(selector) { + var operations = [], + selectors, sel, i, len; + selectors = Ext.splitAndUnescape(selector, ','); + for (i = 0 , len = selectors.length; i < len; i++) { + // Trim the whitespace as the parser expects it. + sel = Ext.String.trim(selectors[i]); + // Usually, a dangling comma at the end of a selector means a typo. + // In that case, the last sel value will be an empty string; the parser + // will silently ignore it which is not good, so we throw an error here. + if (sel === '') { + Ext.raise('Invalid ComponentQuery selector: ""'); + } + operations.push(cq._parse(sel)); + } + // Now that we have all our operations in an array, we are going + // to create a new Query using these operations. + return new cq.Query({ + operations: operations + }); + }, + _parse: function(selector) { + var operations = [], + trim = Ext.String.trim, + length = matchers.length, + lastSelector, tokenMatch, token, matchedChar, modeMatch, selectorMatch, transform, i, matcher, method, args; + // We are going to parse the beginning of the selector over and + // over again, slicing off the selector any portions we converted into an + // operation, until it is an empty string. + while (selector && lastSelector !== selector) { + lastSelector = selector; + // First we check if we are dealing with a token like #, * or an xtype + tokenMatch = selector.match(tokenRe); + if (tokenMatch) { + matchedChar = tokenMatch[1]; + token = trim(tokenMatch[2]).replace(unescapeRe, '$1'); + // If the token is prefixed with a # we push a filterById operation to our stack + if (matchedChar === '#') { + operations.push({ + method: filterById, + args: [ + token + ] + }); + } else // If the token is a * or an xtype string, we push a filterByXType + // operation to the stack. + { + operations.push({ + method: filterByXType, + args: [ + token, + Boolean(tokenMatch[3]) + ] + }); + } + // Now we slice of the part we just converted into an operation + selector = selector.replace(tokenMatch[0], '').replace(stripLeadingSpaceRe, '$1'); + } + // If the next part of the query is not a space or > or ^, it means we + // are going to check for more things that our current selection + // has to comply to. + while (!(modeMatch = selector.match(modeRe))) { + // Lets loop over each type of matcher and execute it + // on our current selector. + for (i = 0; selector && i < length; i++) { + matcher = matchers[i]; + selectorMatch = selector.match(matcher.re); + method = matcher.method; + transform = matcher.argTransform; + // If we have a match, add an operation with the method + // associated with this matcher, and pass the regular + // expression matches are arguments to the operation. + if (selectorMatch) { + // Transform function will do unescaping and additional checks + if (transform) { + args = transform(selectorMatch); + } else { + args = selectorMatch.slice(1); + } + operations.push({ + method: Ext.isString(matcher.method) ? // Turn a string method into a function by formatting the string with our selector matche expression + // A new method is created for different match expressions, eg {id=='textfield-1024'} + // Every expression may be different in different selectors. + Ext.functionFactory('items', Ext.String.format.apply(Ext.String, [ + method + ].concat(selectorMatch.slice(1)))) : matcher.method, + args: args + }); + selector = selector.replace(selectorMatch[0], '').replace(stripLeadingSpaceRe, '$1'); + break; + } + // Break on match + // Exhausted all matches: It's an error + if (i === (length - 1)) { + Ext.raise('Invalid ComponentQuery selector: "' + arguments[0] + '"'); + } + } + } + // Now we are going to check for a mode change. This means a space + // or a > to determine if we are going to select all the children + // of the currently matched items, or a ^ if we are going to use the + // ownerCt axis as the candidate source. + if (modeMatch[1]) { + // Assignment, and test for truthiness! + operations.push({ + mode: modeMatch[2] || modeMatch[1] + }); + // When we have consumed the mode character, clean up leading spaces + selector = selector.replace(modeMatch[0], '').replace(stripLeadingSpaceRe, ''); + } + } + return operations; + } + }); + /** + * Same as {@link Ext.ComponentQuery#query}. + * @param {String} selector The selector string to filter returned Components. + * @param {Ext.container.Container} [root] The Container within which to perform the query. + * If omitted, all Components within the document are included in the search. + * + * This parameter may also be an array of Components to filter according to the selector. + * @return {Ext.Component[]} The matched Components. + * @method all + * @member Ext + */ + Ext.all = function() { + return cq.query.apply(cq, arguments); + }; + /** + * Returns the first match to the given component query. + * See {@link Ext.ComponentQuery#query}. + * @param {String} selector The selector string to filter returned Component. + * @param {Ext.container.Container} [root] The Container within which to perform the query. + * If omitted, all Components within the document are included in the search. + * + * This parameter may also be an array of Components to filter according to the selector. + * @return {Ext.Component} The first matched Component or `null`. + * @method first + * @member Ext + */ + Ext.first = function() { + var matches = cq.query.apply(cq, arguments); + return (matches && matches[0]) || null; + }; +}); + +/** + * @private + */ +Ext.define('Ext.Evented', { + alternateClassName: 'Ext.EventedBase', + mixins: [ + 'Ext.mixin.Observable' + ], + initialized: false, + constructor: function(config) { + // Base constructor is overriden for testing + this.callParent(); + this.mixins.observable.constructor.call(this, config); + this.initialized = true; + }, + onClassExtended: function(cls, data) { + if (!data.hasOwnProperty('eventedConfig')) { + return; + } + var config = data.config, + eventedConfig = data.eventedConfig, + name, cfg; + if (config) { + Ext.applyIf(config, eventedConfig); + } else { + cls.addConfig(eventedConfig); + } + /* + * These are generated setters for eventedConfig + * + * If the component is initialized, it invokes fireAction to fire the event as well, + * which indicate something has changed. Otherwise, it just executes the action + * (happens during initialization) + * + * This is helpful when we only want the event to be fired for subsequent changes. + * Also it's a major performance improvement for instantiation when fired events + * are mostly useless since there's no listeners + */ + //TODO: Move this into Observable + for (name in eventedConfig) { + if (eventedConfig.hasOwnProperty(name)) { + cfg = Ext.Config.get(name); + data[cfg.names.set] = cfg.eventedSetter || cfg.getEventedSetter(); + } + } + } +}); + +/** + * This mixin provides a common interface for objects that can be positioned, e.g. + * {@link Ext.Component Components} and {@link Ext.dom.Element Elements} + * @private + */ +Ext.define('Ext.util.Positionable', { + mixinId: 'positionable', + _positionTopLeft: [ + 'position', + 'top', + 'left' + ], + // Stub implementation called after positioning. + // May be implemented in subclasses. Component has an implementation. + // Hardware acceleration due to the transform:translateZ(0) flickering + // when painting clipped elements. This class allows that to be turned off + // while elements are in a clipped state. + clippedCls: Ext.baseCSSPrefix + 'clipped', + afterSetPosition: Ext.emptyFn, + // *********************** + // Begin Abstract Methods + // *********************** + /** + * Gets the x,y coordinates of an element specified by the anchor position on the + * element. + * @param {Ext.dom.Element} el The element + * @param {String} [anchor='tl'] The specified anchor position. + * See {@link #alignTo} for details on supported anchor positions. + * @param {Boolean} [local] True to get the local (element top/left-relative) anchor + * position instead of page coordinates + * @param {Object} [size] An object containing the size to use for calculating anchor + * position {width: (target width), height: (target height)} (defaults to the + * element's current size) + * @return {Number[]} [x, y] An array containing the element's x and y coordinates + * @private + */ + getAnchorToXY: function() { + Ext.raise("getAnchorToXY is not implemented in " + this.$className); + }, + /** + * Returns the size of the element's borders and padding. + * @return {Object} an object with the following numeric properties + * - beforeX + * - afterX + * - beforeY + * - afterY + * @private + */ + getBorderPadding: function() { + Ext.raise("getBorderPadding is not implemented in " + this.$className); + }, + /** + * Returns the x coordinate of this element reletive to its `offsetParent`. + * @return {Number} The local x coordinate + */ + getLocalX: function() { + Ext.raise("getLocalX is not implemented in " + this.$className); + }, + /** + * Returns the x and y coordinates of this element relative to its `offsetParent`. + * @return {Number[]} The local XY position of the element + */ + getLocalXY: function() { + Ext.raise("getLocalXY is not implemented in " + this.$className); + }, + /** + * Returns the y coordinate of this element reletive to its `offsetParent`. + * @return {Number} The local y coordinate + */ + getLocalY: function() { + Ext.raise("getLocalY is not implemented in " + this.$className); + }, + /** + * Gets the current X position of the DOM element based on page coordinates. + * @return {Number} The X position of the element + */ + getX: function() { + Ext.raise("getX is not implemented in " + this.$className); + }, + /** + * Gets the current position of the DOM element based on page coordinates. + * @return {Number[]} The XY position of the element + */ + getXY: function() { + Ext.raise("getXY is not implemented in " + this.$className); + }, + /** + * Gets the current Y position of the DOM element based on page coordinates. + * @return {Number} The Y position of the element + */ + getY: function() { + Ext.raise("getY is not implemented in " + this.$className); + }, + /** + * Sets the local x coordinate of this element using CSS style. When used on an + * absolute positioned element this method is symmetrical with {@link #getLocalX}, but + * may not be symmetrical when used on a relatively positioned element. + * @param {Number} x The x coordinate. A value of `null` sets the left style to 'auto'. + * @return {Ext.util.Positionable} this + */ + setLocalX: function() { + Ext.raise("setLocalX is not implemented in " + this.$className); + }, + /** + * Sets the local x and y coordinates of this element using CSS style. When used on an + * absolute positioned element this method is symmetrical with {@link #getLocalXY}, but + * may not be symmetrical when used on a relatively positioned element. + * @param {Number/Array} x The x coordinate or an array containing [x, y]. A value of + * `null` sets the left style to 'auto' + * @param {Number} [y] The y coordinate, required if x is not an array. A value of + * `null` sets the top style to 'auto' + * @return {Ext.util.Positionable} this + */ + setLocalXY: function() { + Ext.raise("setLocalXY is not implemented in " + this.$className); + }, + /** + * Sets the local y coordinate of this element using CSS style. When used on an + * absolute positioned element this method is symmetrical with {@link #getLocalY}, but + * may not be symmetrical when used on a relatively positioned element. + * @param {Number} y The y coordinate. A value of `null` sets the top style to 'auto'. + * @return {Ext.util.Positionable} this + */ + setLocalY: function() { + Ext.raise("setLocalY is not implemented in " + this.$className); + }, + /** + * Sets the X position of the DOM element based on page coordinates. + * @param {Number} x The X position + * @return {Ext.util.Positionable} this + */ + setX: function() { + Ext.raise("setX is not implemented in " + this.$className); + }, + /** + * Sets the position of the DOM element in page coordinates. + * @param {Number[]} pos Contains X & Y [x, y] values for new position (coordinates + * are page-based) + * @return {Ext.util.Positionable} this + */ + setXY: function() { + Ext.raise("setXY is not implemented in " + this.$className); + }, + /** + * Sets the Y position of the DOM element based on page coordinates. + * @param {Number} y The Y position + * @return {Ext.util.Positionable} this + */ + setY: function() { + Ext.raise("setY is not implemented in " + this.$className); + }, + // *********************** + // End Abstract Methods + // *********************** + // TODO: currently only used by ToolTip. does this method belong here? + /** + * @private + */ + adjustForConstraints: function(xy, parent) { + var vector = this.getConstrainVector(parent, xy); + if (vector) { + xy[0] += vector[0]; + xy[1] += vector[1]; + } + return xy; + }, + /** + * Aligns the element with another element relative to the specified anchor points. If + * the other element is the document it aligns it to the viewport. The position + * parameter is optional, and can be specified in any one of the following formats: + * + * - **Blank**: Defaults to aligning the element's top-left corner to the target's + * bottom-left corner ("tl-bl"). + * - **Two anchors**: If two values from the table below are passed separated by a dash, + * the first value is used as the element's anchor point, and the second value is + * used as the target's anchor point. + * - **Two edge/offset descriptors:** An edge/offset descriptor is an edge initial + * (`t`/`r`/`b`/`l`) followed by a percentage along that side. This describes a + * point to align with a similar point in the target. So `'t0-b0'` would be + * the same as `'tl-bl'`, `'l0-r50'` would place the top left corner of this item + * halfway down the right edge of the target item. This allows more flexibility + * and also describes which two edges are considered adjacent when positioning a tip pointer. + * + * Following are all of the supported predefined anchor positions: + * + * Value Description + * ----- ----------------------------- + * tl The top left corner + * t The center of the top edge + * tr The top right corner + * l The center of the left edge + * c The center + * r The center of the right edge + * bl The bottom left corner + * b The center of the bottom edge + * br The bottom right corner + * + * You can put a '?' at the end of the alignment string to constrain the positioned element to the + * {@link Ext.Viewport Viewport}. The element will attempt to align as specified, but the position + * will be adjusted to constrain to the viewport if necessary. Note that the element being aligned + * might be swapped to align to a different position than that specified in order to enforce the viewport + * constraints. + * + * Example Usage: + * + * // align el to other-el using the default positioning + * // ("tl-bl", non-constrained) + * el.alignTo("other-el"); + * + * // align the top left corner of el with the top right corner of other-el + * // (constrained to viewport) + * el.alignTo("other-el", "tl-tr?"); + * + * // align the bottom right corner of el with the center left edge of other-el + * el.alignTo("other-el", "br-l?"); + * + * // align the center of el with the bottom left corner of other-el and + * // adjust the x position by -6 pixels (and the y position by 0) + * el.alignTo("other-el", "c-bl", [-6, 0]); + * + * // align the 25% point on the bottom edge of this el + * // with the 75% point on the top edge of other-el. + * el.alignTo("other-el", 'b25-t75'); + * + * @param {Ext.util.Positionable/HTMLElement/String} element The Positionable, + * HTMLElement, or id of the element to align to. + * @param {String} [position="tl-bl?"] The position to align to + * @param {Number[]} [offsets] Offset the positioning by [x, y] + * Element animation config object + * @param {Boolean} animate (private) + * @return {Ext.util.Positionable} this + */ + alignTo: function(element, position, offsets, animate) { + var me = this, + el = me.el; + return me.setXY(me.getAlignToXY(element, position, offsets), el.anim && !!animate ? el.anim(animate) : false); + }, + /** + * Calculates x,y coordinates specified by the anchor position on the element, adding + * extraX and extraY values. + * @param {String} [anchor='tl'] The specified anchor position. + * See {@link #alignTo} for details on supported anchor positions. + * @param {Number} [extraX] value to be added to the x coordinate + * @param {Number} [extraY] value to be added to the y coordinate + * @param {Object} [size] An object containing the size to use for calculating anchor + * position {width: (target width), height: (target height)} (defaults to the + * element's current size) + * @return {Number[]} [x, y] An array containing the element's x and y coordinates + * @private + */ + calculateAnchorXY: function(anchor, extraX, extraY, size) { + var region = this.getRegion(); + region.setPosition(0, 0); + region.translateBy(extraX || 0, extraY || 0); + if (size) { + region.setWidth(size.width); + region.setHeight(size.height); + } + return region.getAnchorPoint(anchor); + }, + /** + * This function converts a legacy alignment string such as 't-b' into a + * pair of edge, offset objects which describe the alignment points of + * the two regions. + * + * So tl-br becomes {myEdge:'t', offset:0}, {otherEdge:'b', offset:100} + * + * This not only allows more flexibility in the alignment possibilities, + * but it also resolves any ambiguity as to chich two edges are desired + * to be adjacent if an anchor pointer is required. + * @private + */ + convertPositionSpec: function(posSpec) { + return Ext.util.Region.getAlignInfo(posSpec); + }, + /** + * Gets the x,y coordinates to align this element with another element. See + * {@link #alignTo} for more info on the supported position values. + * @param {Ext.util.Positionable/HTMLElement/String} alignToEl The Positionable, + * HTMLElement, or id of the element to align to. + * @param {String} [position="tl-bl?"] The position to align to + * @param {Number[]} [offsets] Offset the positioning by [x, y] + * @return {Number[]} [x, y] + */ + getAlignToXY: function(alignToEl, position, offsets) { + var newRegion = this.getAlignToRegion(alignToEl, position, offsets); + return [ + newRegion.x, + newRegion.y + ]; + }, + getAlignToRegion: function(alignToEl, posSpec, offset, minHeight) { + var me = this, + inside, newRegion, bodyScroll; + alignToEl = Ext.fly(alignToEl.el || alignToEl); + if (!alignToEl || !alignToEl.dom) { + Ext.raise({ + sourceClass: 'Ext.util.Positionable', + sourceMethod: 'getAlignToXY', + msg: 'Attempted to align an element that doesn\'t exist' + }); + } + posSpec = me.convertPositionSpec(posSpec); + // If position spec ended with a "?" or "!", then constraining is necessary + if (posSpec.constrain) { + // Constrain to the correct enclosing object: + // If the assertive form was used (like "tl-bl!"), constrain to the alignToEl. + if (posSpec.constrain === '!') { + inside = alignToEl; + } else { + // Otherwise, attempt to use the constrainTo property. + // Otherwise, if we are a Component, there will be a container property. + // Otherwise, use this Positionable's element's parent node. + inside = me.constrainTo || me.container || me.el.parent(); + } + inside = Ext.fly(inside.el || inside).getConstrainRegion(); + } + if (alignToEl === Ext.getBody()) { + bodyScroll = alignToEl.getScroll(); + offset = [ + bodyScroll.left, + bodyScroll.top + ]; + } + newRegion = me.getRegion().alignTo({ + target: alignToEl.getRegion(), + inside: inside, + minHeight: minHeight, + offset: offset, + align: posSpec, + axisLock: true + }); + return newRegion; + }, + /** + * Gets the x,y coordinates specified by the anchor position on the element. + * @param {String} [anchor='tl'] The specified anchor position. + * See {@link #alignTo} for details on supported anchor positions. + * @param {Boolean} [local] True to get the local (element top/left-relative) anchor + * position instead of page coordinates + * @param {Object} [size] An object containing the size to use for calculating anchor + * position {width: (target width), height: (target height)} (defaults to the + * element's current size) + * @return {Number[]} [x, y] An array containing the element's x and y coordinates + */ + getAnchorXY: function(anchor, local, size) { + var me = this, + region = me.getRegion(), + el = me.el, + isViewport = el.dom.nodeName === 'BODY' || el.dom.nodeType === 9, + scroll = el.getScroll(); + if (local) { + region.setPosition(0, 0); + } else if (isViewport) { + region.setPosition(scroll.left, scroll.top); + } + if (size) { + region.setWidth(size.width); + region.setHeight(size.height); + } + return region.getAnchorPoint(anchor); + }, + /** + * Return an object defining the area of this Element which can be passed to + * {@link #setBox} to set another Element's size/location to match this element. + * + * @param {Boolean} [contentBox] If true a box for the content of the element is + * returned. + * @param {Boolean} [local] If true the element's left and top relative to its + * `offsetParent` are returned instead of page x/y. + * @return {Object} An object in the format + * @return {Number} return.x The element's X position. + * @return {Number} return.y The element's Y position. + * @return {Number} return.width The element's width. + * @return {Number} return.height The element's height. + * @return {Number} return.bottom The element's lower bound. + * @return {Number} return.right The element's rightmost bound. + * + * The returned object may also be addressed as an Array where index 0 contains the X + * position and index 1 contains the Y position. The result may also be used for + * {@link #setXY} + */ + getBox: function(contentBox, local) { + var me = this, + xy = local ? me.getLocalXY() : me.getXY(), + x = xy[0], + y = xy[1], + w, h, borderPadding, beforeX, beforeY; + // Document body or document is special case + if (me.el.dom.nodeName === 'BODY' || me.el.dom.nodeType === 9) { + w = Ext.Element.getViewportWidth(); + h = Ext.Element.getViewportHeight(); + } else { + w = me.getWidth(); + h = me.getHeight(); + } + if (contentBox) { + borderPadding = me.getBorderPadding(); + beforeX = borderPadding.beforeX; + beforeY = borderPadding.beforeY; + x += beforeX; + y += beforeY; + w -= (beforeX + borderPadding.afterX); + h -= (beforeY + borderPadding.afterY); + } + return { + x: x, + left: x, + 0: x, + y: y, + top: y, + 1: y, + width: w, + height: h, + right: x + w, + bottom: y + h + }; + }, + /** + * Calculates the new [x,y] position to move this Positionable into a constrain region. + * + * By default, this Positionable is constrained to be within the container it was added to, or the element it was + * rendered to. + * + * Priority is given to constraining the top and left within the constraint. + * + * An alternative constraint may be passed. + * @param {String/HTMLElement/Ext.dom.Element/Ext.util.Region} [constrainTo] The Element or {@link Ext.util.Region Region} + * into which this Component is to be constrained. Defaults to the element into which this Positionable + * was rendered, or this Component's {@link Ext.Component#constrainTo. + * @param {Number[]} [proposedPosition] A proposed `[X, Y]` position to test for validity + * and to coerce into constraints instead of using this Positionable's current position. + * @param {Boolean} [local] The proposedPosition is local *(relative to floatParent if a floating Component)* + * @param {Number[]} [proposedSize] A proposed `[width, height]` size to use when calculating + * constraints instead of using this Positionable's current size. + * @return {Number[]} **If** the element *needs* to be translated, the new `[X, Y]` position within + * constraints if possible, giving priority to keeping the top and left edge in the constrain region. + * Otherwise, `false`. + * @private + */ + calculateConstrainedPosition: function(constrainTo, proposedPosition, local, proposedSize) { + var me = this, + vector, + fp = me.floatParent, + parentNode = fp ? fp.getTargetEl() : null, + parentOffset, borderPadding, proposedConstrainPosition, + xy = false; + if (local && fp) { + parentOffset = parentNode.getXY(); + borderPadding = parentNode.getBorderPadding(); + parentOffset[0] += borderPadding.beforeX; + parentOffset[1] += borderPadding.beforeY; + if (proposedPosition) { + proposedConstrainPosition = [ + proposedPosition[0] + parentOffset[0], + proposedPosition[1] + parentOffset[1] + ]; + } + } else { + proposedConstrainPosition = proposedPosition; + } + // Calculate the constrain vector to coerce our position to within our + // constrainTo setting. getConstrainVector will provide a default constraint + // region if there is no explicit constrainTo, *and* there is no floatParent owner Component. + constrainTo = constrainTo || me.constrainTo || parentNode || me.container || me.el.parent(); + if (local && proposedConstrainPosition) { + proposedConstrainPosition = me.reverseTranslateXY(proposedConstrainPosition); + } + vector = ((me.constrainHeader && me.header.rendered) ? me.header : me).getConstrainVector(constrainTo, proposedConstrainPosition, proposedSize); + // false is returned if no movement is needed + if (vector) { + xy = proposedPosition || me.getPosition(local); + xy[0] += vector[0]; + xy[1] += vector[1]; + } + return xy; + }, + /** + * Returns the content region of this element for purposes of constraining or clipping floating + * children. That is the region within the borders and scrollbars, but not within the padding. + * + * @return {Ext.util.Region} A Region containing "top, left, bottom, right" properties. + */ + getConstrainRegion: function() { + var me = this, + el = me.el, + isBody = el.dom.nodeName === 'BODY', + dom = el.dom, + borders = el.getBorders(), + pos = el.getXY(), + left = pos[0] + borders.beforeX, + top = pos[1] + borders.beforeY, + scroll, width, height; + // For the body we want to do some special logic. + if (isBody) { + scroll = el.getScroll(); + left = scroll.left; + top = scroll.top; + width = Ext.Element.getViewportWidth(); + height = Ext.Element.getViewportHeight(); + } else { + width = dom.clientWidth; + height = dom.clientHeight; + } + return new Ext.util.Region(top, left + width, top + height, left); + }, + /** + * Returns the `[X, Y]` vector by which this Positionable's element must be translated to make a best + * attempt to constrain within the passed constraint. Returns `false` if the element + * does not need to be moved. + * + * Priority is given to constraining the top and left within the constraint. + * + * The constraint may either be an existing element into which the element is to be + * constrained, or a {@link Ext.util.Region Region} into which this element is to be + * constrained. + * + * By default, any extra shadow around the element is **not** included in the constrain calculations - the edges + * of the element are used as the element bounds. To constrain the shadow within the constrain region, set the + * `constrainShadow` property on this element to `true`. + * + * @param {Ext.util.Positionable/HTMLElement/String/Ext.util.Region} [constrainTo] The + * Positionable, HTMLElement, element id, or Region into which the element is to be + * constrained. + * @param {Number[]} [proposedPosition] A proposed `[X, Y]` position to test for validity + * and to produce a vector for instead of using the element's current position + * @param {Number[]} [proposedSize] A proposed `[width, height]` size to constrain + * instead of using the element's current size + * @return {Number[]/Boolean} **If** the element *needs* to be translated, an `[X, Y]` + * vector by which this element must be translated. Otherwise, `false`. + */ + getConstrainVector: function(constrainTo, proposedPosition, proposedSize) { + var me = this, + thisRegion = me.getRegion(), + vector = [ + 0, + 0 + ], + shadowSize = (me.shadow && me.constrainShadow && !me.shadowDisabled) ? me.el.shadow.getShadowSize() : undefined, + overflowed = false, + constraintInsets = me.constraintInsets; + if (!(constrainTo instanceof Ext.util.Region)) { + constrainTo = Ext.get(constrainTo.el || constrainTo); + // getConstrainRegion uses clientWidth and clientHeight. + // so it will clear any scrollbars. + constrainTo = constrainTo.getConstrainRegion(); + } + // Apply constraintInsets + if (constraintInsets) { + constraintInsets = Ext.isObject(constraintInsets) ? constraintInsets : Ext.Element.parseBox(constraintInsets); + constrainTo.adjust(constraintInsets.top, constraintInsets.right, constraintInsets.bottom, constraintInsets.left); + } + // Shift this region to occupy the proposed position + if (proposedPosition) { + thisRegion.translateBy(proposedPosition[0] - thisRegion.x, proposedPosition[1] - thisRegion.y); + } + // Set the size of this region to the proposed size + if (proposedSize) { + thisRegion.right = thisRegion.left + proposedSize[0]; + thisRegion.bottom = thisRegion.top + proposedSize[1]; + } + // Reduce the constrain region to allow for shadow + if (shadowSize) { + constrainTo.adjust(shadowSize[0], -shadowSize[1], -shadowSize[2], shadowSize[3]); + } + // Constrain the X coordinate by however much this Element overflows + if (thisRegion.right > constrainTo.right) { + overflowed = true; + vector[0] = (constrainTo.right - thisRegion.right); + } + // overflowed the right + if (thisRegion.left + vector[0] < constrainTo.left) { + overflowed = true; + vector[0] = (constrainTo.left - thisRegion.left); + } + // overflowed the left + // Constrain the Y coordinate by however much this Element overflows + if (thisRegion.bottom > constrainTo.bottom) { + overflowed = true; + vector[1] = (constrainTo.bottom - thisRegion.bottom); + } + // overflowed the bottom + if (thisRegion.top + vector[1] < constrainTo.top) { + overflowed = true; + vector[1] = (constrainTo.top - thisRegion.top); + } + // overflowed the top + return overflowed ? vector : false; + }, + /** + * Returns the offsets of this element from the passed element. The element must both + * be part of the DOM tree and not have display:none to have page coordinates. + * @param {Ext.util.Positionable/HTMLElement/String} offsetsTo The Positionable, + * HTMLElement, or element id to get get the offsets from. + * @return {Number[]} The XY page offsets (e.g. `[100, -200]`) + */ + getOffsetsTo: function(offsetsTo) { + var o = this.getXY(), + e = offsetsTo.isRegion ? [ + offsetsTo.x, + offsetsTo.y + ] : Ext.fly(offsetsTo.el || offsetsTo).getXY(); + return [ + o[0] - e[0], + o[1] - e[1] + ]; + }, + /** + * Returns a region object that defines the area of this element. + * @param {Boolean} [contentBox] If true a box for the content of the element is + * returned. + * @param {Boolean} [local] If true the element's left and top relative to its + * `offsetParent` are returned instead of page x/y. + * @return {Ext.util.Region} A Region containing "top, left, bottom, right" properties. + */ + getRegion: function(contentBox, local) { + var box = this.getBox(contentBox, local); + return new Ext.util.Region(box.top, box.right, box.bottom, box.left); + }, + /** + * Returns a region object that defines the client area of this element. + * + * That is, the area *within* any scrollbars. + * @return {Ext.util.Region} A Region containing "top, left, bottom, right" properties. + */ + getClientRegion: function() { + var me = this, + el = me.el, + dom = el.dom, + viewContentBox = me.getBox(true), + scrollbarHeight = dom.offsetHeight > dom.clientHeight, + scrollbarWidth = dom.offsetWidth > dom.clientWidth, + padding, scrollSize, isRTL; + if (scrollbarHeight || scrollbarWidth) { + scrollSize = Ext.getScrollbarSize(); + // Capture width taken by any vertical scrollbar. + // If there is a vertical scrollbar, shrink the box. + if (scrollbarWidth) { + scrollbarWidth = scrollSize.width; + isRTL = el.getStyle('direction') === 'rtl' && !Ext.supports.rtlVertScrollbarOnRight; + if (isRTL) { + padding = el.getPadding('l'); + viewContentBox.left -= padding + Math.max(padding, scrollbarWidth); + } else { + padding = el.getPadding('r'); + viewContentBox.right += padding - Math.max(padding, scrollbarWidth); + } + } + // Capture height taken by any horizontal scrollbar. + // If there is a horizontal scrollbar, shrink the box. + if (scrollbarHeight) { + scrollbarHeight = scrollSize.height; + padding = el.getPadding('b'); + viewContentBox.bottom += padding - Math.max(padding, scrollbarHeight); + } + } + // The client region excluding any scrollbars. + return new Ext.util.Region(viewContentBox.top, viewContentBox.right, viewContentBox.bottom, viewContentBox.left); + }, + /** + * Returns the **content** region of this element. That is the region within the borders + * and padding. + * @return {Ext.util.Region} A Region containing "top, left, bottom, right" member data. + */ + getViewRegion: function() { + var me = this, + el = me.el, + isBody = el.dom.nodeName === 'BODY', + borderPadding, scroll, pos, top, left, width, height; + // For the body we want to do some special logic + if (isBody) { + scroll = el.getScroll(); + left = scroll.left; + top = scroll.top; + width = Ext.Element.getViewportWidth(); + height = Ext.Element.getViewportHeight(); + } else { + borderPadding = me.getBorderPadding(); + pos = me.getXY(); + left = pos[0] + borderPadding.beforeX; + top = pos[1] + borderPadding.beforeY; + width = me.getWidth(true); + height = me.getHeight(true); + } + return new Ext.util.Region(top, left + width, top + height, left); + }, + /** + * Move the element relative to its current position. + * @param {String} direction Possible values are: + * + * - `"l"` (or `"left"`) + * - `"r"` (or `"right"`) + * - `"t"` (or `"top"`, or `"up"`) + * - `"b"` (or `"bottom"`, or `"down"`) + * + * @param {Number} distance How far to move the element in pixels + * @param {Boolean} animate (private) + */ + move: function(direction, distance, animate) { + var me = this, + xy = me.getXY(), + x = xy[0], + y = xy[1], + left = [ + x - distance, + y + ], + right = [ + x + distance, + y + ], + top = [ + x, + y - distance + ], + bottom = [ + x, + y + distance + ], + hash = { + l: left, + left: left, + r: right, + right: right, + t: top, + top: top, + up: top, + b: bottom, + bottom: bottom, + down: bottom + }; + direction = direction.toLowerCase(); + me.setXY([ + hash[direction][0], + hash[direction][1] + ], animate); + }, + /** + * Sets the element's box. + * @param {Object} box The box to fill {x, y, width, height} + * @return {Ext.util.Positionable} this + */ + setBox: function(box) { + var me = this, + x, y; + if (box.isRegion) { + box = { + x: box.left, + y: box.top, + width: box.right - box.left, + height: box.bottom - box.top + }; + } + me.constrainBox(box); + x = box.x; + y = box.y; + // Position to the contrained position + // Call setSize *last* so that any possible layout has the last word on position. + me.setXY([ + x, + y + ]); + me.setSize(box.width, box.height); + me.afterSetPosition(x, y); + return me; + }, + /** + * @private + */ + constrainBox: function(box) { + var me = this, + constrainedPos, x, y; + if (me.constrain || me.constrainHeader) { + x = ('x' in box) ? box.x : box.left; + y = ('y' in box) ? box.y : box.top; + constrainedPos = me.calculateConstrainedPosition(null, [ + x, + y + ], false, [ + box.width, + box.height + ]); + // If it *needs* constraining, change the position + if (constrainedPos) { + box.x = constrainedPos[0]; + box.y = constrainedPos[1]; + } + } + }, + /** + * Translates the passed page coordinates into left/top css values for the element + * @param {Number/Array} x The page x or an array containing [x, y] + * @param {Number} [y] The page y, required if x is not an array + * @return {Object} An object with left and top properties. e.g. + * {left: (value), top: (value)} + */ + translatePoints: function(x, y) { + var pos = this.translateXY(x, y); + return { + left: pos.x, + top: pos.y + }; + }, + /** + * Translates the passed page coordinates into x and y css values for the element + * @param {Number/Array} x The page x or an array containing [x, y] + * @param {Number} [y] The page y, required if x is not an array + * @return {Object} An object with x and y properties. e.g. + * {x: (value), y: (value)} + * @private + */ + translateXY: function(x, y) { + var me = this, + el = me.el, + styles = el.getStyle(me._positionTopLeft), + relative = styles.position === 'relative', + left = parseFloat(styles.left), + top = parseFloat(styles.top), + xy = me.getXY(); + if (Ext.isArray(x)) { + y = x[1]; + x = x[0]; + } + if (isNaN(left)) { + left = relative ? 0 : el.dom.offsetLeft; + } + if (isNaN(top)) { + top = relative ? 0 : el.dom.offsetTop; + } + left = (typeof x === 'number') ? x - xy[0] + left : undefined; + top = (typeof y === 'number') ? y - xy[1] + top : undefined; + return { + x: left, + y: top + }; + }, + /** + * Converts local coordinates into page-level coordinates + * @param {Number[]} xy The local x and y coordinates + * @return {Number[]} The translated coordinates + * @private + */ + reverseTranslateXY: function(xy) { + var coords = xy, + el = this.el, + dom = el.dom, + offsetParent = dom.offsetParent, + relative, offsetParentXY, x, y; + if (offsetParent) { + relative = el.isStyle('position', 'relative') , offsetParentXY = Ext.fly(offsetParent).getXY() , x = xy[0] + offsetParentXY[0] + offsetParent.clientLeft; + y = xy[1] + offsetParentXY[1] + offsetParent.clientTop; + if (relative) { + // relative positioned elements sit inside the offsetParent's padding, + // while absolute positioned element sit just inside the border + x += el.getPadding('l'); + y += el.getPadding('t'); + } + coords = [ + x, + y + ]; + } + return coords; + }, + privates: { + /** + * Clips this Component/Element to fit within the passed element's or component's view area + * @param {Ext.Component/Ext.Element/Ext.util.Region} clippingEl The Component or element or Region which should + * clip this element even if this element is outside the bounds of that region. + * @param {Number} sides The sides to clip 1=top, 2=right, 4=bottom, 8=left. + * + * This is to support components being clipped to their logical owner, such as a grid row editor when the + * row being edited scrolls out of sight. The editor should be clipped at the edge of the scrolling element. + * @private + */ + clipTo: function(clippingEl, sides) { + var clippingRegion, + el = this.el, + floaterRegion = el.getRegion(), + overflow, i, + clipValues = [], + clippedCls = this.clippedCls, + clipStyle, clipped, shadow; + // Allow a Region to be passed + if (clippingEl.isRegion) { + clippingRegion = clippingEl; + } else { + clippingRegion = (clippingEl.isComponent ? clippingEl.el : Ext.fly(clippingEl)).getConstrainRegion(); + } + // Default to clipping all round. + if (!sides) { + sides = 15; + } + // Calculate how much all sides exceed the clipping region + if (sides & 1 && (overflow = clippingRegion.top - floaterRegion.top) > 0) { + clipValues[0] = overflow; + clipped = true; + } else { + clipValues[0] = -10000; + } + if (sides & 2 && (overflow = floaterRegion.right - clippingRegion.right) > 0) { + clipValues[1] = Math.max(0, el.getWidth() - overflow); + clipped = true; + } else { + clipValues[1] = 10000; + } + if (sides & 4 && (overflow = floaterRegion.bottom - clippingRegion.bottom) > 0) { + clipValues[2] = Math.max(0, el.getHeight() - overflow); + clipped = true; + } else { + clipValues[2] = 10000; + } + if (sides & 8 && (overflow = clippingRegion.left - floaterRegion.left) > 0) { + clipValues[3] = overflow; + clipped = true; + } else { + clipValues[3] = -10000; + } + clipStyle = 'rect('; + for (i = 0; i < 4; ++i) { + // Use the clipValue if there is one calculated. + // If not, top and left must be 0px, right and bottom must be 'auto'. + clipStyle += Ext.Element.addUnits(clipValues[i], 'px'); + clipStyle += (i === 3) ? ')' : ','; + } + el.dom.style.clip = clipStyle; + // hardware acceleration causes flickering problems on clipped elements. + // disable it while an element is clipped. + el.addCls(clippedCls); + // Clip/unclip shadow too. + // TODO: As SOON as IE8 retires, refactor Ext.dom.Shadow to use CSS3BoxShadow directly on its el + // Then we won't have to bother clipping the shadow as well. We'll just have to adjust the clipping on the + // element outwards in the unclipped dimensions to keep the shadow visible. + if ((shadow = el.shadow) && (el = shadow.el) && el.dom) { + clipValues[2] -= shadow.offsets.y; + clipValues[3] -= shadow.offsets.x; + clipStyle = 'rect('; + for (i = 0; i < 4; ++i) { + // Use the clipValue if there is one calculated. + // If not, clear the edges by 10px to allow the shadow's spread to be visible. + clipStyle += Ext.Element.addUnits(clipValues[i], 'px'); + clipStyle += (i === 3) ? ')' : ','; + } + el.dom.style.clip = clipStyle; + // Clip does not work on IE8 shadows + // TODO: As SOON as IE8 retires, refactor Ext.dom.Shadow to use CSS3BoxShadow directly on its el + if (clipped && !Ext.supports.CSS3BoxShadow) { + el.dom.style.display = 'none'; + } else { + el.dom.style.display = ''; + // hardware acceleration causes flickering problems on clipped elements. + // disable it while an element is clipped. + el.addCls(clippedCls); + } + } + }, + /** + * Clears any clipping applied to this component by {@link #method-clipTo}. + * @private + */ + clearClip: function() { + var el = this.el, + clippedCls = this.clippedCls; + el.dom.style.clip = Ext.isIE8 ? 'auto' : ''; + // hardware acceleration causes flickering problems on clipped elements. + // re-enable it when an element is unclipped. + el.removeCls(clippedCls); + // unclip shadow too. + if (el.shadow && el.shadow.el && el.shadow.el.dom) { + el.shadow.el.dom.style.clip = Ext.isIE8 ? 'auto' : ''; + // Clip does not work on IE8 shadows + // TODO: As SOON as IE8 retires, refactor Ext.dom.Shadow to use CSS3BoxShadow directly on its el + if (!Ext.supports.CSS3BoxShadow) { + el.dom.style.display = ''; + // hardware acceleration causes flickering problems on clipped elements. + // re-enable it when an element is unclipped. + el.removeCls(clippedCls); + } + } + } + } +}); + +/** + * @class Ext.util.Positionable + */ +Ext.define('Ext.overrides.util.Positionable', { + override: 'Ext.util.Positionable', + /** + * @method alignTo + * @param {Ext.util.Positionable/HTMLElement/String} anchorToEl The Positionable, + * HTMLElement, or id of the element to align to. + * @param {String} [alignment="tl-bl?"] The position to align to + * @param {Number[]} [offsets] Offset the positioning by [x, y] + * @param {Boolean/Object} [animate] true for the default animation or a standard + * Element animation config object + * @return {Ext.util.Positionable} this + */ + /** + * @method anchorTo + * Anchors an element to another element and realigns it when the window is resized. + * @param {Ext.util.Positionable/HTMLElement/String} anchorToEl The Positionable, + * HTMLElement, or id of the element to align to. + * @param {String} [alignment="tl-bl?"] The position to align to + * @param {Number[]} [offsets] Offset the positioning by [x, y] + * @param {Boolean/Object} [animate] true for the default animation or a standard + * Element animation config object + * @param {Boolean/Number} [monitorScroll=50] True to monitor body scroll and + * reposition. If this parameter is a number, it is used as the buffer delay in + * milliseconds. + * @param {Function} [callback] The function to call after the animation finishes + * @return {Ext.util.Positionable} this + */ + anchorTo: function(anchorToEl, alignment, offsets, animate, monitorScroll, callback) { + var me = this, + scroll = !Ext.isEmpty(monitorScroll), + action = function() { + me.mixins.positionable.alignTo.call(me, anchorToEl, alignment, offsets, animate); + Ext.callback(callback, me); + }, + anchor = me.getAnchor(); + // previous listener anchor, remove it + me.removeAnchor(); + Ext.apply(anchor, { + fn: action, + scroll: scroll + }); + Ext.on('resize', action, null); + if (scroll) { + Ext.getWin().on('scroll', action, null, { + buffer: !isNaN(monitorScroll) ? monitorScroll : 50 + }); + } + action(); + // align immediately + return me; + }, + getAnchor: function() { + var el = this.el, + data, anchor; + if (!el || !el.dom) { + return; + } + data = el.getData(); + anchor = data._anchor; + if (!anchor) { + anchor = data._anchor = {}; + } + return anchor; + }, + alignTo: function(element, position, offsets, /* private (documented in ext) */ + animate) { + var me = this, + el = me.el, + newMaxHeight, newRegion; + // Release any height constraint prior to aligning if we are shrinkwrap height. + if (me.isComponent && me.getSizeModel().height.shrinkWrap) { + if (me.maxHeight) { + me.setMaxHeight(null); + } + newMaxHeight = true; + } + newRegion = me.getAlignToRegion(element, position, offsets, me.minHeight || 150); + me.setXY([ + newRegion.x, + newRegion.y + ], el.anim && !!animate ? el.anim(animate) : false); + // Impose calculated height constraint. + if (newMaxHeight && (newMaxHeight = newRegion.getHeight()) !== me.getHeight()) { + me.setMaxHeight(newMaxHeight); + } + return me; + }, + /** + * @method move + * Move the element relative to its current position. + * @param {String} direction Possible values are: + * + * - `"l"` (or `"left"`) + * - `"r"` (or `"right"`) + * - `"t"` (or `"top"`, or `"up"`) + * - `"b"` (or `"bottom"`, or `"down"`) + * + * @param {Number} distance How far to move the element in pixels + * @param {Boolean/Object} [animate] true for the default animation or a standard + * Element animation config object + */ + /** + * Remove any anchor to this element. See {@link #anchorTo}. + * @return {Ext.util.Positionable} this + */ + removeAnchor: function() { + var anchor = this.getAnchor(); + if (anchor && anchor.fn) { + Ext.un('resize', anchor.fn); + if (anchor.scroll) { + Ext.getWin().on('scroll', anchor.fn); + } + delete anchor.fn; + } + return this; + }, + /** + * @method setBox + * Sets the element's box. If animate is true then x, y, width, and height will be + * animated concurrently. + * @param {Object} box The box to fill {x, y, width, height} + * @param {Boolean/Object} [animate] true for the default animation or a standard + * Element animation config object + * @return {Ext.util.Positionable} this + */ + setBox: function(box, animate) { + var me = this; + if (box.isRegion) { + box = { + x: box.left, + y: box.top, + width: box.right - box.left, + height: box.bottom - box.top + }; + } + if (animate) { + me.constrainBox(box); + me.animate(Ext.applyIf({ + to: box, + listeners: { + afteranimate: Ext.Function.bind(me.afterSetPosition, me, [ + box.x, + box.y + ]) + } + }, animate)); + } else { + me.callParent([ + box + ]); + } + return me; + } +}); +/** + * @method setX + * Sets the X position of the DOM element based on page coordinates. + * @param {Number} x The X position + * @param {Boolean/Object} [animate] True for the default animation, or a standard + * Element animation config object + * @return {Ext.util.Positionable} this + */ +/** + * @method setXY + * Sets the position of the DOM element in page coordinates. + * @param {Number[]} pos Contains X & Y [x, y] values for new position (coordinates + * are page-based) + * @param {Boolean/Object} [animate] True for the default animation, or a standard + * Element animation config object + * @return {Ext.util.Positionable} this + */ +/** + * @method setY + * Sets the Y position of the DOM element based on page coordinates. + * @param {Number} y The Y position + * @param {Boolean/Object} [animate] True for the default animation, or a standard + * Element animation config object + * @return {Ext.util.Positionable} this + */ + +/** + * Private utility class that manages the internal cache for {@link Ext.dom.Shadow Underlays} + * and {@link Ext.dom.Shim Shims}. + * @private + */ +Ext.define('Ext.dom.UnderlayPool', { + /** + * @constructor + * @param {Object} elementConfig A {@link Ext.dom.Helper DomHelper} config object to + * use for generating elements in the pool. + */ + constructor: function(elementConfig) { + this.elementConfig = elementConfig; + this.cache = []; + }, + /** + * Checks an element out of the pool. + * @return {Ext.dom.Element} + */ + checkOut: function() { + var el = this.cache.shift(); + if (!el) { + el = Ext.Element.create(this.elementConfig); + el.setVisibilityMode(2); + // tell the spec runner to ignore this element when checking if the dom is clean + el.dom.setAttribute('data-sticky', true); + } + return el; + }, + /** + * Checks an element back into the pool for future reuse + * @param {Ext.dom.Element} el + */ + checkIn: function(el) { + this.cache.push(el); + Ext.getDetachedBody().dom.appendChild(el.dom); + }, + /** + * Reset the pool by emptying the cache and destroying all its elements + */ + reset: function() { + var cache = this.cache, + i = cache.length; + while (i--) { + cache[i].destroy(); + } + this.cache = []; + } +}); + +/** + * A class that provides an underlay element which displays behind an absolutely positioned + * target element and tracks its size and position. Abstract base class for + * {@link Ext.dom.Shadow} and {@link Ext.dom.Shim} + * + * + * @private + * @abstract + */ +Ext.define('Ext.dom.Underlay', { + requires: [ + 'Ext.dom.UnderlayPool' + ], + /** + * @cfg {Ext.dom.Element} target + * The target element + */ + /** + * @cfg {Number} zIndex + * The CSS z-index to use for this underlay. Defaults to the z-index of {@link #target}. + */ + constructor: function(config) { + Ext.apply(this, config); + }, + /** + * @method + * @protected + * Called before the underlay is shown, immediately after its element is retrieved + * from the pool + */ + beforeShow: Ext.emptyFn, + /** + * @protected + * Returns the dom element that this underlay should be inserted before. + * Defaults to the target element + * @return {Ext.dom.Element} + */ + getInsertionTarget: function() { + return this.target; + }, + /** + * @protected + * @return {Ext.dom.UnderlayPool} + */ + getPool: function() { + return this.pool || (this.self.prototype.pool = new Ext.dom.UnderlayPool(this.elementConfig)); + }, + /** + * Hides the underlay + */ + hide: function() { + var me = this, + el = me.el; + if (el) { + if (el.dom) { + el.hide(); + me.getPool().checkIn(el); + } + me.el = null; + } + me.hidden = true; + }, + /** + * Aligns the underlay to its target element + * @param {Number} [x] The x position of the target element. If not provided, the + * x position will be read from the DOM. + * @param {Number} [y] The y position of the target element. If not provided, the + * y position will be read from the DOM. + * @param {Number} [width] The width of the target element. If not provided, the + * width will be read from the DOM. + * @param {Number} [height] The height of the target element. If not provided, the + * height will be read from the DOM. + */ + realign: function(x, y, width, height) { + var me = this, + el = me.el, + target = me.target, + offsets = me.offsets, + max = Math.max; + if (el) { + if (x == null) { + x = target.getX(); + } + if (y == null) { + y = target.getY(); + } + if (width == null) { + width = target.getWidth(); + } + if (height == null) { + height = target.getHeight(); + } + if (offsets) { + x = x + offsets.x; + y = y + offsets.y; + width = max(width + offsets.w, 0); + height = max(height + offsets.h, 0); + } + el.setXY([ + x, + y + ]); + el.setSize(width, height); + } + }, + /** + * Adjust the z-index of this underlay + * @param {Number} zIndex The new z-index + */ + setZIndex: function(zIndex) { + this.zIndex = zIndex; + if (this.el) { + this.el.setStyle("z-index", zIndex); + } + }, + /** + * Shows the underlay + */ + show: function() { + var me = this, + target = me.target, + zIndex = me.zIndex, + el = me.el, + insertionTarget = me.getInsertionTarget().dom, + dom; + if (!el) { + el = me.el = me.getPool().checkOut(); + } + me.beforeShow(); + if (zIndex == null) { + // For best results, we need the underlay to be as close as possible to its + // target element in the z-index stacking order without overlaying the target + // element. Since the UnderlayPool inserted the underlay as high as possible + // in the dom tree when we checked the underlay out of the pool, we can assume + // that it comes before the target element in the dom tree, and therefore can + // give it the exact same index as the target element. + zIndex = (parseInt(target.getStyle("z-index"), 10)); + } + if (zIndex) { + el.setStyle("z-index", zIndex); + } + // Overlay elements are shared, so fix position to match current owner + el.setStyle('position', me.fixed ? 'fixed' : ''); + dom = el.dom; + if (dom.nextSibling !== insertionTarget) { + // inserting the underlay as the previous sibling of the target ensures that + // it will show behind the target, as long as its z-index is less than or equal + // to the z-index of the target element. + target.dom.parentNode.insertBefore(dom, insertionTarget); + } + el.show(); + me.realign(); + me.hidden = false; + } +}); + +/** + * Simple class that can provide a shadow effect for any absolutely positioned {@link + * Ext.dom.Element Element}. + * + * Not meant to be used directly. To apply a shadow to an Element use the + * {@link Ext.dom.Element#enableShadow enableShadow} method. + * + * @private + */ +Ext.define('Ext.dom.Shadow', { + extend: 'Ext.dom.Underlay', + alternateClassName: 'Ext.Shadow', + /** + * @cfg {String} mode + * The shadow display mode. Supports the following options: + * + * - sides : Shadow displays on both sides and bottom only + * - frame : Shadow displays equally on all four sides + * - drop : Traditional bottom-right drop shadow + */ + mode: 'drop', + /** + * @cfg {Number} offset + * The number of pixels to offset the shadow from the element + */ + offset: 4, + cls: Ext.baseCSSPrefix + (!Ext.supports.CSS3BoxShadow ? 'ie' : 'css') + '-shadow', + /** + * Creates new Shadow. + * @param {Object} config (optional) Config object. + */ + constructor: function(config) { + var me = this, + outerOffsets, offsets, offset, rad; + me.callParent([ + config + ]); + me.elementConfig = { + cls: me.cls, + role: 'presentation' + }; + offset = me.offset; + rad = Math.floor(offset / 2); + me.opacity = 50; + switch (me.mode.toLowerCase()) { + case "drop": + outerOffsets = { + x: 0, + y: 0, + w: offset, + h: offset + }; + if (Ext.supports.CSS3BoxShadow) { + offsets = { + x: offset, + y: offset, + h: -offset, + w: -offset + }; + } else { + offsets = { + x: -rad, + y: -rad, + h: -rad, + w: -rad + }; + }; + break; + case "sides": + outerOffsets = { + x: -offset, + y: 0, + w: offset * 2, + h: offset + }; + if (Ext.supports.CSS3BoxShadow) { + offsets = { + x: 0, + y: offset, + h: -offset, + w: 0 + }; + } else { + offsets = { + x: 1 + rad - 2 * offset, + y: -(1 + rad), + h: -1, + w: rad - 1 + }; + }; + break; + case "frame": + outerOffsets = { + x: -offset, + y: -offset, + w: offset * 2, + h: offset * 2 + }; + if (Ext.supports.CSS3BoxShadow) { + offsets = { + x: 0, + y: 0, + h: 0, + w: 0 + }; + } else { + offsets = { + x: 1 + rad - 2 * offset, + y: 1 + rad - 2 * offset, + h: offset - rad - 1, + w: offset - rad - 1 + }; + }; + break; + case "bottom": + outerOffsets = { + x: -offset, + y: 0, + w: offset * 2, + h: offset + }; + if (Ext.supports.CSS3BoxShadow) { + offsets = { + x: 0, + y: offset, + h: -offset, + w: 0 + }; + } else { + offsets = { + x: 0, + y: offset, + h: 0, + w: 0 + }; + }; + break; + } + /** + * @property {Object} offsets The offsets used for positioning the shadow element + * relative to its target element + */ + me.offsets = offsets; + /** + * @property {Object} outerOffsets Offsets that represent the union of the areas + * of the target element and the shadow combined. Used by Ext.dom.Element for + * ensuring that the shim (if present) extends under the full area of both elements. + */ + me.outerOffsets = outerOffsets; + }, + /** + * @private + * Returns the shadow size on each side of the element in standard CSS order: top, right, bottom, left; + * @return {Number[]} Top, right, bottom and left shadow size. + */ + getShadowSize: function() { + var me = this, + offset = me.el ? me.offset : 0, + result = [ + offset, + offset, + offset, + offset + ], + mode = me.mode.toLowerCase(); + // There are only offsets if the shadow element is present. + if (me.el && mode !== 'frame') { + result[0] = 0; + if (mode == 'drop') { + result[3] = 0; + } + } + return result; + }, + /** + * @private + * CSS property used to set the box shadow. + */ + boxShadowProperty: (function() { + var property = 'boxShadow', + style = document.documentElement.style; + if (!('boxShadow' in style)) { + if ('WebkitBoxShadow' in style) { + // Safari prior to version 5.1 and Chrome prior to version 10 + property = 'WebkitBoxShadow'; + } else if ('MozBoxShadow' in style) { + // FF 3.5 & 3.6 + property = 'MozBoxShadow'; + } + } + return property; + }()), + beforeShow: function() { + var me = this, + style = me.el.dom.style, + shim = me.shim; + if (Ext.supports.CSS3BoxShadow) { + style[me.boxShadowProperty] = '0 0 ' + (me.offset + 2) + 'px #888'; + } else { + style.filter = "progid:DXImageTransform.Microsoft.alpha(opacity=" + me.opacity + ") progid:DXImageTransform.Microsoft.Blur(pixelradius=" + (me.offset) + ")"; + } + // if we are showing a shadow, and we already have a visible shim, we need to + // realign the shim to ensure that it includes the size of target and shadow els + if (shim) { + shim.realign(); + } + }, + /** + * Sets the opacity of the shadow + * @param {Number} opacity The opacity + */ + setOpacity: function(opacity) { + var el = this.el; + if (el) { + if (Ext.isIE && !Ext.supports.CSS3BoxShadow) { + opacity = Math.floor(opacity * 100 / 2) / 100; + } + this.opacity = opacity; + el.setOpacity(opacity); + } + } +}); + +/** + * Simple class that provides an iframe shim for any absolutely positioned {@link + * Ext.dom.Element Element} to prevent windowed objects from showing through. + * + * Not meant to be used directly. Internally shims are applied to Elements using + * {@link Ext.dom.Element#enableShim enableShim}. Developers should use the + * {@link Ext.util.Floating#shim shim} config to add shims to their + * {@link Ext.Component Components} or set {@link Ext#useShims Ext.useShims}=true. + * @private + */ +Ext.define('Ext.dom.Shim', { + extend: 'Ext.dom.Underlay', + cls: Ext.baseCSSPrefix + 'shim', + constructor: function(config) { + this.callParent([ + config + ]); + this.elementConfig = { + tag: 'iframe', + cls: this.cls, + role: 'presentation', + frameBorder: '0', + src: Ext.SSL_SECURE_URL, + // tabIndex of -1 ensures that the iframe is not focusable by the user + tabindex: '-1' + }; + }, + getInsertionTarget: function() { + // ensure that the shim is inserted before the shadow in the dom, so that the + // shadow will be stacked on top of it. + var shadow = this.shadow; + return (shadow && shadow.el) || this.target; + } +}); + +/** + * A special Ext.util.Event subclass that adds support for capture (top-down propagation) + * listeners, and non-delegated (directly attached to the dom) listeners. + * + * An Ext.Element will have one instance of this class per event type that is being listened + * for. The ElementEvent instance provides a single point for attaching event listeners + * and abstracts away important details on the timing and ordering of event firing. + * Internally this class manages up to 3 separate Ext.util.Event instances. These represent + * separate stacks of listeners that may be invoked during different phases of event propagation. + * + * - `captures` - tracks listeners that should fire during the "capture" phase of the + * standard delegated model (listeners attached using capture:true) + * - `direct` - tracks directly attached listeners, that is listeners that should fire + * immediately when the event is dispatched to the dom element, before the event bubbles + * upward and delegated listener processing begins + * (listeners attached using delegated:false) + * - `directCaptures` - tracks directly attached capture listeners (only works in IE10+) + * + * For more detail on the timing of when these event stacks are dispatched please see + * Ext.event.publisher.Dom + * + * @private + */ +Ext.define('Ext.dom.ElementEvent', { + extend: 'Ext.util.Event', + addListener: function(fn, scope, options, caller, manager) { + var me = this, + added = false, + name = me.name, + isDirectEvent = Ext.event.publisher.Dom.instance.directEvents[name], + captures, directs, directCaptures; + options = options || {}; + if (options.delegated === false || isDirectEvent) { + if (isDirectEvent && options.delegate) { + options.capture = true; + } + if (options.capture) { + directCaptures = me.directCaptures || (me.directCaptures = new Ext.util.Event(me.observable, name)); + added = directCaptures.addListener(fn, scope, options, caller, manager); + } else { + directs = me.directs || (me.directs = new Ext.util.Event(me.observable, name)); + added = directs.addListener(fn, scope, options, caller, manager); + } + } else if (options.capture) { + captures = me.captures || (me.captures = new Ext.util.Event(me.observable, name)); + added = captures.addListener(fn, scope, options, caller, manager); + } else { + added = me.callParent([ + fn, + scope, + options, + caller, + manager + ]); + } + return added; + }, + removeListener: function(fn, scope) { + var me = this, + captures = me.captures, + directs = me.directs, + directCaptures = me.directCaptures, + removed = false, + index = me.findListener(fn, scope); + if (index !== -1) { + removed = me.callParent([ + fn, + scope, + index + ]); + } else { + if (directs) { + index = directs.findListener(fn, scope); + } + if (index !== -1) { + removed = directs.removeListener(fn, scope, index); + } else { + if (captures) { + index = captures.findListener(fn, scope); + } + if (index !== -1) { + removed = captures.removeListener(fn, scope, index); + } else if (directCaptures) { + index = directCaptures.findListener(fn, scope); + if (index !== -1) { + removed = directCaptures.removeListener(fn, scope, index); + } + } + } + } + return removed; + }, + clearListeners: function() { + var me = this, + directCaptures = me.directCaptures, + directs = me.directs, + captures = me.captures; + if (directCaptures) { + directCaptures.clearListeners(); + } + if (directs) { + directs.clearListeners(); + } + if (captures) { + captures.clearListeners(); + } + me.callParent(); + }, + suspend: function() { + var me = this, + directCaptures = me.directCaptures, + directs = me.directs, + captures = me.captures; + if (directCaptures) { + directCaptures.suspend(); + } + if (directs) { + directs.suspend(); + } + if (captures) { + captures.suspend(); + } + me.callParent(); + }, + resume: function() { + var me = this, + directCaptures = me.directCaptures, + directs = me.directs, + captures = me.captures; + if (directCaptures) { + directCaptures.resume(); + } + if (directs) { + directs.resume(); + } + if (captures) { + captures.resume(); + } + me.callParent(); + } +}); + +/** + * Abstract base class for event publishers + * @private + */ +Ext.define('Ext.event.publisher.Publisher', { + isEventPublisher: true, + $vetoClearingPrototypeOnDestroy: true, + /** + * @property {Array} handledEvents + * An array of events that this publisher handles. + */ + handledEvents: [], + statics: { + /** + * @property {Object} publishers + * A map of all publisher singleton instances. Publishers register themselves + * in this map as soon as they are constructed. + */ + publishers: {}, + /** + * @property publishersByEvent + * A map of handled event names to the publisher that handles each event. + * Provides a convenient way for looking up the publisher that handles any given + * event, for example: + * + * // get the publisher that handles click: + * var publisher = Ext.event.publisher.Publisher.publishersByEvent.click; + */ + publishersByEvent: {} + }, + constructor: function() { + var me = this, + type = me.type; + /** + * @property {Object} handles + * @private + * A map for conveniently checking if this publisher handles a given event + */ + me.handles = {}; + if (!type) { + Ext.raise("Event publisher '" + me.$className + "' defined without a 'type' property."); + } + if (me.self.instance) { + Ext.raise("Cannot create multiple instances of '" + me.$className + "'. " + "Use '" + me.$className + ".instance' to retrieve the singleton instance."); + } + me.registerEvents(); + Ext.event.publisher.Publisher.publishers[type] = me; + }, + /** + * Registers all {@link #handledEvents} in the + * {@link Ext.event.publisher.Publisher#publishersByEvent} map. + * @param {String[]} [events] optional events to register instead of handledEvents. + * @protected + */ + registerEvents: function(events) { + var me = this, + publishersByEvent = Ext.event.publisher.Publisher.publishersByEvent, + handledEvents = events || me.handledEvents, + ln = handledEvents.length, + eventName, i; + for (i = 0; i < ln; i++) { + eventName = handledEvents[i]; + me.handles[eventName] = 1; + publishersByEvent[eventName] = me; + } + }, + subscribe: function() { + Ext.raise("Ext.event.publisher.Publisher subclass '" + this.$className + '" has no subscribe method.'); + }, + unsubscribe: function() { + Ext.raise("Ext.event.publisher.Publisher subclass '" + this.$className + '" has no unsubscribe method.'); + }, + fire: function(element, eventName, args) { + var event; + if (element.hasListeners[eventName]) { + event = element.events[eventName]; + if (event) { + event.fire.apply(event, args); + } + } + } +}); + +/** + * @private + */ +Ext.define('Ext.util.Offset', { + /* Begin Definitions */ + statics: { + fromObject: function(obj) { + if (obj instanceof this) { + return obj; + } + if (typeof obj === 'number') { + return new this(obj, obj); + } + if (obj.length) { + return new this(obj[0], obj[1]); + } + return new this(obj.x, obj.y); + } + }, + /* End Definitions */ + constructor: function(x, y) { + this.x = (x != null && !isNaN(x)) ? x : 0; + this.y = (y != null && !isNaN(y)) ? y : 0; + return this; + }, + copy: function() { + return new Ext.util.Offset(this.x, this.y); + }, + copyFrom: function(p) { + this.x = p.x; + this.y = p.y; + }, + toString: function() { + return "Offset[" + this.x + "," + this.y + "]"; + }, + equals: function(offset) { + if (!(offset instanceof this.statics())) { + Ext.raise('Offset must be an instance of Ext.util.Offset'); + } + return (this.x === offset.x && this.y === offset.y); + }, + add: function(offset) { + if (!(offset instanceof this.statics())) { + Ext.raise('Offset must be an instance of Ext.util.Offset'); + } + this.x += offset.x; + this.y += offset.y; + }, + round: function(to) { + if (!isNaN(to)) { + var factor = Math.pow(10, to); + this.x = Math.round(this.x * factor) / factor; + this.y = Math.round(this.y * factor) / factor; + } else { + this.x = Math.round(this.x); + this.y = Math.round(this.y); + } + }, + isZero: function() { + return this.x === 0 && this.y === 0; + } +}); + +/** + * This class represents a rectangular region in X,Y space, and performs geometric + * transformations or tests upon the region. + * + * This class may be used to compare the document regions occupied by elements. + */ +Ext.define('Ext.util.Region', function() { + var ExtUtil = Ext.util, + constrainRe = /([^\?!]*)(!|\?)?$/, + alignRe = /^(?:(?:([trbl])(\d+))|(tl|t|tc|tr|l|c|r|bl|b|bc|br))(?:-(?:(?:([trbl])(\d+))|(tl|t|tc|tr|l|c|r|bl|b|bc|br)))?$/i, + // Each side has the first letter as the main align side, so [tlbr] + // The next optional component is a offset factor, so [tb] may be followed by [lr] and vice versa + // The offset factor may also be a number along that edge from 0 to 100. + // So 'tl-br' is equal to 't0-b100'. + // The offset factor defaults to 'c' or 50 meaning the 't-b' is equivalent to + // 't50-b50' or 'tc-bc' + LTROffsetFactors = { + l: 0, + r: 100, + t: 0, + b: 100, + c: 50 + }, + RTLOffsetFactors = { + l: 100, + r: 0, + t: 0, + b: 100, + c: 50 + }, + relativePositions = { + b: 0, + l: 1, + t: 2, + r: 3 + }, + alignMap = { + "tl-tr": "l0-r0", + "tl-r": "l0-r50", + "bl-r": "l100-r50", + "bl-br": "l100-r100", + "tr-tl": "r0-l0", + "tr-l": "r0-l50", + "br-l": "r100-l50", + "br-bl": "r100-l100" + }, + rtlAlignMap = { + "tl-tr": "r0-l0", + "tl-r": "r0-l50", + "bl-r": "r100-l50", + "bl-br": "r100-l100", + "tr-tl": "l0-r0", + "tr-l": "l0-r50", + "br-l": "l100-r50", + "br-bl": "l100-r100" + }, + adjustParams = [], + zeroOffset = new ExtUtil.Offset(0, 0), + parseRegion = function(box) { + var Region = ExtUtil.Region, + type = typeof box, + top, right, bottom, left; + if (box == null) { + return Region.EMPTY; + } + if (box.isRegion) { + return box; + } + if (box.isElement || box.nodeType === 1) { + return this.getRegion(box); + } + if (type === 'string') { + box = box.split(' '); + switch (box.length) { + case 1: + box[1] = box[2] = box[3] = box[0]; + break; + case 2: + box[2] = box[0]; + box[3] = box[1]; + break; + case 3: + box[3] = box[1]; + } + top = parseInt(box[0], 10) || 0; + right = parseInt(box[1], 10) || 0; + bottom = parseInt(box[2], 10) || 0; + left = parseInt(box[3], 10) || 0; + } else if (type === 'number') { + top = right = bottom = left = box; + } else if (typeof box.x === 'number') { + top = box.y; + left = box.x; + if (typeof box.right === 'number') { + right = box.right; + bottom = box.bottom; + } else { + right = left + box.width; + bottom = top + box.height; + } + } else { + Ext.raise('Not convertible to a Region: ' + box); + } + return new Region(top, right, bottom, left); + }, + magnitude = [ + -1, + 1, + 1, + -1 + ], + // Depending on the "relativePosition" which will be 0,1,2 or 3 for T,R,B,L + // extend the adjacent edge of the target to account for the offset. + // Also, shrink the adjacent edge to create overlap for the anchor to center in. + addAnchorOffset = function(target, anchorSize, relativePosition) { + // Expand the adjacent edge by the anchor HEIGHT. + if (relativePosition != null && anchorSize) { + adjustParams[0] = adjustParams[1] = adjustParams[2] = adjustParams[3] = 0; + adjustParams[relativePosition] = anchorSize.y * magnitude[relativePosition]; + target = ExtUtil.Region.from(target); + target.adjust.apply(target, adjustParams); + } + return target; + }, + // Shrink the adjacent edge to create overlap for the anchor to center in. + calculateAnchorPosition = function(target, result, relativePosition, anchorSize, inside) { + var anchorWidth = Math.ceil(anchorSize.x), + minOverlap = Math.ceil(anchorWidth / 2) + 3, + min, max, anchorPos, isBefore, overlapLine, x, y; + // target is out of bounds. We can't show an anchor + if (inside && !inside.intersect(target)) { + return; + } + if (relativePosition != null) { + // The result is to the left or right of the target + if (relativePosition & 1) { + // Not enough height to support a side anchor + if (result.getHeight() < anchorWidth + 4) { + return; + } + // + // +------+ <--- min + // | | + // | | + // +---------+ < | <-anchorMax + // | | +------+ + // | | + // | | + // | | + // | | + // | | +-------+ <--- max + // +---------+ < | <-anchorMin + // | | + // | | + // +-------+ + // + // Coerce the result's top to create enough overlap with target. + // Needs at least anchorWidth / 2 + 2 to look right. + min = target.top + minOverlap - result.height; + max = target.bottom - minOverlap - 1; + result.setPosition(result.x, Math.min(Math.max(result.y, min), max)); + // Now calculate the min & max permissible anchor top so that the + // anchor baseline clears the result's corner by ar least 2px. + min = result.top + 2; + max = result.bottom - (anchorWidth + 2); + isBefore = relativePosition === 3; + x = isBefore ? result.right : result.left; + overlapLine = new ExtUtil.Region(Math.max(result.top, target.top), x, Math.min(result.bottom, target.bottom), x); + // Align to the centre of the overlap line, wherever that may be + anchorPos = new ExtUtil.Region(0, 0, 0, 0).setWidth(anchorSize.y).setHeight(anchorWidth).alignTo({ + target: overlapLine, + align: isBefore ? 'l-r' : 'r-l', + overlap: true + }); + // Coerce the anchor into the bounds of the result. + anchorPos.setPosition(anchorPos.x, Math.min(Math.max(anchorPos.y, min), max)); + anchorPos.position = isBefore ? 'right' : 'left'; + } else // The result is above or below the target. + { + // Not enough width to support a top/bottom anchor + if (result.getWidth() < anchorWidth + 4) { + return; + } + // Coerce the result's left to create enough overlap with target. + // Needs at least anchorWidth / 2 + 2 to look right. + min = target.left + minOverlap - result.width; + max = target.right - minOverlap - 1; + result.setPosition(Math.min(Math.max(result.x, min), max), result.y); + // Now calculate the min & max permissible anchor left so that the + // anchor baseline clears the result's corner by ar least 2px. + min = result.left + 2; + max = result.right - (anchorWidth + 2); + // If there is not enough overlap. coerce the result to create enough overlap + isBefore = relativePosition === 0; + y = isBefore ? result.bottom : result.top; + overlapLine = new ExtUtil.Region(y, Math.min(result.right, target.right), y, Math.max(result.left, target.left)); + // Align to the centre of the overlap line, wherever that may be + anchorPos = new ExtUtil.Region(0, 0, 0, 0).setWidth(anchorWidth).setHeight(anchorSize.y).alignTo({ + target: overlapLine, + align: isBefore ? 't-b' : 'b-t', + overlap: true + }); + // Coerce the anchor into the bounds of the result. + anchorPos.setPosition(Math.min(Math.max(anchorPos.x, min), max), anchorPos.y); + anchorPos.position = isBefore ? 'bottom' : 'top'; + } + // If anchor is outside constrain region it cannot be shown. + if (inside && !inside.contains(anchorPos)) { + return; + } + result.anchor = anchorPos; + result.anchor.align = relativePosition; + } + }, + checkMinHeight = function(minHeight, result, target, inside) { + var newHeight; + if (minHeight && inside) { + // Overflows the bottom of the target + if (result.top >= target.bottom && result.bottom > inside.bottom) { + result.setHeight(Math.max(result.getHeight() + inside.bottom - result.bottom, minHeight)); + result.constrainHeight = true; + } + // Overflows the top of the target + else if (result.bottom <= target.top && result.top < inside.top) { + newHeight = Math.max(result.getHeight() + result.top - inside.top, minHeight); + result.adjust(result.getHeight() - newHeight); + result.constrainHeight = true; + } + // Just too high + else if (result.getHeight() > inside.getHeight()) { + result.setHeight(Math.max(minHeight, inside.getHeight())); + result.setPosition(result.x, 0); + result.constrainHeight = true; + } + } + }, + checkMinWidth = function(minWidth, result, target, inside) { + var newWidth; + if (minWidth && inside) { + // Overflows the right of the target + if (result.left >= target.right && result.right > inside.right) { + result.setWidth(Math.max(result.getWidth() + inside.right - result.right, minWidth)); + result.constrainWidth = true; + } + // Overflows the left of the target + else if (result.right <= target.left && result.left < inside.left) { + newWidth = Math.max(result.getWidth() + result.left - inside.left, minWidth); + result.adjust(0, 0, 0, result.getWidth() - newWidth); + result.constrainWidth = true; + } + // Just too wide + else if (result.getWidth() > inside.getWidth()) { + result.setWidth(Math.max(minWidth, inside.getWidth())); + result.setPosition(0, result.y); + result.constrainWidth = true; + } + } + }; + return { + requires: [ + 'Ext.util.Offset' + ], + isRegion: true, + statics: { + /** + * @static + * Retrieves an Ext.util.Region for a particular element. + * @param {String/HTMLElement/Ext.dom.Element} el An element ID, htmlElement or Ext.Element representing an element in the document. + * @return {Ext.util.Region} region + */ + getRegion: function(el) { + return Ext.fly(el).getRegion(); + }, + /** + * @static + * Creates a Region from a "box" Object which contains four numeric properties `top`, `right`, `bottom` and `left`. + * @param {Object} o An object with `top`, `right`, `bottom` and `left` properties. + * @return {Ext.util.Region} region The Region constructed based on the passed object + */ + from: function(o) { + return new this(o.top, o.right, o.bottom, o.left); + }, + /** + * This function converts a legacy alignment string such as 't-b' into a + * pair of edge, offset objects which describe the alignment points of + * the two regions. + * + * So tl-br becomes {myEdge:'t', offset:0}, {otherEdge:'b', offset:100} + * + * This not only allows more flexibility in the alignment possibilities, + * but it also resolves any ambiguity as to which two edges are desired + * to be adjacent if an anchor pointer is required. + * + * @param {String} align The align spec, eg `"tl-br"` + * @param {Boolean} [rtl] Pass `true` to use RTL calculations. + */ + getAlignInfo: function(align, rtl) { + if (typeof align === 'object') { + return align; + } + align = align ? ((align.indexOf('-') < 0) ? 'tl-' + align : align) : 'tl-bl'; + // Snip any constraint modifier off so that we can match the alignMaps + constrain = constrainRe.exec(align); + align = constrain[1]; + // Convert left to right alignments which are specified using top/bottom corner definitions. + align = (rtl ? rtlAlignMap : alignMap)[align] || align; + var offsetFactors = rtl ? RTLOffsetFactors : LTROffsetFactors, + constrain, + parts = alignRe.exec(align), + result; + if (!parts) { + Ext.raise({ + sourceClass: 'Ext.util.Region', + sourceMethod: 'getAlignInfo', + position: align, + msg: 'Attempted to align an element with an invalid position: "' + align + '"' + }); + } + result = { + myEdge: parts[1], + myOffset: parts[2], + otherEdge: parts[4], + otherOffset: parts[5], + constrain: constrain[2] + }; + // t-l, b-r etc. + // Convert points to edge and offset. + if (parts[3]) { + result.myEdge = parts[3][0]; + result.myOffset = offsetFactors[parts[3][1]]; + if (result.myOffset == null) { + result.myOffset = 50; + } + } + if (parts[6]) { + result.otherEdge = parts[6][0]; + result.otherOffset = offsetFactors[parts[6][1]]; + if (result.otherOffset == null) { + result.otherOffset = 50; + } + } + // TOP=0, RIGHT=1, BOTTOM=2, LEFT=3, INSIDE=undefined + result.position = relativePositions[result.myEdge]; + return result; + } + }, + /* End Definitions */ + /** + * Creates a region from the bounding sides. + * @param {Number} top The topmost pixel of the Region. + * @param {Number} right The rightmost pixel of the Region. + * @param {Number} bottom The bottom pixel of the Region. + * @param {Number} left The leftmost pixel of the Region. + */ + constructor: function(top, right, bottom, left) { + var me = this; + me.y = me.top = me[1] = top; + me.right = right; + me.bottom = bottom; + me.x = me.left = me[0] = left; + me.height = me.bottom - me.top; + me.width = me.right - me.left; + }, + /** + * Translates this Region to the specified position + * @param {Number} x The new X position. + * @param {Number} y The new Y position. + * @returns {Ext.util.Region} This region after translation. + */ + setPosition: function(x, y) { + // Allow [x, y] + if (arguments.length === 1) { + y = x[1]; + x = x[0]; + } + return this.translateBy(x - this.x, y - this.y); + }, + /** + * Checks if this region completely contains the region or point that is passed in. + * @param {Ext.util.Region/Ext.util.Point} region + * @return {Boolean} + */ + contains: function(region) { + var me = this; + return (region.x >= me.x && (region.right || region.x) <= me.right && region.y >= me.y && (region.bottom || region.y) <= me.bottom); + }, + /** + * Checks if this region intersects the region passed in. + * @param {Ext.util.Region} region + * @return {Ext.util.Region/Boolean} Returns the intersected region or false if there is no intersection. + */ + intersect: function(region) { + var me = this, + t = Math.max(me.y, region.y), + r = Math.min(me.right, region.right), + b = Math.min(me.bottom, region.bottom), + l = Math.max(me.x, region.x); + if (b > t && r > l) { + return new this.self(t, r, b, l); + } else { + return false; + } + }, + /** + * Returns the smallest region that contains the current AND targetRegion. + * @param {Ext.util.Region} region + * @return {Ext.util.Region} a new region + */ + union: function(region) { + var me = this, + t = Math.min(me.y, region.y), + r = Math.max(me.right, region.right), + b = Math.max(me.bottom, region.bottom), + l = Math.min(me.x, region.x); + return new this.self(t, r, b, l); + }, + /** + * Modifies the current region to be constrained to the targetRegion. + * @param {Ext.util.Region} targetRegion + * @return {Ext.util.Region} this + */ + constrainTo: function(targetRegion) { + var me = this, + constrain = Ext.Number.constrain; + me.top = me.y = constrain(me.top, targetRegion.y, targetRegion.bottom); + me.bottom = constrain(me.bottom, targetRegion.y, targetRegion.bottom); + me.left = me.x = constrain(me.left, targetRegion.x, targetRegion.right); + me.right = constrain(me.right, targetRegion.x, targetRegion.right); + me.height = me.bottom - me.top; + me.width = me.right - me.left; + return me; + }, + /** + * Modifies the current region to be adjusted by offsets. + * @param {Number} top Top offset + * @param {Number} right Right offset + * @param {Number} bottom Bottom offset + * @param {Number} left Left offset + * @return {Ext.util.Region} this + */ + adjust: function(top, right, bottom, left) { + var me = this; + me.top = me.y += top || 0; + me.left = me.x += left || 0; + me.right += right || 0; + me.bottom += bottom || 0; + me.height = me.bottom - me.top; + me.width = me.right - me.left; + return me; + }, + /** + * Get the offset amount of a point outside the region + * @param {String} [axis] + * @param {Ext.util.Point} [p] the point + * @return {Ext.util.Offset} + */ + getOutOfBoundOffset: function(axis, p) { + if (!Ext.isObject(axis)) { + if (axis === 'x') { + return this.getOutOfBoundOffsetX(p); + } else { + return this.getOutOfBoundOffsetY(p); + } + } else { + p = axis; + var d = new ExtUtil.Offset(); + d.x = this.getOutOfBoundOffsetX(p.x); + d.y = this.getOutOfBoundOffsetY(p.y); + return d; + } + }, + /** + * Get the offset amount on the x-axis + * @param {Number} p the offset + * @return {Number} + */ + getOutOfBoundOffsetX: function(p) { + if (p <= this.x) { + return this.x - p; + } else if (p >= this.right) { + return this.right - p; + } + return 0; + }, + /** + * Get the offset amount on the y-axis + * @param {Number} p the offset + * @return {Number} + */ + getOutOfBoundOffsetY: function(p) { + if (p <= this.y) { + return this.y - p; + } else if (p >= this.bottom) { + return this.bottom - p; + } + return 0; + }, + /** + * Check whether the point / offset is out of bound + * @param {String} [axis] + * @param {Ext.util.Point/Number} [p] the point / offset + * @return {Boolean} + */ + isOutOfBound: function(axis, p) { + if (!Ext.isObject(axis)) { + if (axis === 'x') { + return this.isOutOfBoundX(p); + } else { + return this.isOutOfBoundY(p); + } + } else { + p = axis; + return (this.isOutOfBoundX(p.x) || this.isOutOfBoundY(p.y)); + } + }, + /** + * Check whether the offset is out of bound in the x-axis + * @param {Number} p the offset + * @return {Boolean} + */ + isOutOfBoundX: function(p) { + return (p < this.x || p > this.right); + }, + /** + * Check whether the offset is out of bound in the y-axis + * @param {Number} p the offset + * @return {Boolean} + */ + isOutOfBoundY: function(p) { + return (p < this.y || p > this.bottom); + }, + /** + * Restrict a point within the region by a certain factor. + * @param {String} [axis] + * @param {Ext.util.Point/Ext.util.Offset/Object} [p] + * @param {Number} [factor] + * @return {Ext.util.Point/Ext.util.Offset/Object/Number} + * @private + */ + restrict: function(axis, p, factor) { + if (Ext.isObject(axis)) { + var newP; + factor = p; + p = axis; + if (p.copy) { + newP = p.copy(); + } else { + newP = { + x: p.x, + y: p.y + }; + } + newP.x = this.restrictX(p.x, factor); + newP.y = this.restrictY(p.y, factor); + return newP; + } else { + if (axis === 'x') { + return this.restrictX(p, factor); + } else { + return this.restrictY(p, factor); + } + } + }, + /** + * Restrict an offset within the region by a certain factor, on the x-axis + * @param {Number} p + * @param {Number} [factor=1] The factor. + * @return {Number} + * @private + */ + restrictX: function(p, factor) { + if (!factor) { + factor = 1; + } + if (p <= this.x) { + p -= (p - this.x) * factor; + } else if (p >= this.right) { + p -= (p - this.right) * factor; + } + return p; + }, + /** + * Restrict an offset within the region by a certain factor, on the y-axis + * @param {Number} p + * @param {Number} [factor] The factor, defaults to 1 + * @return {Number} + * @private + */ + restrictY: function(p, factor) { + if (!factor) { + factor = 1; + } + if (p <= this.y) { + p -= (p - this.y) * factor; + } else if (p >= this.bottom) { + p -= (p - this.bottom) * factor; + } + return p; + }, + /** + * Returns the Region to which this rectangle should be moved in order to + * have the desired alignment with the specified target while remaining within the + * constraint. + * + * The `align` option can be one of these forms: + * + * - **Blank**: Defaults to aligning the region's top-left corner to the target's + * bottom-left corner ("tl-bl"). + * - **Two anchors**: If two values from the table below are passed separated by a dash, + * the first value is used as this region's anchor point, and the second value is + * used as the target's anchor point. + * - **One anchor**: The passed anchor position is used as the target's anchor point. + * This region will position its top-left corner (tl) to that point. + * - **Two edge/offset descriptors:** An edge/offset descriptor is an edge initial + * (`t`/`r`/`b`/`l`) followed by a percentage along that side. This describes a + * point to align with a similar point in the target. So `'t0-b0'` would be + * the same as `'tl-bl'`, `'l0-r50'` would place the top left corner of this item + * halfway down the right edge of the target item. This allows more flexibility + * and also describes which two edges are considered adjacent when positioning an anchor. + * + * If the `inside` option is passed, the Region will attempt to align as specified, + * but the position will be adjusted to constrain to the `inside` Region if necessary. + * Note that the Region being aligned might be swapped to align to a different position + * than that specified in order to enforce the constraints. Following are all of the + * supported anchor positions: + * + * Value Description + * ----- ----------------------------- + * tl The top left corner + * t The center of the top edge + * tr The top right corner + * l The center of the left edge + * c The center + * r The center of the right edge + * bl The bottom left corner + * b The center of the bottom edge + * br The bottom right corner + * + * Example Usage: + * + * var xy = comp.getRegion().alignTo({ + * align: 't-b', // align comp's top/center to el's bottom/center + * target: el.getRegion(), + * anchorSize: new Ext.util.Point(10, 10), + * inside: new Ext.util.Region(0, Ext.Element.getViewportWidth(), Ext.Element.getViewportHeight(), 0) + * }); + * + * @param {Object} options The alignment options. + * @param {Ext.util.Region} options.target The rectangle to which this rectangle + * should align. + * @param {String} [options.align=tl-bl] The alignment descriptor for positioning this + * rectangle with respect to the `target`. See {@link Ext.util.Positionable#alignTo}. + * Note that if the requested alignment results in violation of the `inside` constraint, + * the result will be flipped align to the closest edge which conforms to the constraint. + * + * @param {Array/Ext.util.Position} [options.position] The position at which to place the + * resulting region before being excluded from the target area and aligned to the closest + * edge which allows conformity with any passed `inside` option. Used instead of the `align` option. + * @param {Ext.util.Offset/Number[]} [options.offset] An offset by which to adjust the result. + * @param {Ext.util.Offset/Number[]} [options.anchorSize] The width and height of any external anchor + * element. This is used to calculate the true bounds of the Region inclusive of the anchor. + * The `x` dimension is the height of the arrow in all orientations, and the `y` dimension + * is the width of the baseline of the arrow in all dimensions. + * If this option is used, and the returned region successfully clears the + * bounds of the target, then the anchor region will be returned in the return value + * as the `anchor` property. This will in turn have a `position` property which will + * be `'top'`, `'left`, `'right'`, or `'bottom'`. + * @param {Boolean} [options.overlap] Pass `true` to allow this rectangle to overlap + * the target. + * @param {Boolean} [options.rtl] Pass `true` to swap left/right alignment. + * @param {Ext.util.Region/Ext.dom.Element} [options.inside] The rectangle to + * which this rectangle is constrained. + * @param {Number} [options.minHeight] Used when this Region is to be aligned directly + * below or above the target. Gives the option to reduce the height to fit in the + * available space. + * @param {Boolean} [options.axisLock] If `true`, then fallback on constraint violation will + * only take place along the major align axis. That is, if `align: "l-r"` is being used, and + * `axisLock: true` is used, then if constraints fail, only fallback to `r-l` is considered. + * @return {Ext.util.Region} The Region that will align this rectangle. Note that if + * a `minHeight` option was passed, and alignment is either above or below the target, + * the Region might be reduced to fit within the space. + */ + alignTo: function(options) { + var me = this, + Region = me.self, + Offset = ExtUtil.Offset, + Element = Ext.Element, + target = parseRegion(options.target), + targetPlusAnchorOffset, + rtl = options.rtl, + overlap = options.overlap, + align = options.align, + anchorSize = options.anchorSize, + offset = options.offset, + inside = options.inside, + position = options.position, + allowXTranslate = options.allowXTranslate, + allowYTranslate = options.allowYTranslate, + wasConstrained, result, initialPosition, constrainedPosition; + if (offset) { + offset = Offset.fromObject(offset); + if (!(offset instanceof Offset)) { + Ext.raise('offset option must be an Ext.util.Offset'); + } + } + if (anchorSize) { + anchorSize = Offset.fromObject(anchorSize); + if (!(anchorSize instanceof Offset)) { + Ext.raise('anchorSize option must be an Ext.util.Offset'); + } + } + if (inside && !inside.isRegion) { + if (Ext.getDom(inside) === document.body) { + inside = new Region(0, Element.getDocumentWidth(), Element.getDocumentHeight(), 0); + } else { + inside = Ext.fly(inside).getRegion(); + } + } + // Position the region using an exact position. + // Our purpose is then to constrain within the inside + // Region, while probably not occluding the target. + if (position) { + if (position.length === 2) { + position = new ExtUtil.Point(position[0], position[1]); + } + // Calculate the unconstrained position. + result = new Region().copyFrom(me).setPosition(position.x, position.y); + } else { + // Convert string align spec to informational object + align = me.getAlignInfo(align, rtl); + // target is out of bounds. + // Move it so that it's 1px inside to that the alignment points + if (inside) { + if (target.x >= inside.right) { + target.setPosition(inside.right - 1, target.y); + if (align.position !== 3) { + align = me.getAlignInfo('r-l', rtl); + } + } else if (target.right < inside.x) { + target.setPosition(inside.x - target.getWidth() + 1, target.y); + if (align.position !== 1) { + align = me.getAlignInfo('l-r', rtl); + } + } + if (target.y >= inside.bottom) { + target.setPosition(target.x, inside.bottom - 1); + if (align.position !== 0) { + align = me.getAlignInfo('b-t', rtl); + } + } else if (target.bottom < inside.y) { + target.setPosition(target.x, inside.y - target.getHeight() + 1); + if (align.position !== 2) { + align = me.getAlignInfo('t-b', rtl); + } + } + } + // Adjust the adjacent edge to account for the anchor height. + targetPlusAnchorOffset = anchorSize ? addAnchorOffset(target, anchorSize, align.position) : target; + // Start with requested position. + result = Region.from(me).translateBy(me.getAlignToVector(targetPlusAnchorOffset, align)); + // If they ASKED for it to intersect (eg: c-c, tl-c). we must honour that, and not exclude it. + overlap = !!result.intersect(targetPlusAnchorOffset); + if (offset && (overlap || !anchorSize)) { + result.translateBy(offset); + } + // Calculate the anchor position. + // This also forces the adjacent edges to overlap enough to create space for the anchor arrow. + if (anchorSize) { + calculateAnchorPosition(target, result, align.position, anchorSize, inside); + } + } + // If we are constraining Region... + if (inside) { + initialPosition = result.copy(); + // Constrain to within left boundary + if (result.left < inside.left) { + result.translateBy(inside.left - result.left, 0); + wasConstrained = true; + } + // If it overflows right, and there is space to move it left, then do so. + if (result.right > inside.right && result.left > inside.left) { + result.translateBy(inside.right - result.right, 0); + wasConstrained = true; + } + // Constrain to within top boundary + if (result.top < inside.top) { + result.translateBy(0, inside.top - result.top); + wasConstrained = true; + } + // If it overflows bottom, and there is space to move it up, then do so. + if (result.bottom > inside.bottom && result.top > inside.top) { + result.translateBy(0, inside.bottom - result.bottom); + wasConstrained = true; + } + // If we've budged the result to within the constrain bounds, + // ensure the result region does not overlay the target + if (wasConstrained && !overlap) { + // Recalculate it. We must return null if anchoring is not possible. + result.anchor = null; + // axisLock means that only flipping in the align axis is allowed, not fallback + // to all other sides. + // + // That is, if align is l-r, and the result won't fit, it only + // falls back to r-l. + // + // This will be used for BoundLists which must only flip from t0-b0 to b0-t0 + if (options.axisLock) { + if (align.position & 1) { + allowYTranslate = false; + } else { + allowXTranslate = false; + } + } + // If using an [X,Y] position, then only total occlusion causes exclusion + if (position) { + if (result.contains(position)) { + position.exclude(result, { + inside: inside, + centerOnSideChange: false + }); + } + } else // If edge aligning, we must completely exclude the region + { + constrainedPosition = result.copy(); + if (result.intersect(targetPlusAnchorOffset)) { + // This will also exclude any additional anchor even if the region itself + // does not intersect. + align.position = target.exclude(result, { + initialPosition: initialPosition, + defaultPosition: align.position, + inside: inside, + minHeight: options.minHeight, + minWidth: options.minWidth, + allowX: allowXTranslate, + allowY: allowYTranslate, + offset: offset, + anchorHeight: anchorSize ? anchorSize.y : 0, + centerOnSideChange: !!anchorSize + }); + } else if (options.minWidth && result.getWidth() > inside.getWidth()) { + result.setPosition(0, result.y); + result.setWidth(Math.max(inside.getWidth(), options.minWidth)); + result.constrainWidth = true; + } else if (options.minHeight && result.getHeight() > inside.getHeight()) { + result.setPosition(result.x, 0); + result.setHeight(Math.max(inside.getHeight(), options.minHeight)); + result.constrainHeight = true; + } + result.align = align; + if (inside.contains(result)) { + // Calculate the anchor position. + // This also forces the adjacent edges to overlap enough to create space for the anchor arrow. + if (anchorSize) { + calculateAnchorPosition(target, result, align.position, anchorSize, inside); + } + } else // We tried everything, but couldn't fit in the "inside" region. + // Fall back to the constrained position overlapping the target. + // Usually happens on a phone where there's not enough space to edge-align + // and insist on no overlapping of align target . + { + result = constrainedPosition; + } + } + } + } + return result; + }, + /** + * This method pushes the "other" Region out of this region via the shortest + * translation. If an "inside" Region is passed, the exclusion also honours + * that constraint. + * @param {Region} other The Region to move so that it does not intersect this Region. + * @param {Object} options Object of options passed to exclude. + * @param {Region} options.inside A Region into which the other Region must be constrained. + * @param {Number} [options.minHeight] If passed, indicates that the height may be reduced up + * to a point to fit the "other" region below or above the target but within the "inside" Region. + * @param {Boolean} [options.allowX=true] Pass `false` to disallow translation along the X axis. + * @param {Boolean} [options.allowY=true] Pass `false` to disallow translation along the Y axis. + * @return {Number} The edge it is now aligned to, 0=top, 1=right, 2=bottom, 3=left. + */ + exclude: function(other, options) { + options = options || {}; + var me = this, + initialPosition = options.initialPosition || other, + inside = options.inside, + defaultPosition = options.defaultPosition, + centerOnSideChange = options.centerOnSideChange, + minHeight = options.minHeight, + minWidth = options.minWidth, + allowX = options.allowX !== false, + allowY = options.allowY !== false, + anchorHeight = options.anchorHeight, + offset = options.offset, + translations = [], + testRegion, t, i, sizeConstrainedSolution, leastBadSolution, intersection, result; + // Create adjustments for each dimension so we can also exclude any anchor + if (!offset) { + offset = zeroOffset; + } + // Calculate vectors to move the "other" region by to fully clear this region. + // Store the total moved distance, (element [4]) as the distance from the initially + // desired position, not the constrained, overlapped position. + if (allowY) { + translations.push([ + 0, + me.top - other.bottom - anchorHeight + offset.y, + 'b-t', + 0, + Math.abs(me.top - initialPosition.bottom - anchorHeight + offset.y) + ]); + translations.push([ + 0, + me.bottom - other.top + anchorHeight + offset.y, + 't-b', + 2, + Math.abs(me.bottom - initialPosition.top + anchorHeight + offset.y) + ]); + } else { + centerOnSideChange = false; + } + if (allowX) { + translations.push([ + me.left - other.right - anchorHeight + offset.x, + 0, + 'r-l', + 3, + Math.abs(me.left - initialPosition.right - anchorHeight + offset.x) + ]); + translations.push([ + me.right - other.left + anchorHeight + offset.x, + 0, + 'l-r', + 1, + Math.abs(me.right - initialPosition.left + anchorHeight + offset.x) + ]); + } else { + centerOnSideChange = false; + } + // Sort the exclusion vectors into order, shortest first + Ext.Array.sort(translations, function(l, r) { + var result = l[4] - r[4]; + // If equidistant, prefer the translation which moves to the defaultPosition + if (!result) { + if (l[3] === defaultPosition) { + return -1; + } + if (r[3] === defaultPosition) { + return 1; + } + } + return result; + }); + // We might have to fall back through the choices of direction + // until we find one which doesn't violate the constraints. + if (inside) { + for (i = 0; i < translations.length; i++) { + t = translations[i]; + testRegion = ExtUtil.Region.from(other); + testRegion.translateBy.apply(testRegion, t); + // When we find a translation that satisfies the constraint, we're done + if (inside.contains(testRegion)) { + other.copyFrom(testRegion); + result = { + align: t[2], + position: t[3], + distance: t[4] + }; + break; + } + // If we are directly above or below and we are allowed to shrink the + // height, and it's too high, then calculate a height constrained solution + // to which we can fall back if no translations are fully successful. + if (minHeight) { + checkMinHeight(minHeight, testRegion, me, inside); + if (inside.contains(testRegion)) { + if (!sizeConstrainedSolution || testRegion.getArea() > sizeConstrainedSolution.region.getArea()) { + sizeConstrainedSolution = { + region: testRegion, + align: t[2], + position: t[3], + distance: t[4] + }; + } + } + } + if (minWidth) { + checkMinWidth(minWidth, testRegion, me, inside); + if (inside.contains(testRegion)) { + if (!sizeConstrainedSolution || testRegion.getArea() > sizeConstrainedSolution.region.getArea()) { + sizeConstrainedSolution = { + region: testRegion, + align: t[2], + position: t[3], + distance: t[4] + }; + } + } + } + // If all else fails, keep track of the translation which yields the largest intersection + // with the "inside" region. If there's no translation which satisfies the constraint, + // use this least bad one. + intersection = inside.intersect(testRegion); + if (intersection) { + intersection = intersection.getArea(); + if (!leastBadSolution || (intersection && leastBadSolution.area < intersection)) { + leastBadSolution = { + region: testRegion, + align: t[2], + position: t[3], + distance: t[4], + area: intersection + }; + } + } + } + if (!result) { + // Only constrain height if other translations fail. + if (sizeConstrainedSolution) { + other.copyFrom(sizeConstrainedSolution.region); + result = sizeConstrainedSolution; + other.constrainWidth = sizeConstrainedSolution.region.constrainWidth; + other.constrainHeight = sizeConstrainedSolution.region.constrainHeight; + } + // Only use the least bad failed solution as a last resort. + else if (leastBadSolution) { + other.copyFrom(leastBadSolution.region); + result = leastBadSolution; + } + } + if (result) { + // The exclude switched align axis (t/b to l/r), flip it to a center align on + // the new side. + if ((result.position & 1) !== (defaultPosition & 1)) { + if (result.distance && centerOnSideChange) { + t = other.alignTo({ + align: result.align, + target: me, + anchorSize: anchorHeight, + offset: offset, + axisLock: true, + inside: inside, + minHeight: options.minHeight, + minWidth: options.minWidth + }); + if (inside.contains(t)) { + other.setPosition(t.x, t.y); + } + } + } + return result.position; + } + } else // No external constraint + { + // Move by the shortest path + other.translateBy.apply(other, translations[0]); + return translations[0][3]; + } + return defaultPosition; + }, + getAlignToXY: function(target, align, rtl) { + var alignVector = this.getAlignToVector(target, align, rtl); + return [ + this.x + alignVector[0], + this.y + alignVector[1] + ]; + }, + getAnchorPoint: function(align, rtl) { + align = (typeof align === 'string') ? this.getAlignInfo(align + '-tl', rtl) : align; + return this['getAnchorPoint_' + align.myEdge](align.myOffset); + }, + getAlignToVector: function(target, align, rtl) { + align = (typeof align === 'string') ? this.getAlignInfo(align, rtl) : align; + var myAnchorPoint = this['getAnchorPoint_' + align.myEdge](align.myOffset), + targetAnchorPoint = target['getAnchorPoint_' + align.otherEdge](align.otherOffset); + return [ + targetAnchorPoint[0] - myAnchorPoint[0], + targetAnchorPoint[1] - myAnchorPoint[1] + ]; + }, + getAnchorPoint_t: function(offset) { + return [ + this.x + Math.round(this.getWidth() * (offset / 100)), + this.y + ]; + }, + getAnchorPoint_b: function(offset) { + return [ + this.x + Math.round(this.getWidth() * (offset / 100)), + this.bottom + ]; + }, + getAnchorPoint_l: function(offset) { + return [ + this.x, + this.y + Math.round(this.getHeight() * (offset / 100)) + ]; + }, + getAnchorPoint_r: function(offset) { + return [ + this.right, + this.y + Math.round(this.getHeight() * (offset / 100)) + ]; + }, + getAnchorPoint_c: function() { + return [ + this.x + Math.round(this.getWidth() / 2), + this.y + Math.round(this.getHeight() / 2) + ]; + }, + getCenter: function() { + return [ + this.x + this.width / 2, + this.y + this.height / 2 + ]; + }, + getHeight: function() { + return this.bottom - this.y; + }, + getWidth: function() { + return this.right - this.x; + }, + getArea: function() { + return this.getHeight() * this.getWidth(); + }, + setHeight: function(h) { + this.height = h; + this.bottom = this.top + h; + return this; + }, + setWidth: function(w) { + this.width = w; + this.right = this.left + w; + return this; + }, + /** + * Get the width / height of this region + * @return {Object} an object with width and height properties + * @private + */ + getSize: function() { + return { + width: this.right - this.x, + height: this.bottom - this.y + }; + }, + setSize: function(w, h) { + if (h === undefined) { + h = w; + } + this.setWidth(w); + return this.setHeight(h); + }, + /** + * Create a copy of this Region. + * @return {Ext.util.Region} + */ + copy: function() { + return new this.self(this.y, this.right, this.bottom, this.x); + }, + /** + * Copy the values of another Region to this Region + * @param {Ext.util.Region} p The region to copy from. + * @return {Ext.util.Region} This Region + */ + copyFrom: function(p) { + var me = this; + me.top = me.y = me[1] = p.y; + me.right = p.right; + me.bottom = p.bottom; + me.left = me.x = me[0] = p.x; + return me; + }, + /* + * Dump this to an eye-friendly string, great for debugging + * @return {String} + */ + toString: function() { + return "Region[" + this.top + "," + this.right + "," + this.bottom + "," + this.left + "]"; + }, + /** + * Translate this Region by the given offset amount + * @param {Ext.util.Offset/Object} x Object containing the `x` and `y` properties. + * Or the x value is using the two argument form. + * @param {Number} y The y value unless using an Offset object. + * @return {Ext.util.Region} this This Region + */ + translateBy: function(x, y) { + if (x.length) { + y = x[1]; + x = x[0]; + } else if (arguments.length === 1) { + y = x.y; + x = x.x; + } + var me = this; + me.top = me.y += y; + me.right += x; + me.bottom += y; + me.left = me.x += x; + return me; + }, + /** + * Round all the properties of this region + * @return {Ext.util.Region} this This Region + */ + round: function() { + var me = this; + me.top = me.y = Math.round(me.y); + me.right = Math.round(me.right); + me.bottom = Math.round(me.bottom); + me.left = me.x = Math.round(me.x); + return me; + }, + /** + * Check whether this region is equivalent to the given region + * @param {Ext.util.Region} region The region to compare with + * @return {Boolean} + */ + equals: function(region) { + return (this.top === region.top && this.right === region.right && this.bottom === region.bottom && this.left === region.left); + }, + /** + * Returns the offsets of this region from the passed region or point. + * @param {Ext.util.Region/Ext.util.Point} offsetsTo The region or point to get get + * the offsets from. + * @return {Object} The XY page offsets + * @return {Number} return.x The x offset + * @return {Number} return.y The y offset + */ + getOffsetsTo: function(offsetsTo) { + return { + x: this.x - offsetsTo.x, + y: this.y - offsetsTo.y + }; + }, + highlight: function() { + var highlightEl = Ext.getBody().createChild({ + style: 'background-color:#52a0db;opacity:0.4;position:absolute;z-index:9999999' + }); + highlightEl.setBox(this); + Ext.defer(function() { + highlightEl.destroy(); + }, 5000); + return highlightEl; + } + }; +}, function(Region) { + Region.prototype.getAlignInfo = Region.getAlignInfo; + Region.EMPTY = new Region(0, 0, 0, 0); + if (Object.freeze) { + Object.freeze(Region.EMPTY); + } +}); + +/** + * Represents a 2D point with x and y properties, useful for comparison and instantiation + * from an event: + * + * var point = Ext.util.Point.fromEvent(e); + */ +Ext.define('Ext.util.Point', { + extend: 'Ext.util.Region', + isPoint: true, + radianToDegreeConstant: 180 / Math.PI, + origin: { + x: 0, + y: 0 + }, + statics: { + /** + * Returns a new instance of {@link Ext.util.Point} based on the `pageX` / `pageY` values of the given event. + * @static + * @param {Event} e The event. + * @return {Ext.util.Point} + */ + fromEvent: function(e) { + var changedTouches = e.changedTouches, + touch = (changedTouches && changedTouches.length > 0) ? changedTouches[0] : e; + return this.fromTouch(touch); + }, + /** + * Returns a new instance of {@link Ext.util.Point} based on the `pageX` / `pageY` values of the given touch. + * @static + * @param {Event} touch + * @return {Ext.util.Point} + */ + fromTouch: function(touch) { + return new this(touch.pageX, touch.pageY); + }, + /** + * Returns a new point from an object that has `x` and `y` properties, if that object is not an instance + * of {@link Ext.util.Point}. Otherwise, returns the given point itself. + * @param {Object} object + * @return {Ext.util.Point} + */ + from: function(object) { + if (!object) { + return new this(0, 0); + } + if (!(object instanceof this)) { + return new this(object.x, object.y); + } + return object; + } + }, + /** + * Creates point on 2D plane. + * @param {Number} [x=0] X coordinate. + * @param {Number} [y=0] Y coordinate. + */ + constructor: function(x, y) { + if (x == null) { + x = 0; + } + if (y == null) { + y = 0; + } + this.callParent([ + y, + x, + y, + x + ]); + }, + /** + * Copy a new instance of this point. + * @return {Ext.util.Point} The new point. + */ + clone: function() { + return new this.self(this.x, this.y); + }, + /** + * Clones this Point. + * @deprecated 2.0.0 Please use {@link #clone} instead. + * @return {Ext.util.Point} The new point. + */ + copy: function() { + return this.clone.apply(this, arguments); + }, + /** + * Copy the `x` and `y` values of another point / object to this point itself. + * @param {Ext.util.Point/Object} point. + * @return {Ext.util.Point} This point. + */ + copyFrom: function(point) { + this.x = point.x; + this.y = point.y; + return this; + }, + /** + * Returns a human-eye-friendly string that represents this point, + * useful for debugging. + * @return {String} For example `Point[12,8]`. + */ + toString: function() { + return "Point[" + this.x + "," + this.y + "]"; + }, + /** + * Compare this point and another point. + * @param {Ext.util.Point/Object} point The point to compare with, either an instance + * of {@link Ext.util.Point} or an object with `x` and `y` properties. + * @return {Boolean} Returns whether they are equivalent. + */ + equals: function(point) { + return (this.x === point.x && this.y === point.y); + }, + /** + * Returns `true` if the passed point is within a certain distance of this point. + * @param {Ext.util.Point/Object} point The point to check with, either an instance + * of {@link Ext.util.Point} or an object with `x` and `y` properties. + * @param {Object/Number} threshold Can be either an object with `x` and `y` properties or a number. + * @return {Boolean} + */ + isCloseTo: function(point, threshold) { + if (typeof threshold == 'number') { + return this.getDistanceTo(point) <= threshold; + } + var x = point.x, + y = point.y, + thresholdX = threshold.x, + thresholdY = threshold.y; + return (this.x <= x + thresholdX && this.x >= x - thresholdX && this.y <= y + thresholdY && this.y >= y - thresholdY); + }, + /** + * Returns `true` if this point is close to another one. + * @deprecated 2.0.0 Please use {@link #isCloseTo} instead. + * @return {Boolean} + */ + isWithin: function() { + return this.isCloseTo.apply(this, arguments); + }, + /** + * Determins whether this Point contained by the passed Region, Component or element. + * @param {Ext.util.Region/Ext.Component/Ext.dom.Element/HTMLElement} region + * The rectangle to check that this Point is within. + * @return {Boolean} + */ + isContainedBy: function(region) { + if (!(region instanceof Ext.util.Region)) { + region = Ext.get(region.el || region).getRegion(); + } + return region.contains(this); + }, + /** + * Compare this point with another point when the `x` and `y` values of both points are rounded. For example: + * [100.3,199.8] will equals to [100, 200]. + * @param {Ext.util.Point/Object} point The point to compare with, either an instance + * of Ext.util.Point or an object with `x` and `y` properties. + * @return {Boolean} + */ + roundedEquals: function(point) { + if (!point || typeof point !== 'object') { + point = this.origin; + } + return (Math.round(this.x) === Math.round(point.x) && Math.round(this.y) === Math.round(point.y)); + }, + getDistanceTo: function(point) { + if (!point || typeof point !== 'object') { + point = this.origin; + } + var deltaX = this.x - point.x, + deltaY = this.y - point.y; + return Math.sqrt(deltaX * deltaX + deltaY * deltaY); + }, + getAngleTo: function(point) { + if (!point || typeof point !== 'object') { + point = this.origin; + } + var deltaX = this.x - point.x, + deltaY = this.y - point.y; + return Math.atan2(deltaY, deltaX) * this.radianToDegreeConstant; + } +}, function() { + /** + * @method translate + * @member Ext.util.Point + * Alias for {@link #translateBy} + * @inheritdoc Ext.util.Region#method-translateBy + */ + this.prototype.translate = this.prototype.translateBy; +}); + +/** + * Just as {@link Ext.dom.Element} wraps around a native DOM node, {@link Ext.event.Event} wraps the browser's native + * event-object normalizing cross-browser differences such as mechanisms to stop event-propagation along with a method + * to prevent default actions from taking place. + * + * Here is a simple example of how you use it: + * + * @example + * var container = Ext.create('Ext.Container', { + * layout: 'fit', + * renderTo: Ext.getBody(), + * items: [{ + * id: 'logger', + * html: 'Click somewhere!', + * padding: 5 + * }] + * }); + * + * container.getEl().on({ + * click: function(e, node) { + * var string = ''; + * + * string += 'You clicked at: { x: ' + e.pageX + ', y: ' + e.pageY + ' } (e.pageX & e.pageY)'; + * string += '
'; + * string += 'The HTMLElement you clicked has the className of: ' + e.target.className + ' (e.target)'; + * string += '
'; + * string += 'The HTMLElement which has the listener has a className of: ' + e.currentTarget.className + ' (e.currentTarget)'; + * + * Ext.getCmp('logger').setHtml(string); + * } + * }); + * + * ## Recognizers + * + * Ext JS includes many default event recognizers to know when a user interacts with the application. + * + * For a full list of default recognizers, and more information, please view the {@link Ext.event.gesture.Recognizer} documentation. + * + * This class also provides a set of constants for use with key events. These are useful + * for determining if a specific key was pressed, and are available both on instances, + * and as static properties of the class. The following two statements are equivalent: + * + * if (e.getKey() === Ext.event.Event.TAB) { + * // tab key was pressed + * } + * + * if (e.getKey() === e.TAB) { + * // tab key was pressed + * } + */ +Ext.define('Ext.event.Event', { + alternateClassName: 'Ext.EventObjectImpl', + requires: [ + 'Ext.util.Point' + ], + /** + * @property {Number} distance + * The distance of the event. + * + * **This is only available when the event type is `swipe` and `pinch`.** + */ + /** + * @property {HTMLElement} target + * The element that fired this event. For the element whose handlers are currently + * being processed, i.e. the element that the event handler was attached to, use + * `currentTarget` + */ + /** + * @property {HTMLElement} currentTarget + * Refers to the element the event handler was attached to, vs the `target`, which is + * the actual element that fired the event. For example, if the event bubbles, the + * `target` element may be a descendant of the `currentTarget`, as the event may + * have been triggered on the `target` and then bubbled up to the `currentTarget` + * where it was handled. + */ + /** + * @property {HTMLElement} delegatedTarget + * Same as `currentTarget` + * @deprecated 5.0.0 use {@link #currentTarget} instead. + */ + /** + * @property {Number} button + * Indicates which mouse button caused the event for mouse events, for example + * `mousedown`, `click`, `mouseup`: + * - `0` for left button. + * - `1` for middle button. + * - `2` for right button. + * + * *Note*: In IE8 & IE9, the `click` event does not provide the button. + */ + /** + * @property {Number} pageX The browsers x coordinate of the event. + * Note: this only works in browsers that support pageX on the native browser event + * object (pageX is not natively supported in IE9 and earlier). In Ext JS, for a + * cross browser normalized x-coordinate use {@link #getX} + */ + /** + * @property {Number} pageY The browsers y coordinate of the event. + * Note: this only works in browsers that support pageY on the native browser event + * object (pageY is not natively supported in IE9 and earlier). In Ext JS, for a + * cross browser normalized y-coordinate use {@link #getY} + */ + /** + * @property {Boolean} ctrlKey + * True if the control key was down during the event. + * In Mac this will also be true when meta key was down. + */ + /** + * @property {Boolean} altKey + * True if the alt key was down during the event. + */ + /** + * @property {Boolean} shiftKey + * True if the shift key was down during the event. + */ + /** + * @property {Event} browserEvent + * The raw browser event which this object wraps. + */ + /** + * @property {String} pointerType + * The pointer type for this event. May be empty if the event was + * not triggered by a pointer. Current available types are: + * - `mouse` + * - `touch` + * - `pen` + */ + /** + * @property {Boolean} + * `true` if {@link #stopPropagation} has been called on this instance + * @private + */ + stopped: false, + /** + * @property {Boolean} + * `true` if {@link #claimGesture} has been called on this instance + * @private + */ + claimed: false, + /** + * @property {Boolean} + * Indicates whether or not {@link #preventDefault preventDefault()} was called on the event. + */ + defaultPrevented: false, + isEvent: true, + // With these events, the relatedTarget can sometimes be an Object literal in FF. + geckoRelatedTargetEvents: { + blur: 1, + dragenter: 1, + dragleave: 1, + focus: 1 + }, + statics: { + resolveTextNode: function(node) { + return (node && node.nodeType === 3) ? node.parentNode : node; + }, + /** + * @private + * An amalgamation of pointerEvents/mouseEvents/touchEvents. + * Will be populated in class callback. + */ + gestureEvents: {}, + /** + * @private + */ + pointerEvents: { + pointerdown: 1, + pointermove: 1, + pointerup: 1, + pointercancel: 1, + pointerover: 1, + pointerout: 1, + pointerenter: 1, + pointerleave: 1, + MSPointerDown: 1, + MSPointerMove: 1, + MSPointerUp: 1, + MSPointerOver: 1, + MSPointerOut: 1, + MSPointerCancel: 1, + MSPointerEnter: 1, + MSPointerLeave: 1 + }, + /** + * @private + */ + mouseEvents: { + mousedown: 1, + mousemove: 1, + mouseup: 1, + mouseover: 1, + mouseout: 1, + mouseenter: 1, + mouseleave: 1 + }, + /** + * @private + * These are tracked separately from mouseEvents because the mouseEvents map + * is used by Dom publisher to eliminate duplicate events on devices that fire + * multiple kinds of events (mouse, touch, pointer). Adding click events to the + * mouse events map can cause click events to be blocked from firing in some cases. + */ + clickEvents: { + click: 1, + dblclick: 1 + }, + /** + * @private + */ + touchEvents: { + touchstart: 1, + touchmove: 1, + touchend: 1, + touchcancel: 1 + }, + /** + * @private + */ + focusEvents: { + focus: 1, + focusin: 1, + focusenter: 1 + }, + /** + * @private + */ + blurEvents: { + blur: 1, + focusout: 1, + focusleave: 1 + }, + // msPointerTypes in IE10 are numbers, in the w3c spec they are strings. + // this map allows us to normalize the pointerType for an event + // http://www.w3.org/TR/pointerevents/#widl-PointerEvent-pointerType + // http://msdn.microsoft.com/en-us/library/ie/hh772359(v=vs.85).aspx + pointerTypeMap: { + 2: 'touch', + 3: 'pen', + 4: 'mouse', + touch: 'touch', + pen: 'pen', + mouse: 'mouse' + }, + keyEventRe: /^key/, + keyFlags: { + CTRL: 'ctrlKey', + CONTROL: 'ctrlKey', + ALT: 'altKey', + SHIFT: 'shiftKey', + CMD: 'metaKey', + COMMAND: 'metaKey', + CMDORCTRL: Ext.isMac ? 'metaKey' : 'ctrlKey', + COMMANDORCONTROL: Ext.isMac ? 'metaKey' : 'ctrlKey', + META: 'metaKey' + }, + modifierGlyphs: { + ctrlKey: '⌃', + altKey: '⌥', + metaKey: Ext.isMac ? '⌘' : '⊞', + shiftKey: '⇧' + }, + specialKeyGlyphs: { + BACKSPACE: '⌫', + TAB: '⇥', + ENTER: '⏎', + RETURN: '⏎', + SPACE: '␣', + PAGE_UP: '⇞', + PAGE_DOWN: '⇟', + END: '⇲', + HOME: '⌂', + LEFT: '←', + UP: '↑', + RIGHT: '→', + DOWN: '↓', + PRINT_SCREEN: '⎙', + INSERT: '⎀', + DELETE: '⌦', + CONTEXT_MENU: '☰' + }, + _hyphenRe: /^[a-z]+\-/i, + // eg "Ctrl-" (instead of "Ctrl+") + /** + * Convert a key specification in the form eg: "CTRL+ALT+DELETE" to the glyph sequence + * for use in menu items, eg "⌃⌥⌦". + * @private + */ + getKeyId: function(keyName) { + // Translate eg: 27 to "ESC" + if (typeof keyName === 'number') { + keyName = this.keyCodes[keyName]; + } else { + keyName = keyName.toUpperCase(); + } + var me = this, + delim = me._hyphenRe.test(keyName) ? '-' : '+', + parts = (keyName === delim) ? [ + delim + ] : keyName.split(delim), + numModifiers = parts.length - 1, + rawKey = parts[numModifiers], + result = [], + eventFlag, i; + if (!Ext.event.Event[rawKey]) { + Ext.raise('Invalid key name: "' + rawKey + '"'); + } + for (i = 0; i < numModifiers; i++) { + eventFlag = me.keyFlags[parts[i]]; + if (!eventFlag) { + Ext.raise('Invalid key modifier: "' + parts[i] + '"'); + } + result[eventFlag] = true; + } + if (result.ctrlKey) { + result.push(me.modifierGlyphs.ctrlKey); + } + if (result.altKey) { + result.push(me.modifierGlyphs.altKey); + } + if (result.shiftKey) { + result.push(me.modifierGlyphs.shiftKey); + } + if (result.metaKey) { + result.push(me.modifierGlyphs.metaKey); + } + result.push(this.specialKeyGlyphs[rawKey] || rawKey); + return result.join(''); + }, + /** + * @private + */ + globalTabKeyDown: function(e) { + if (e.keyCode === 9) { + Ext.event.Event.forwardTab = !e.shiftKey; + } + }, + /** + * @private + */ + globalTabKeyUp: function(e) { + if (e.keyCode === 9) { + delete Ext.event.Event.forwardTab; + } + } + }, + constructor: function(event) { + var me = this, + self = me.self, + resolveTextNode = me.self.resolveTextNode, + changedTouches = event.changedTouches, + // The target object from which to obtain the coordinates (pageX, pageY). For + // mouse and pointer events this is simply the event object itself, but touch + // events have their coordinates on the "Touch" object(s) instead. + coordinateOwner = changedTouches ? changedTouches[0] : event, + type = event.type, + pointerType, relatedTarget; + // Do not use event.timeStamp as it is not consistent cross browser (some browsers + // use high resolution time stamps, while others use milliseconds) + me.timeStamp = me.time = Ext.now(); + me.pageX = coordinateOwner.pageX; + me.pageY = coordinateOwner.pageY; + me.clientX = coordinateOwner.clientX; + me.clientY = coordinateOwner.clientY; + me.target = me.delegatedTarget = resolveTextNode(event.target); + me.currentTarget = resolveTextNode(event.currentTarget); + relatedTarget = event.relatedTarget; + if (relatedTarget) { + if (Ext.isGecko && me.geckoRelatedTargetEvents[type]) { + try { + me.relatedTarget = resolveTextNode(relatedTarget); + } catch (e) { + me.relatedTarget = null; + } + } else { + me.relatedTarget = resolveTextNode(relatedTarget); + } + } + me.browserEvent = me.event = event; + me.type = type; + // set button to 0 if undefined so that touchstart, touchend, and tap will quack + // like left mouse button mousedown mouseup, and click + me.button = event.button || 0; + me.shiftKey = event.shiftKey; + // mac metaKey behaves like ctrlKey + me.ctrlKey = event.ctrlKey || event.metaKey || false; + me.altKey = event.altKey; + me.charCode = event.charCode; + me.keyCode = event.keyCode; + me.buttons = event.buttons; + // When invoking synthetic events, current APIs do not + // have the ability to specify the buttons config, which + // defaults to button. For buttons, 0 means no button + // is pressed, whereas for button, 0 means left click. + // Normalize that here + if (me.button === 0 && me.buttons === 0) { + me.buttons = 1; + } + if (self.focusEvents[type] || self.blurEvents[type]) { + if (self.forwardTab !== undefined) { + me.forwardTab = self.forwardTab; + } + if (self.focusEvents[type]) { + me.fromElement = event.relatedTarget; + me.toElement = event.target; + } else { + me.fromElement = event.target; + me.toElement = event.relatedTarget; + } + } else if (type !== 'keydown') { + // Normally this property should be cleaned up in keyup handler; + // however that one might never come if something prevented default + // on the keydown. Make sure the property won't get stuck. + delete self.forwardTab; + } + if (self.mouseEvents[type]) { + pointerType = 'mouse'; + } else if (self.clickEvents[type]) { + // On pointer events browsers like IE11 and Edge click events have a pointerType + // property. On touch events devices we check if the last touchend event + // happened less than a second ago - if so we can reasonably assume that + // the click event happened because of a tap on the screen. + pointerType = self.pointerTypeMap[event.pointerType] || (((Ext.now() - Ext.event.publisher.Dom.lastTouchEndTime) < 1000) ? 'touch' : 'mouse'); + } else if (self.pointerEvents[type]) { + // In electron the mousemove event when the mouse first enters the document + // can have a pointerType of "", so default it to mouse if not found in the map. + pointerType = self.pointerTypeMap[event.pointerType] || 'mouse'; + } else if (self.touchEvents[type]) { + pointerType = 'touch'; + } + if (pointerType) { + me.pointerType = pointerType; + } + // Is this is not the primary touch for PointerEvents (first touch) + // or there are multiples touches for Touch Events + me.isMultitouch = event.isPrimary === false || (event.touches && event.touches.length > 1); + }, + /** + * Creates a new Event object that is prototype-chained to this event. Useful for + * creating identical events so that certain properties can be changed without + * affecting the original event. For example, translated events have their "type" + * corrected in this manner. + * @param {Object} props properties to set on the chained event + * @private + */ + chain: function(props) { + var e = Ext.Object.chain(this); + e.parentEvent = this; + // needed for stopPropagation + return Ext.apply(e, props); + }, + /** + * Correctly scales a given wheel delta. + * @param {Number} delta The delta value. + * @private + */ + correctWheelDelta: function(delta) { + var scale = this.WHEEL_SCALE, + ret = Math.round(delta / scale); + if (!ret && delta) { + ret = (delta < 0) ? -1 : 1; + } + // don't allow non-zero deltas to go to zero! + return ret; + }, + getChar: function() { + var r = this.which(); + return String.fromCharCode(r); + }, + /** + * Gets the character code for the event. + * @return {Number} + */ + getCharCode: function() { + return this.charCode || this.keyCode; + }, + /** + * Returns a normalized keyCode for the event. + * @return {Number} The key code + */ + getKey: function() { + return this.keyCode || this.charCode; + }, + /** + * Returns the name of the keyCode for the event. + * @return {String} The key name + */ + getKeyName: function() { + return this.type === 'keypress' ? String.fromCharCode(this.getCharCode()) : this.keyCodes[this.keyCode]; + }, + /** + * Returns the `key` property of a keyboard event. + * @return {String} + */ + key: function() { + return this.browserEvent.key; + }, + which: function() { + var me = this, + e = me.browserEvent, + r = e.which; + if (r == null) { + if (me.self.keyEventRe.test(e.type)) { + r = e.charCode || e.keyCode; + } else if ((r = e.button) !== undefined) { + // L M R button codes (1, 4, 2): + r = (r & 1) ? 1 : ((r & 4) ? 2 : ((r & 2) ? 3 : 0)); + } + } + return r; + }, + /** + * If this is an event of {@link #type} `paste`, this returns the clipboard data + * of the pasesd mime type. + * + * @param {String} [type='text/plain'] The mime type of the data to extract from the + * clipabord. + * + * Note that this uses non-standard browaer APIs and may not work reliably on all + * platforms. + * @return {Mixed} The clipboard data. + * @since 6.5.1 + */ + getClipboardData: function(type) { + var clipboardData = this.browserEvent.clipboardData, + clipIE = Ext.global.clipboardData, + // IE + result = null, + typeIE; + type = type || 'text/plain'; + if (clipboardData && clipboardData.getData) { + result = clipboardData.getData(type); + } else if (clipIE && clipIE.getData) { + typeIE = this.ieMimeType[type]; + if (typeIE) { + result = clipIE.getData(typeIE); + } + } + return result; + }, + /** + * Returns a point object that consists of the object coordinates. + * @return {Ext.util.Point} point + */ + getPoint: function() { + var me = this, + point = me.point, + xy; + if (!point) { + xy = me.getXY(); + point = me.point = new Ext.util.Point(xy[0], xy[1]); + } + return point; + }, + /** + * Gets the related target. + * @param {String} [selector] A simple selector to filter the target or look for an + * ancestor of the target. See {@link Ext.dom.Query} for information about simple + * selectors. + * @param {Number/HTMLElement} [maxDepth] The max depth to search as a number or + * element (defaults to 10 || document.body). + * @param {Boolean} [returnEl] `true` to return a Ext.Element object instead of DOM + * node. + * @return {HTMLElement} + */ + getRelatedTarget: function(selector, maxDepth, returnEl) { + var relatedTarget = this.relatedTarget, + target = null; + // In some cases in IE10/11, when the mouse is leaving the document over a scrollbar + // the relatedTarget will be an empty object literal. So just check we have an element + // looking object here before we proceed. + if (relatedTarget && relatedTarget.nodeType) { + if (selector) { + target = Ext.fly(relatedTarget).findParent(selector, maxDepth, returnEl); + } else { + target = returnEl ? Ext.get(relatedTarget) : relatedTarget; + } + } + return target; + }, + /** + * Gets the target for the event. + * @param {String} selector (optional) A simple selector to filter the target or look + * for an ancestor of the target + * @param {Number/Mixed} [maxDepth=10||document.body] (optional) The max depth to + * search as a number or element (defaults to 10 || document.body) + * @param {Boolean} returnEl (optional) `true` to return a Ext.Element object instead + * of DOM node. + * @return {HTMLElement} + */ + getTarget: function(selector, maxDepth, returnEl) { + return selector ? Ext.fly(this.target).findParent(selector, maxDepth, returnEl) : (returnEl ? Ext.get(this.target) : this.target); + }, + /** + * Returns the time of the event. + * @return {Date} + */ + getTime: function() { + return this.time; + }, + /** + * Normalizes mouse wheel y-delta across browsers. To get x-delta information, use + * {@link #getWheelDeltas} instead. + * @return {Number} The mouse wheel y-delta + */ + getWheelDelta: function() { + var deltas = this.getWheelDeltas(); + return deltas.y; + }, + /** + * Returns the mouse wheel deltas for this event. + * @return {Object} An object with "x" and "y" properties holding the mouse wheel deltas. + */ + getWheelDeltas: function() { + var me = this, + event = me.browserEvent, + dx = 0, + dy = 0; + // the deltas + if (Ext.isDefined(event.wheelDeltaX)) { + // WebKit and Edge have both dimensions + dx = event.wheelDeltaX; + dy = event.wheelDeltaY; + } else if (event.wheelDelta) { + // old WebKit and IE + dy = event.wheelDelta; + } else if ('deltaX' in event) { + // IE11 + dx = event.deltaX; + dy = -event.deltaY; + } + // backwards + else if (event.detail) { + // Gecko + dy = -event.detail; + // gecko is backwards + // Gecko sometimes returns really big values if the user changes settings to + // scroll a whole page per scroll + if (dy > 100) { + dy = 3; + } else if (dy < -100) { + dy = -3; + } + // Firefox 3.1 adds an axis field to the event to indicate direction of + // scroll. See https://developer.mozilla.org/en/Gecko-Specific_DOM_Events + if (Ext.isDefined(event.axis) && event.axis === event.HORIZONTAL_AXIS) { + dx = dy; + dy = 0; + } + } + return { + x: me.correctWheelDelta(dx), + y: me.correctWheelDelta(dy) + }; + }, + /** + * Gets the x coordinate of the event. + * @return {Number} + */ + getX: function() { + return this.getXY()[0]; + }, + /** + * Gets the X and Y coordinates of the event. + * @return {Number[]} The xy values like [x, y] + */ + getXY: function() { + var me = this, + xy = me.xy; + if (!xy) { + xy = me.xy = [ + me.pageX, + me.pageY + ]; + var x = xy[0], + browserEvent, doc, docEl, body; + // pageX/pageY not available (undefined, not null), use clientX/clientY instead + if (!x && x !== 0) { + browserEvent = me.browserEvent; + doc = document; + docEl = doc.documentElement; + body = doc.body; + xy[0] = browserEvent.clientX + (docEl && docEl.scrollLeft || body && body.scrollLeft || 0) - (docEl && docEl.clientLeft || body && body.clientLeft || 0); + xy[1] = browserEvent.clientY + (docEl && docEl.scrollTop || body && body.scrollTop || 0) - (docEl && docEl.clientTop || body && body.clientTop || 0); + } + } + return xy; + }, + /** + * Gets the y coordinate of the event. + * @return {Number} + */ + getY: function() { + return this.getXY()[1]; + }, + /** + * Returns true if the control, meta, shift or alt key was pressed during this event. + * @return {Boolean} + */ + hasModifier: function() { + var me = this; + return !!(me.ctrlKey || me.altKey || me.shiftKey || me.metaKey); + }, + /** + * Checks if the key pressed was a "navigation" key. A navigation key is defined by + * these keys: + * + * - Page Up + * - Page Down + * - End + * - Home + * - Left + * - Up + * - Right + * - Down + * - Return + * - Tab + * - Esc + * + * @param {Boolean} [scrollableOnly] Only check navigation keys that can cause + * element scrolling by their default action. + * + * @return {Boolean} `true` if the press is a navigation keypress + */ + isNavKeyPress: function(scrollableOnly) { + var me = this, + k = me.keyCode, + isKeyPress = me.type === 'keypress'; + // See specs for description of behaviour + return ((!isKeyPress || Ext.isGecko) && k >= 33 && k <= 40) || (// Page Up/Down, End, Home, Left, Up, Right, Down + !scrollableOnly && (k === me.RETURN || k === me.TAB || k === me.ESC)); + }, + /** + * Checks if the key pressed was a "special" key. A special key is defined as one of + * these keys: + * + * - Page Up + * - Page Down + * - End + * - Home + * - Left arrow + * - Up arrow + * - Right arrow + * - Down arrow + * - Return + * - Tab + * - Esc + * - Backspace + * - Delete + * - Shift + * - Ctrl + * - Alt + * - Pause + * - Caps Lock + * - Print Screen + * - Insert + * + * @return {Boolean} `true` if the key for this event is special + */ + isSpecialKey: function() { + var me = this, + k = me.keyCode, + isGecko = Ext.isGecko, + isKeyPress = me.type === 'keypress'; + // See specs for description of behaviour + return (isGecko && isKeyPress && me.charCode === 0) || (this.isNavKeyPress()) || (k === me.BACKSPACE) || (k === me.ENTER) || (k >= 16 && k <= 20) || (// Shift, Ctrl, Alt, Pause, Caps Lock + (!isKeyPress || isGecko) && k >= 44 && k <= 46); + }, + // Print Screen, Insert, Delete + makeUnpreventable: function() { + this.browserEvent.preventDefault = Ext.emptyFn; + }, + /** + * Prevents the browsers default handling of the event. + * @chainable + */ + preventDefault: function() { + var me = this, + parentEvent = me.parentEvent; + me.defaultPrevented = true; + // if the event was created by prototype-chaining a new object to an existing event + // instance, we need to make sure the parent event is defaultPrevented as well. + if (parentEvent) { + parentEvent.defaultPrevented = true; + } + me.browserEvent.preventDefault(); + return me; + }, + setCurrentTarget: function(target) { + this.currentTarget = this.delegatedTarget = target; + }, + /** + * Stop the event (`{@link #preventDefault}` and `{@link #stopPropagation}`). + * @chainable + */ + stopEvent: function() { + return this.preventDefault().stopPropagation(); + }, + // map of events that should fire global mousedown even if stopped + mousedownEvents: { + mousedown: 1, + pointerdown: 1, + touchstart: 1 + }, + // map of events that should fire global mouseup even if stopped + mouseupEvents: { + mouseup: 1, + pointerup: 1, + touchend: 1 + }, + /** + * Cancels bubbling of the event. + * @chainable + */ + stopPropagation: function() { + var me = this, + browserEvent = me.browserEvent, + parentEvent = me.parentEvent; + // Fire the "unstoppable" global mousedown event + // (used for menu hiding, etc) + if (me.mousedownEvents[me.type]) { + Ext.GlobalEvents.fireMouseDown(me); + } + // Fire the "unstoppable" global mouseup event + // (used for component unpressing, etc) + if (me.mouseupEvents[me.type]) { + Ext.GlobalEvents.fireMouseUp(me); + } + // Set stopped for delegated event listeners. Dom publisher will check this + // property during its emulated propagation phase (see doPublish) + me.stopped = true; + // if the event was created by prototype-chaining a new object to an existing event + // instance, we need to make sure the parent event is stopped. This feature most + // likely comes into play when dealing with event translation. For example on touch + // browsers addListener('mousedown') actually attaches a 'touchstart' listener behind + // the scenes. When the 'touchstart' event is dispatched, the event system will + // create a "chained" copy of the event object before correcting its type back to + // 'mousedown' and calling the handler. When propagating the event we look at the + // original event, not the chained one to determine if propagation should continue, + // so the stopped property must be set on the parentEvent or stopPropagation + // will not work. + if (parentEvent && !me.isGesture) { + parentEvent.stopped = true; + } + if (!browserEvent.stopPropagation) { + // IE < 10 does not have stopPropagation() + browserEvent.cancelBubble = true; + return me; + } + // For non-delegated event listeners (those that are directly attached to the + // DOM element) we need to call the browserEvent's stopPropagation() method. + browserEvent.stopPropagation(); + return me; + }, + /** + * Claims this event as the currently active gesture. Once a gesture is claimed + * no other gestures will fire events until after the current gesture has completed. + * For example, if `claimGesture()` is invoked on a dragstart or drag event, no + * swipestart or swipe events will be fired until the drag gesture completes, even if + * the gesture also meets the required duration and distance requirements to be recognized + * as a swipe. + * + * If `claimGesture()` is invoked on a mouse, touch, or pointer event, it will disable + * all gesture events until termination of the current gesture is indicated by a + * mouseup, touchend, or pointerup event. + * + * @return {Ext.event.Event} + */ + claimGesture: function() { + var me = this, + parentEvent = me.parentEvent; + me.claimed = true; + if (parentEvent && !me.isGesture) { + parentEvent.claimGesture(); + } else { + // Claiming a gesture should also prevent default browser actions like pan/zoom + // if possible (only works on browsers that support touch events - browsers that + // use pointer events must declare a CSS touch-action on elements to prevent the + // default touch action from occurring. + me.preventDefault(); + } + return me; + }, + /** + * Returns true if the target of this event is a child of `el`. If the allowEl + * parameter is set to false, it will return false if the target is `el`. + * Example usage: + * + * // Handle click on any child of an element + * Ext.getBody().on('click', function(e){ + * if(e.within('some-el')){ + * alert('Clicked on a child of some-el!'); + * } + * }); + * + * // Handle click directly on an element, ignoring clicks on child nodes + * Ext.getBody().on('click', function(e,t){ + * if((t.id == 'some-el') && !e.within(t, true)){ + * alert('Clicked directly on some-el!'); + * } + * }); + * + * @param {String/HTMLElement/Ext.dom.Element} el The id, DOM element or Ext.Element to check + * @param {Boolean} [related] `true` to test if the related target is within el instead + * of the target + * @param {Boolean} [allowEl=true] `true` to allow the target to be considered "within" itself. + * `false` to only allow child elements. + * @return {Boolean} + */ + within: function(el, related, allowEl) { + var t; + if (el) { + t = related ? this.getRelatedTarget() : this.getTarget(); + } + if (!t || (allowEl === false && t === Ext.getDom(el))) { + return false; + } + return Ext.fly(el).contains(t); + }, + privates: { + ieMimeType: { + "text/plain": 'Text' + } + }, + deprecated: { + '4.0': { + methods: { + /** + * @method getPageX + * Gets the x coordinate of the event. + * @return {Number} + * @deprecated 4.0 use {@link #getX} instead + * @member Ext.event.Event + */ + getPageX: 'getX', + /** + * @method getPageY + * Gets the y coordinate of the event. + * @return {Number} + * @deprecated 4.0 use {@link #getY} instead + * @member Ext.event.Event + */ + getPageY: 'getY' + } + } + } +}, function(Event) { + var constants = { + /** Key constant @type Number */ + BACKSPACE: 8, + /** Key constant @type Number */ + TAB: 9, + /** Key constant @type Number */ + NUM_CENTER: 12, + /** Key constant @type Number */ + ENTER: 13, + /** Key constant @type Number */ + RETURN: 13, + /** Key constant @type Number */ + SHIFT: 16, + /** Key constant @type Number */ + CTRL: 17, + /** Key constant @type Number */ + ALT: 18, + /** Key constant @type Number */ + PAUSE: 19, + /** Key constant @type Number */ + CAPS_LOCK: 20, + /** Key constant @type Number */ + ESC: 27, + /** Key constant @type Number */ + SPACE: 32, + /** Key constant @type Number */ + PAGE_UP: 33, + /** Key constant @type Number */ + PAGE_DOWN: 34, + /** Key constant @type Number */ + END: 35, + /** Key constant @type Number */ + HOME: 36, + /** Key constant @type Number */ + LEFT: 37, + /** Key constant @type Number */ + UP: 38, + /** Key constant @type Number */ + RIGHT: 39, + /** Key constant @type Number */ + DOWN: 40, + /** Key constant @type Number */ + PRINT_SCREEN: 44, + /** Key constant @type Number */ + INSERT: 45, + /** Key constant @type Number */ + DELETE: 46, + /** Key constant @type Number */ + ZERO: 48, + /** Key constant @type Number */ + ONE: 49, + /** Key constant @type Number */ + TWO: 50, + /** Key constant @type Number */ + THREE: 51, + /** Key constant @type Number */ + FOUR: 52, + /** Key constant @type Number */ + FIVE: 53, + /** Key constant @type Number */ + SIX: 54, + /** Key constant @type Number */ + SEVEN: 55, + /** Key constant @type Number */ + EIGHT: 56, + /** Key constant @type Number */ + NINE: 57, + /** Key constant @type Number */ + A: 65, + /** Key constant @type Number */ + B: 66, + /** Key constant @type Number */ + C: 67, + /** Key constant @type Number */ + D: 68, + /** Key constant @type Number */ + E: 69, + /** Key constant @type Number */ + F: 70, + /** Key constant @type Number */ + G: 71, + /** Key constant @type Number */ + H: 72, + /** Key constant @type Number */ + I: 73, + /** Key constant @type Number */ + J: 74, + /** Key constant @type Number */ + K: 75, + /** Key constant @type Number */ + L: 76, + /** Key constant @type Number */ + M: 77, + /** Key constant @type Number */ + N: 78, + /** Key constant @type Number */ + O: 79, + /** Key constant @type Number */ + P: 80, + /** Key constant @type Number */ + Q: 81, + /** Key constant @type Number */ + R: 82, + /** Key constant @type Number */ + S: 83, + /** Key constant @type Number */ + T: 84, + /** Key constant @type Number */ + U: 85, + /** Key constant @type Number */ + V: 86, + /** Key constant @type Number */ + W: 87, + /** Key constant @type Number */ + X: 88, + /** Key constant @type Number */ + Y: 89, + /** Key constant @type Number */ + Z: 90, + /** Key constant @type Number */ + META: 91, + // Command key on mac, left window key on Windows + /** Key constant @type Number */ + CONTEXT_MENU: 93, + /** Key constant @type Number */ + NUM_ZERO: 96, + /** Key constant @type Number */ + NUM_ONE: 97, + /** Key constant @type Number */ + NUM_TWO: 98, + /** Key constant @type Number */ + NUM_THREE: 99, + /** Key constant @type Number */ + NUM_FOUR: 100, + /** Key constant @type Number */ + NUM_FIVE: 101, + /** Key constant @type Number */ + NUM_SIX: 102, + /** Key constant @type Number */ + NUM_SEVEN: 103, + /** Key constant @type Number */ + NUM_EIGHT: 104, + /** Key constant @type Number */ + NUM_NINE: 105, + /** Key constant @type Number */ + NUM_MULTIPLY: 106, + /** Key constant @type Number */ + NUM_PLUS: 107, + /** Key constant @type Number */ + NUM_MINUS: 109, + /** Key constant @type Number */ + NUM_PERIOD: 110, + /** Key constant @type Number */ + NUM_DIVISION: 111, + /** Key constant @type Number */ + F1: 112, + /** Key constant @type Number */ + F2: 113, + /** Key constant @type Number */ + F3: 114, + /** Key constant @type Number */ + F4: 115, + /** Key constant @type Number */ + F5: 116, + /** Key constant @type Number */ + F6: 117, + /** Key constant @type Number */ + F7: 118, + /** Key constant @type Number */ + F8: 119, + /** Key constant @type Number */ + F9: 120, + /** Key constant @type Number */ + F10: 121, + /** Key constant @type Number */ + F11: 122, + /** Key constant @type Number */ + F12: 123, + /** + * @property {Number} + * The mouse wheel delta scaling factor. This value depends on browser + * version and OS and attempts to produce a similar scrolling experience + * across all platforms and browsers. + * + * To change this value: + * + * Ext.event.Event.prototype.WHEEL_SCALE = 72; + */ + WHEEL_SCALE: 120 + }, + // IE, Opera and other Windows browsers use 120 + keyCodes = {}, + gestureEvents = Event.gestureEvents, + prototype = Event.prototype, + i, keyName, keyCode, keys, s, scale; + if (Ext.isGecko) { + // Firefox uses 3 on all platforms + constants.WHEEL_SCALE = 3; + } else if (Ext.isMac) { + // Continuous scrolling devices have momentum and produce much more scroll than + // discrete devices on the same OS and browser. To make things exciting, Safari + // (and not Chrome) changed from small values to 120 (like IE). + if (Ext.isSafari && Ext.webKitVersion >= 532) { + // Safari changed the scrolling factor to match IE (for details see + // https://bugs.webkit.org/show_bug.cgi?id=24368). The WebKit version where this + // change was introduced was 532.0 + // Detailed discussion: + // https://bugs.webkit.org/show_bug.cgi?id=29601 + // http://trac.webkit.org/browser/trunk/WebKit/chromium/src/mac/WebInputEventFactory.mm#L1063 + scale = 120; + } else { + // MS optical wheel mouse produces multiples of 12 which is close enough + // to help tame the speed of the continuous mice... + scale = 12; + } + // Momentum scrolling produces very fast scrolling, so increase the scale factor + // to help produce similar results cross platform. This could be even larger and + // it would help those mice, but other mice would become almost unusable as a + // result (since we cannot tell which device type is in use). + constants.WHEEL_SCALE = 3 * scale; + } + Ext.apply(gestureEvents, Event.mouseEvents); + Ext.apply(gestureEvents, Event.pointerEvents); + Ext.apply(gestureEvents, Event.touchEvents); + Ext.apply(Event, constants); + Ext.apply(prototype, constants); + // Don't need that + delete constants.WHEEL_SCALE; + // ENTER and RETURN has the same keyCode, but since RETURN + // comes later it will win over ENTER down there. However + // ENTER is used more often and feels more natural. + delete constants.RETURN; + // We need this to do reverse lookup of key name by its code + for (keyName in constants) { + keyCode = constants[keyName]; + keyCodes[keyCode] = keyName; + } + Event.keyCodes = prototype.keyCodes = keyCodes; + // Classic Event override will install this handler in IE9- + if (!Ext.isIE9m) { + document.addEventListener('keydown', Event.globalTabKeyDown, true); + document.addEventListener('keyup', Event.globalTabKeyUp, true); + } + /** + * @member Ext.event.Event + * @private + * Returns the X and Y coordinates of this event without regard to any RTL + * direction settings. + */ + prototype.getTrueXY = prototype.getXY; + if (typeof KeyboardEvent !== 'undefined' && !('key' in KeyboardEvent.prototype)) { + prototype._keys = keys = { + 3: 'Cancel', + 6: 'Help', + 8: 'Backspace', + 9: 'Tab', + 12: 'Clear', + 13: 'Enter', + 16: 'Shift', + 17: 'Control', + 18: 'Alt', + 19: 'Pause', + 20: 'CapsLock', + 27: 'Escape', + 28: 'Convert', + 29: 'NonConvert', + 30: 'Accept', + 31: 'ModeChange', + 32: ' ', + 33: 'PageUp', + 34: 'PageDown', + 35: 'End', + 36: 'Home', + 37: 'ArrowLeft', + 38: 'ArrowUp', + 39: 'ArrowRight', + 40: 'ArrowDown', + 41: 'Select', + 42: 'Print', + 43: 'Execute', + 44: 'PrintScreen', + 45: 'Insert', + 46: 'Delete', + 48: [ + '0', + ')' + ], + 49: [ + '1', + '!' + ], + 50: [ + '2', + '@' + ], + 51: [ + '3', + '#' + ], + 52: [ + '4', + '$' + ], + 53: [ + '5', + '%' + ], + 54: [ + '6', + '^' + ], + 55: [ + '7', + '&' + ], + 56: [ + '8', + '*' + ], + 57: [ + '9', + '(' + ], + 91: 'OS', + 93: 'ContextMenu', + 144: 'NumLock', + 145: 'ScrollLock', + 181: 'VolumeMute', + 182: 'VolumeDown', + 183: 'VolumeUp', + 186: [ + ';', + ':' + ], + 187: [ + '=', + '+' + ], + 188: [ + ',', + '<' + ], + 189: [ + '-', + '_' + ], + 190: [ + '.', + '>' + ], + 191: [ + '/', + '?' + ], + 192: [ + '`', + '~' + ], + 219: [ + '[', + '{' + ], + 220: [ + '\\', + '|' + ], + 221: [ + ']', + '}' + ], + 222: [ + "'", + '"' + ], + 224: 'Meta', + 225: 'AltGraph', + 246: 'Attn', + 247: 'CrSel', + 248: 'ExSel', + 249: 'EraseEof', + 250: 'Play', + 251: 'ZoomOut' + }; + for (i = 1; i < 25; ++i) { + keys[i + 111] = 'F' + i; + } + // F1 - F24 + for (i = 0; i < 26; ++i) { + // a-z, A-Z + keys[i] = [ + String.fromCharCode(i + 97), + String.fromCharCode(i + 65) + ]; + } + prototype.key = function() { + var k = keys[this.browserEvent.which || this.keyCode]; + if (k && typeof k !== 'string') { + k = k[+this.shiftKey]; + } + return k; + }; + } +}); + +/** + * @class Ext.event.Event + */ +Ext.define('Ext.overrides.event.Event', { + override: 'Ext.event.Event', + /** + * @method injectEvent + * @member Ext.event.Event + * Injects a DOM event using the data in this object and (optionally) a new target. + * This is a low-level technique and not likely to be used by application code. The + * currently supported event types are: + *

HTMLEvents

+ *
    + *
  • load
  • + *
  • unload
  • + *
  • select
  • + *
  • change
  • + *
  • submit
  • + *
  • reset
  • + *
  • resize
  • + *
  • scroll
  • + *
+ *

MouseEvents

+ *
    + *
  • click
  • + *
  • dblclick
  • + *
  • mousedown
  • + *
  • mouseup
  • + *
  • mouseover
  • + *
  • mousemove
  • + *
  • mouseout
  • + *
+ *

UIEvents

+ *
    + *
  • focusin
  • + *
  • focusout
  • + *
  • activate
  • + *
  • focus
  • + *
  • blur
  • + *
+ * @param {Ext.Element/HTMLElement} target (optional) If specified, the target for the event. This + * is likely to be used when relaying a DOM event. If not specified, {@link #getTarget} + * is used to determine the target. + */ + injectEvent: (function() { + var API, + dispatchers = {}, + // keyed by event type (e.g., 'mousedown') + crazyIEButtons; + // Good reference: http://developer.yahoo.com/yui/docs/UserAction.js.html + // IE9 has createEvent, but this code causes major problems with htmleditor (it + // blocks all mouse events and maybe more). TODO + if (!Ext.isIE9m && document.createEvent) { + // if (DOM compliant) + API = { + createHtmlEvent: function(doc, type, bubbles, cancelable) { + var event = doc.createEvent('HTMLEvents'); + event.initEvent(type, bubbles, cancelable); + return event; + }, + createMouseEvent: function(doc, type, bubbles, cancelable, detail, clientX, clientY, ctrlKey, altKey, shiftKey, metaKey, button, relatedTarget) { + var event = doc.createEvent('MouseEvents'), + view = doc.defaultView || window; + if (event.initMouseEvent) { + event.initMouseEvent(type, bubbles, cancelable, view, detail, clientX, clientY, clientX, clientY, ctrlKey, altKey, shiftKey, metaKey, button, relatedTarget); + } else { + // old Safari + event = doc.createEvent('UIEvents'); + event.initEvent(type, bubbles, cancelable); + event.view = view; + event.detail = detail; + event.screenX = clientX; + event.screenY = clientY; + event.clientX = clientX; + event.clientY = clientY; + event.ctrlKey = ctrlKey; + event.altKey = altKey; + event.metaKey = metaKey; + event.shiftKey = shiftKey; + event.button = button; + event.relatedTarget = relatedTarget; + } + return event; + }, + createUIEvent: function(doc, type, bubbles, cancelable, detail) { + var event = doc.createEvent('UIEvents'), + view = doc.defaultView || window; + event.initUIEvent(type, bubbles, cancelable, view, detail); + return event; + }, + fireEvent: function(target, type, event) { + target.dispatchEvent(event); + } + }; + } else if (document.createEventObject) { + // else if (IE) + crazyIEButtons = { + 0: 1, + 1: 4, + 2: 2 + }; + API = { + createHtmlEvent: function(doc, type, bubbles, cancelable) { + var event = doc.createEventObject(); + event.bubbles = bubbles; + event.cancelable = cancelable; + return event; + }, + createMouseEvent: function(doc, type, bubbles, cancelable, detail, clientX, clientY, ctrlKey, altKey, shiftKey, metaKey, button, relatedTarget) { + var event = doc.createEventObject(); + event.bubbles = bubbles; + event.cancelable = cancelable; + event.detail = detail; + event.screenX = clientX; + event.screenY = clientY; + event.clientX = clientX; + event.clientY = clientY; + event.ctrlKey = ctrlKey; + event.altKey = altKey; + event.shiftKey = shiftKey; + event.metaKey = metaKey; + event.button = crazyIEButtons[button] || button; + event.relatedTarget = relatedTarget; + // cannot assign to/fromElement + return event; + }, + createUIEvent: function(doc, type, bubbles, cancelable, detail) { + var event = doc.createEventObject(); + event.bubbles = bubbles; + event.cancelable = cancelable; + return event; + }, + fireEvent: function(target, type, event) { + target.fireEvent('on' + type, event); + } + }; + } + //---------------- + // HTMLEvents + Ext.Object.each({ + load: [ + false, + false + ], + unload: [ + false, + false + ], + select: [ + true, + false + ], + change: [ + true, + false + ], + submit: [ + true, + true + ], + reset: [ + true, + false + ], + resize: [ + true, + false + ], + scroll: [ + true, + false + ] + }, function(name, value) { + var bubbles = value[0], + cancelable = value[1]; + dispatchers[name] = function(targetEl, srcEvent) { + var e = API.createHtmlEvent(name, bubbles, cancelable); + API.fireEvent(targetEl, name, e); + }; + }); + //---------------- + // MouseEvents + function createMouseEventDispatcher(type, detail) { + var cancelable = (type !== 'mousemove'); + return function(targetEl, srcEvent) { + var xy = srcEvent.getXY(), + e = API.createMouseEvent(targetEl.ownerDocument, type, true, cancelable, detail, xy[0], xy[1], srcEvent.ctrlKey, srcEvent.altKey, srcEvent.shiftKey, srcEvent.metaKey, srcEvent.button, srcEvent.relatedTarget); + API.fireEvent(targetEl, type, e); + }; + } + Ext.each([ + 'click', + 'dblclick', + 'mousedown', + 'mouseup', + 'mouseover', + 'mousemove', + 'mouseout' + ], function(eventName) { + dispatchers[eventName] = createMouseEventDispatcher(eventName, 1); + }); + //---------------- + // UIEvents + Ext.Object.each({ + focusin: [ + true, + false + ], + focusout: [ + true, + false + ], + activate: [ + true, + true + ], + focus: [ + false, + false + ], + blur: [ + false, + false + ] + }, function(name, value) { + var bubbles = value[0], + cancelable = value[1]; + dispatchers[name] = function(targetEl, srcEvent) { + var e = API.createUIEvent(targetEl.ownerDocument, name, bubbles, cancelable, 1); + API.fireEvent(targetEl, name, e); + }; + }); + //--------- + if (!API) { + // not even sure what ancient browsers fall into this category... + dispatchers = {}; + // never mind all those we just built :P + API = {}; + } + function cannotInject(target, srcEvent) {} + // TODO log something + return function(target) { + var me = this, + dispatcher = dispatchers[me.type] || cannotInject, + t = target ? (target.dom || target) : me.getTarget(); + dispatcher(t, me); + }; + }()), + // call to produce method + preventDefault: function(browserOnly) { + var me = this, + event = me.browserEvent, + parentEvent = me.parentEvent, + unselectable, target, fn; + // This check is for IE8/9. The event object may have been + // invalidated, so we can't delve into the details of it. If so, + // just fall out gracefully and don't attempt to do anything. + if (typeof event.type !== 'unknown') { + // In some cases we want to prevent default on the browser event + // but keep propagating it through our event system. For example, + // in Checkbox selection where the cells with checkboxes should + // prevent focusing on mousedown but still fire the click event. + if (!browserOnly) { + me.defaultPrevented = true; + } + // if the event was created by prototype-chaining a new object to an existing event + // instance, we need to make sure the parent event is defaultPrevented as well. + if (parentEvent) { + parentEvent.defaultPrevented = true; + } + if (event.preventDefault) { + event.preventDefault(); + } else { + // The purpose of the code below is for preventDefault to stop focus from + // occurring like it does in other modern browsers. This only happens in + // IE8/9 when using attachEvent. The use of unselectable seems the most reliable + // way to prevent this from happening. We need to use a timeout to restore the + // unselectable state because if we don't setting it has no effect. It's important + // to set the atrribute to 'on' as opposed to just setting the property on the DOM element. + // See the link below for a discussion on the issue: + // http://bugs.jquery.com/ticket/10345 + if (event.type === 'mousedown') { + target = event.target; + unselectable = target.getAttribute('unselectable'); + if (unselectable !== 'on') { + target.setAttribute('unselectable', 'on'); + fn = function() { + target.setAttribute('unselectable', unselectable); + }; + // This function is hard to track, with a potential to be called + // for any HtmlElement in the document. It may be a Fly, it may + // not belong to any Component, and it may even be created by + // 3rd party code that we have no control over and cannot intercept + // the element being destroyed. + // On the other hand, the function is pretty simple, cannot lead + // to memory leaks and is only fired once. So, no harm no foul. + fn.$skipTimerCheck = true; + Ext.defer(fn, 1); + } + } + // IE9 and earlier do not support preventDefault + event.returnValue = false; + // Some keys events require setting the keyCode to -1 to be prevented + // all ctrl + X and F1 -> F12 + if (event.ctrlKey || event.keyCode > 111 && event.keyCode < 124) { + event.keyCode = -1; + } + } + } + return me; + }, + deprecated: { + '5.0': { + methods: { + /** + * @method clone + * @member Ext.event.Event + * Clones this event. + * @return {Ext.event.Event} The cloned copy + * @deprecated 5.0.0 This method is deprecated. + */ + clone: function() { + return new this.self(this.browserEvent, this); + } + } + } + } +}, function() { + var Event = this, + btnMap; + if (Ext.isIE9m) { + btnMap = { + 0: 0, + 1: 0, + 4: 1, + 2: 2 + }; + Event.override({ + statics: { + /** + * @member Ext.event.Event + * When events are attached using IE's attachEvent API instead of + * addEventListener accessing any members of an event object asynchronously + * results in "Member not found" error. To work around this we fabricate + * our own event object by copying all of its members to a new object. + * @param {Event} browserEvent The native browser event object + * @private + * @static + */ + enableIEAsync: function(browserEvent) { + var name, + fakeEvent = {}; + for (name in browserEvent) { + fakeEvent[name] = browserEvent[name]; + } + return fakeEvent; + } + }, + constructor: function(event, info, touchesMap, identifiers) { + var me = this; + me.callParent([ + event, + info, + touchesMap, + identifiers + ]); + me.button = btnMap[event.button]; + if (event.type === 'contextmenu') { + me.button = 2; + } + // IE8/9 reports click as 0, so we can at least attempt to infer here + // IE8 can throw an error when trying to access properties on a browserEvent + // object when the event has been buffered or delayed. Cache them here + // so we can access them later. + me.toElement = event.toElement; + me.fromElement = event.fromElement; + }, + mouseLeaveRe: /(mouseout|mouseleave)/, + mouseEnterRe: /(mouseover|mouseenter)/, + /** + * @method enableIEAsync + * @member Ext.event.Event + * @inheritdoc Ext.event.Event#static-method-enableIEAsync + * @private + */ + enableIEAsync: function(browserEvent) { + this.browserEvent = this.self.enableIEAsync(browserEvent); + }, + getRelatedTarget: function(selector, maxDepth, returnEl) { + var me = this, + type, target; + if (!me.relatedTarget) { + type = me.type; + if (me.mouseLeaveRe.test(type)) { + target = me.toElement; + } else if (me.mouseEnterRe.test(type)) { + target = me.fromElement; + } + if (target) { + me.relatedTarget = me.self.resolveTextNode(target); + } + } + return me.callParent([ + selector, + maxDepth, + returnEl + ]); + } + }); + // We place these listeners to capture Tab and Shift-Tab key strokes + // and pass this information in the focus/blur event if it happens + // between keydown/keyup pair. + document.attachEvent('onkeydown', Ext.event.Event.globalTabKeyDown); + document.attachEvent('onkeyup', Ext.event.Event.globalTabKeyUp); + window.attachEvent('onunload', function() { + document.detachEvent('onkeydown', Ext.event.Event.globalTabKeyDown); + document.detachEvent('onkeyup', Ext.event.Event.globalTabKeyUp); + }); + } +}); + +/** + * @private + */ +Ext.define('Ext.event.publisher.Dom', { + extend: 'Ext.event.publisher.Publisher', + requires: [ + 'Ext.event.Event' + ], + type: 'dom', + /** + * @property {Array} handledDomEvents + * An array of DOM events that this publisher handles. Events specified in this array + * will be added as global listeners on the {@link #target} + */ + handledDomEvents: [], + reEnterCount: 0, + // The following events do not bubble, but can still be "captured" at the top of + // the DOM, For these events, when the delegated event model is used, we attach a + // single listener on the window object using the "useCapture" option. + captureEvents: { + animationstart: 1, + animationend: 1, + resize: 1, + focus: 1, + blur: 1 + }, + // The following events do not bubble, and cannot be "captured". The only way to + // listen for these events is via a listener attached directly to the target element + directEvents: { + mouseenter: 1, + mouseleave: 1, + pointerenter: 1, + pointerleave: 1, + MSPointerEnter: 1, + MSPointerLeave: 1, + load: 1, + unload: 1, + beforeunload: 1, + error: 1, + DOMContentLoaded: 1, + DOMFrameContentLoaded: 1, + hashchange: 1, + // Scroll can be captured, but it is listed here as one of directEvents instead of + // captureEvents because in some browsers capturing the scroll event does not work + // if the window object itself fired the scroll event. + scroll: 1, + online: 1, + offline: 1 + }, + /** + * In browsers that implement pointerevents when a pointerdown is triggered by touching + * the screen, pointerover and pointerenter events will be fired immmediately before + * the pointerdown. Also pointerout and pointerleave will be fired immediately after + * pointerup when triggered using touch input. For a consistent cross-browser + * experience on touch-screens we block pointerover, pointerout, pointerenter, and + * pointerleave when triggered by touch input, since in most cases pointerover/pointerenter + * behavior is not desired when touching the screen. Note: this should only affect + * events with pointerType === 'touch' or pointerType === 'pen', we do NOT want to + * block these events when triggered using a mouse. + * See also: + * http://www.w3.org/TR/pointerevents/#the-pointerdown-event + * http://www.w3.org/TR/pointerevents/#the-pointerenter-event + * @private + */ + blockedPointerEvents: { + pointerover: 1, + pointerout: 1, + pointerenter: 1, + pointerleave: 1, + MSPointerOver: 1, + MSPointerOut: 1, + MSPointerEnter: 1, + MSPointerLeave: 1 + }, + /** + * Browsers with pointer events may implement "compatibility" mouse events: + * http://www.w3.org/TR/pointerevents/#compatibility-mapping-with-mouse-events + * The behavior implemented in handlers for mouse over/out/enter/leave is not typically + * desired when touching the screen, so we map all of these events to their pointer + * counterparts in Ext.Element event translation code, so that they can be blocked + * via "blockedPointerEvents". The only scenario where this breaks down is in IE10 + * with mouseenter/mouseleave, since MSPointerEnter/MSPointerLeave were not implemented + * in IE10. For these 2 events we have to resort to a different method - capturing + * the timestamp of the last pointer event that has pointerType == 'touch', and if the + * mouse event occurred within a certain threshold we can reasonably assume it occurred + * because of a touch on the screen (see isEventBlocked) + * @private + */ + blockedCompatibilityMouseEvents: { + mouseenter: 1, + mouseleave: 1 + }, + constructor: function() { + var me = this, + supportsPassive = Ext.supports.PassiveEventListener; + me.listenerOptions = supportsPassive ? { + passive: false + } : false; + me.captureOptions = supportsPassive ? { + passive: false, + capture: true + } : true; + me.bubbleSubscribers = {}; + me.captureSubscribers = {}; + me.directSubscribers = {}; + me.directCaptureSubscribers = {}; + // this map tracks all the names of the events that currently have a delegated + // event listener attached so that they can be removed from the dom when the + // publisher is destroyed + me.delegatedListeners = {}; + me.initHandlers(); + Ext.onInternalReady(me.onReady, me); + me.callParent(); + me.registerDomEvents(); + }, + registerDomEvents: function() { + var me = this, + publishersByEvent = Ext.event.publisher.Publisher.publishersByEvent, + domEvents = me.handledDomEvents, + ln = domEvents.length, + i, eventName; + for (i = 0; i < ln; i++) { + eventName = domEvents[i]; + me.handles[eventName] = 1; + publishersByEvent[eventName] = me; + } + }, + onReady: function() { + var me = this, + domEvents = me.handledDomEvents, + ln, i; + if (domEvents) { + // If the publisher has handledDomEvents we attach delegated listeners up front + // for those events. Dom publisher does not have a list of event names, but + // attaches listeners dynamically as subscribers are subscribed. This allows it + // to handle all DOM events that are not explicitly handled by another publisher. + // Subclasses such as Gesture must explicitly list their handledDomEvents. + for (i = 0 , ln = domEvents.length; i < ln; i++) { + me.addDelegatedListener(domEvents[i]); + } + } + // DOM publishers should be the last thing to go since they are used + // to remove any element listeners which is typically part + // of the unload destroy process. + Ext.getWin().on('unload', me.destroy, me, { + priority: -10000 + }); + }, + initHandlers: function() { + var me = this; + me.onDelegatedEvent = Ext.bind(me.onDelegatedEvent, me); + me.onDirectEvent = Ext.bind(me.onDirectEvent, me); + me.onDirectCaptureEvent = Ext.bind(me.onDirectCaptureEvent, me); + }, + addDelegatedListener: function(eventName) { + var me = this; + me.delegatedListeners[eventName] = 1; + me.target.addEventListener(eventName, me.onDelegatedEvent, me.captureEvents[eventName] ? me.captureOptions : me.listenerOptions); + }, + removeDelegatedListener: function(eventName) { + var me = this; + delete me.delegatedListeners[eventName]; + me.target.removeEventListener(eventName, me.onDelegatedEvent, me.captureEvents[eventName] ? me.captureOptions : me.listenerOptions); + }, + addDirectListener: function(eventName, element, capture) { + var me = this; + element.dom.addEventListener(eventName, capture ? me.onDirectCaptureEvent : me.onDirectEvent, capture ? me.captureOptions : me.listenerOptions); + }, + removeDirectListener: function(eventName, element, capture) { + var me = this; + element.dom.removeEventListener(eventName, capture ? me.onDirectCaptureEvent : me.onDirectEvent, capture ? me.captureOptions : me.listenerOptions); + }, + subscribe: function(element, eventName, delegated, capture) { + var me = this, + subscribers, id; + if (delegated && !me.directEvents[eventName]) { + // delegated listeners + subscribers = capture ? me.captureSubscribers : me.bubbleSubscribers; + if (!me.handles[eventName] && !me.delegatedListeners[eventName]) { + // First time we've attached a listener for this eventName - need to begin + // listening at the dom level + me.addDelegatedListener(eventName); + } + if (subscribers[eventName]) { + ++subscribers[eventName]; + } else { + subscribers[eventName] = 1; + } + } else { + subscribers = capture ? me.directCaptureSubscribers : me.directSubscribers; + id = element.id; + // Direct subscribers are tracked by eventName first and by element id second. + // This allows the element id key to be deleted when there are no more subscribers + // so that this map does not grow indefinitely (it can only grow to a finite + // set of event names) - see unsubscribe + subscribers = subscribers[eventName] || (subscribers[eventName] = {}); + if (subscribers[id]) { + ++subscribers[id]; + } else { + subscribers[id] = 1; + me.addDirectListener(eventName, element, capture); + } + } + }, + unsubscribe: function(element, eventName, delegated, capture) { + var me = this, + captureSubscribers, bubbleSubscribers, subscribers, id; + if (delegated && !me.directEvents[eventName]) { + captureSubscribers = me.captureSubscribers; + bubbleSubscribers = me.bubbleSubscribers; + subscribers = capture ? captureSubscribers : bubbleSubscribers; + if (subscribers[eventName]) { + --subscribers[eventName]; + } + if (!me.handles[eventName] && !bubbleSubscribers[eventName] && !captureSubscribers[eventName]) { + // decremented subscribers back to 0 - and the event is not in "handledEvents" + // no longer need to listen at the dom level + this.removeDelegatedListener(eventName); + } + } else { + subscribers = capture ? me.directCaptureSubscribers : me.directSubscribers; + id = element.id; + subscribers = subscribers[eventName]; + if (subscribers[id]) { + --subscribers[id]; + } + if (!subscribers[id]) { + // no more direct subscribers for this element/id/capture, so we can safely + // remove the dom listener + delete subscribers[id]; + me.removeDirectListener(eventName, element, capture); + } + } + }, + getPropagatingTargets: function(target) { + var currentNode = target, + targets = [], + parentNode; + while (currentNode) { + targets.push(currentNode); + parentNode = currentNode.parentNode; + if (!parentNode) { + // If the node has no parentNode it means one of two things - either it is + // not in the dom, or we have looped all the way up to the document object. + // If the latter is the case we need to add the window object to the targets + // to ensure that our propagation mimics browser propagation where events + // can bubble from the document to the window. + parentNode = currentNode.defaultView; + } + currentNode = parentNode; + } + return targets; + }, + /** + * + * @param e {Ext.event.Event/Ext.event.Event[]} An event to publish. Can also be an + * array of events. Gesture publisher passes an array so that gesture events and + * the dom events from which they were synthesized can propagate together. + * @param [targets] {HTMLElement[]} propagation targets. Required if `e` is an array. + * @param {Boolean} [claimed=false] pass true if we are re-entering publish() to + * publish gesture cancellation events that are being fired as a result of something + * being claimed. This ensures that cancellation events cannot be claimed. + * @protected + */ + publish: function(e, targets, claimed) { + var me = this, + hasCaptureSubscribers = false, + hasBubbleSubscribers = false, + events, type, target, el, i, ln, j, eLn; + claimed = claimed || false; + // Gesture publisher passes an already created array of propagating targets. + // For all other events we need to compute the targets for propagation now. + if (!targets) { + if (e instanceof Array) { + Ext.raise("Propagation targets must be supplied when publishing an array of events."); + } + // No targets passed, assume that e is not an array. + target = e.target; + if (me.captureEvents[e.type]) { + el = Ext.cache[target.id]; + targets = el ? [ + el + ] : []; + } else { + targets = me.getPropagatingTargets(target); + } + } + // "e" may be either a single event (as is the case for events fired by dom publisher) + // or it could be an array of events containing a dom event and its recognized + // gesture events. + events = Ext.Array.from(e); + ln = targets.length; + eLn = events.length; + for (i = 0; i < eLn; i++) { + type = events[i].type; + if (!hasCaptureSubscribers && me.captureSubscribers[type]) { + hasCaptureSubscribers = true; + } + if (!hasBubbleSubscribers && me.bubbleSubscribers[type]) { + hasBubbleSubscribers = true; + } + } + // We will now proceed to fire events in both capture and bubble phases. You + // may notice that we are looping all potential targets both times, and only + // firing on the target if there is an Ext.Element wrapper in the cache. This is + // done (vs. eliminating non-cached targets from the array up front) because + // event handlers can add listeners to other elements during propagation. Looping + // all the potential targets ensures that these dynamically added listeners + // are fired. See https://sencha.jira.com/browse/EXTJS-15953 + // capture phase (top-down event propagation). + if (hasCaptureSubscribers) { + for (i = ln; i--; ) { + el = Ext.cache[targets[i].id]; + if (el) { + for (j = 0; j < eLn; j++) { + e = events[j]; + me.fire(el, e.type, e, false, true); + if (!claimed && e.claimed) { + claimed = true; + j = me.filterClaimed(events, e); + eLn = events.length; + } + // filterClaimed may remove items + if (e.stopped) { + events.splice(j, 1); + j--; + eLn--; + } + } + } + } + } + // bubble phase (bottom-up event propagation). + // stopPropagation during capture phase cancels entire bubble phase + if (hasBubbleSubscribers && !e.stopped) { + for (i = 0; i < ln; i++) { + el = Ext.cache[targets[i].id]; + if (el) { + for (j = 0; j < eLn; j++) { + e = events[j]; + me.fire(el, e.type, e, false, false); + if (!claimed && e.claimed && me.filterClaimed) { + claimed = true; + j = me.filterClaimed(events, e); + eLn = events.length; + } + // filterClaimed may remove items + if (e.stopped) { + events.splice(j, 1); + j--; + eLn--; + } + } + } + } + } + }, + /** + * Hook for gesture publisher to override and perform gesture recognition + * @param {Ext.event.Event} e + */ + publishDelegatedDomEvent: function(e) { + this.publish(e); + }, + fire: function(element, eventName, e, direct, capture) { + var event; + if (element.hasListeners[eventName]) { + event = element.events[eventName]; + if (event) { + if (capture && direct) { + event = event.directCaptures; + } else if (capture) { + event = event.captures; + } else if (direct) { + event = event.directs; + } + // yes, this second null check for event is necessary - one of the + // above assignments might have resulted in undefined + if (event) { + e.setCurrentTarget(element.dom); + event.fire(e, e.target); + } + } + } + }, + onDelegatedEvent: function(e) { + if (Ext.elevateFunction) { + // using [e] is faster than using arguments in most browsers + // http://jsperf.com/passing-arguments + Ext.elevateFunction(this.doDelegatedEvent, this, [ + e + ]); + } else { + this.doDelegatedEvent(e); + } + }, + doDelegatedEvent: function(e) { + var me = this, + timeStamp; + e = new Ext.event.Event(e); + timeStamp = e.time; + if (!me.isEventBlocked(e)) { + me.beforeEvent(e); + Ext.frameStartTime = timeStamp; + me.reEnterCountAdjusted = false; + me.reEnterCount++; + me.publishDelegatedDomEvent(e); + // Gesture publisher deals with exceptions in recognizers + if (!me.reEnterCountAdjusted) { + me.reEnterCount--; + } + me.afterEvent(e); + } + }, + /** + * Handler for directly-attached (non-delegated) dom events + * @param {Event} e + * @private + */ + onDirectEvent: function(e) { + if (Ext.elevateFunction) { + // using [e] is faster than using arguments in most browsers + // http://jsperf.com/passing-arguments + Ext.elevateFunction(this.doDirectEvent, this, [ + e, + false + ]); + } else { + this.doDirectEvent(e, false); + } + }, + // When eventPhase is AT_TARGET there's no way to know if we are handling a capture + // or bubble listener, hence the need for this separate handler fn + onDirectCaptureEvent: function(e) { + if (Ext.elevateFunction) { + // using [e] is faster than using arguments in most browsers + // http://jsperf.com/passing-arguments + Ext.elevateFunction(this.doDirectEvent, this, [ + e, + true + ]); + } else { + this.doDirectEvent(e, true); + } + }, + doDirectEvent: function(e, capture) { + var me = this, + currentTarget = e.currentTarget, + timeStamp, el; + e = new Ext.event.Event(e); + timeStamp = e.time; + if (me.isEventBlocked(e)) { + return; + } + me.beforeEvent(e); + Ext.frameStartTime = timeStamp; + el = Ext.cache[currentTarget.id]; + // Element can be removed from the cache by this time, with the node + // still lingering for some reason. This can happen for example when + // load event is fired on an iframe that we constructed when submitting + // a form for file uploads. + if (el) { + // Since natural DOM propagation has occurred, no emulated propagation is needed. + // Simply dispatch the event on the currentTarget element + me.reEnterCountAdjusted = false; + me.reEnterCount++; + me.fire(el, e.type, e, true, capture); + // Gesture publisher deals with exceptions in recognizers + if (!me.reEnterCountAdjusted) { + me.reEnterCount--; + } + } + me.afterEvent(e); + }, + beforeEvent: function(e) { + var browserEvent = e.browserEvent, + // use full class name, not me.self, so that Dom and Gesture publishers will + // both place flags on the same object. + self = Ext.event.publisher.Dom, + touches, touch; + if (browserEvent.type === 'touchstart') { + touches = browserEvent.touches; + if (touches.length === 1) { + // capture the coordinates of the first touchstart event so we can use + // them to eliminate duplicate mouse events if needed, (see isEventBlocked). + touch = touches[0]; + self.lastTouchStartX = touch.pageX; + self.lastTouchStartY = touch.pageY; + } + } + }, + afterEvent: function(e) { + var browserEvent = e.browserEvent, + type = browserEvent.type, + // use full class name, not me.self, so that Dom and Gesture publishers will + // both place flags on the same object. + self = Ext.event.publisher.Dom, + GlobalEvents = Ext.GlobalEvents; + // It is important that the following time stamps are captured after the handlers + // have been invoked because they need to represent the "exit" time, so that they + // can be compared against the next "entry" time into onDelegatedEvent or + // onDirectEvent to detect the time lapse in between the firing of the 2 events. + // We set these flags on "this.self" so that they can be shared between Dom + // publisher and subclasses + if (e.self.pointerEvents[type] && e.pointerType !== 'mouse') { + // track the last time a pointer event was fired as a result of interaction + // with the screen, pointerType === 'touch' most likely but could also be + // pointerType === 'pen' hence the reason we use !== 'mouse', This is used + // to eliminate potential duplicate "compatibility" mouse events + // (see isEventBlocked) + self.lastScreenPointerEventTime = Ext.now(); + } + if (type === 'touchend') { + // Capture a time stamp so we can use it to eliminate potential duplicate + // emulated mouse events on multi-input devices that have touch events, + // e.g. Chrome on Window8 with touch-screen (see isEventBlocked). + self.lastTouchEndTime = Ext.now(); + } + if (!this.reEnterCount && !GlobalEvents.idleEventMask[type]) { + Ext.fireIdle(); + } + }, + /** + * Detects if the given event should be blocked from firing because it is an emulated + * "compatibility" mouse event triggered by a touch on the screen. + * @param {Ext.event.Event} e + * @return {Boolean} + * @private + */ + isEventBlocked: function(e) { + var me = this, + type = e.type, + // use full class name, not me.self, so that Dom and Gesture publishers will + // both look for flags on the same object. + self = Ext.event.publisher.Dom, + now = Ext.now(); + // Gecko has a bug where right clicking will trigger both a contextmenu + // and click event. This only occurs when delegating the event onto the window + // object like we do by default for delegated events. + // This is not possible to feature detect using synthetic events. + // Ticket logged: https://bugzilla.mozilla.org/show_bug.cgi?id=1156023 + if (Ext.isGecko && e.type === 'click' && e.button === 2) { + return true; + } + // prevent emulated pointerover, pointerout, pointerenter, and pointerleave + // events from firing when triggered by touching the screen. + return (me.blockedPointerEvents[type] && e.pointerType !== 'mouse') || // prevent compatibility mouse events from firing on devices with pointer + // events - see comment on blockedCompatibilityMouseEvents for more details + // The time from when the last pointer event fired until when compatibility + // events are received varies depending on the browser, device, and application + // so we use 1 second to be safe + (me.blockedCompatibilityMouseEvents[type] && (now - self.lastScreenPointerEventTime < 1000)) || (Ext.supports.TouchEvents && e.self.mouseEvents[e.type] && // some browsers (e.g. webkit on Windows 8 with touch screen) emulate mouse + // events after touch events have fired. This only seems to happen when there + // is no movement present, so, for example, a touchstart followed immediately + // by a touchend would result in the following sequence of events: + // "touchstart, touchend, mousemove, mousedown, mouseup" + // yes, you read that right, the emulated mousemove fires before mousedown. + // However, touch events with movement (touchstart, touchmove, then touchend) + // do not trigger the emulated mouse events. + // The side effect of this behavior is that single-touch gestures that expect + // no movement (e.g. tap) can double-fire - once when the touchstart/touchend + // occurs, and then again when the emulated mousedown/up occurs. + // We cannot solve the problem by only listening for touch events and ignoring + // mouse events, since we may be on a multi-input device that supports both + // touch and mouse events and we want gestures to respond to both kinds of + // events. Instead we have to detect if the mouse event is a "dupe" by + // checking if its coordinates are near the last touchstart's coordinates, + // and if it's timestamp is within a certain threshold of the last touchend + // event's timestamp. This is because when dealing with multi-touch events, + // the emulated mousedown event (when it does fire) will fire with approximately + // the same coordinates as the first touchstart, but within a short time after + // the last touchend. We use 15px as the distance threshold, to be on the safe + // side because the difference in coordinates can sometimes be up to 6px. + Math.abs(e.pageX - self.lastTouchStartX) < 15 && Math.abs(e.pageY - self.lastTouchStartY) < 15 && // in the majority of cases, the emulated mousedown is observed within + // 5ms of touchend, however, to be certain we avoid a situation where a + // gesture handler gets executed twice we use a threshold of 1000ms. The + // side effect of this is that if a user touches the screen and then quickly + // clicks screen in the same spot, the mousedown/mouseup sequence that + // ensues will not trigger any gesture recognizers. + (Ext.now() - self.lastTouchEndTime) < 1000); + }, + destroy: function() { + var GC = Ext.dom['GarbageCollector'], + eventName; + for (eventName in this.delegatedListeners) { + this.removeDelegatedListener(eventName); + } + // We are wired to the unload event, so we ensure cleanup of low-level stuff + // like the Reaper and the GarbageCollector. + Ext.Reaper.flush(); + if (GC) { + GC.collect(); + } + this.callParent(); + }, + /** + * Resets the internal state of the Dom publisher. Internally the Dom publisher + * keeps track of timing and coordinates of events for eliminating browser duplicates + * (e.g. emulated mousedown after pointerdown etc.). This method resets all this + * cached data to a state similar to when the publisher was first instantiated. + * + * Applications will not typically need to use this method, but it is useful for + * Unit-testing situations where a clean slate is required for each test. + */ + reset: function() { + // use full class name, not me.self, so that Dom and Gesture publishers will + // both reset flags on the same object. + var self = Ext.event.publisher.Dom; + this.reEnterCount = 0; + // set to undefined, not null, because that is the initial state of these vars and + // undefined/null return different results when used in math operations + // (see isEventBlocked) + self.lastScreenPointerEventTime = self.lastTouchEndTime = self.lastTouchStartX = self.lastTouchStartY = undefined; + } +}, function(Dom) { + var doc = document, + defaultView = doc.defaultView, + prototype = Dom.prototype; + if ((Ext.os.is.iOS && Ext.os.version.getMajor() < 5) || Ext.browser.is.AndroidStock || !(defaultView && defaultView.addEventListener)) { + // Delegated listeners will get attached to the document object because + // attaching to the window object will not work. In IE8 this is needed because + // events do not bubble up to the window - bubbling stops at the document + // object. The iOS < 5 check was carried forward from Sencha Touch 2.3 - + // Not sure why it was needed. The check for (defaultView && defaultView.addEventListener) + // was carried forward as well - it may be required for older mobile browsers. + // see also TOUCH-5408 + prototype.target = doc; + } else { + /** + * @member Ext.event.publisher.Dom + * @property {Object} target the DOM target to which listeners are attached for + * delegated events. + * @private + */ + prototype.target = defaultView; + } + Dom.instance = new Dom(); +}); + +Ext.define('Ext.overrides.event.publisher.Dom', { + override: 'Ext.event.publisher.Dom' +}, function(DomPublisher) { + var focusEvents = { + focus: true, + focusin: true, + focusout: true, + blur: true + }; + if (Ext.isIE10m) { + DomPublisher.override({ + isEventBlocked: function(e) { + if (!focusEvents[e.type]) { + return this.callParent([ + e + ]); + } + var body = document.body, + ev = e.browserEvent, + el = Ext.synchronouslyFocusing; + // This horrid hack is necessary to work around the issue with input elements + // in IE10m that can fail to focus under certain conditions. See comment in + // Ext.dom.Element override. + if (el && ((ev.type === 'focusout' && (ev.srcElement === el || ev.srcElement === window) && ev.toElement === body) || (ev.type === 'focusin' && (ev.srcElement === body || ev.srcElement === window) && ev.fromElement === el && ev.toElement === null))) { + return true; + } + return false; + } + }); + } + if (Ext.isIE9m) { + var docElement = document.documentElement, + docBody = document.body, + prototype = DomPublisher.prototype, + onDirectEvent, onDirectCaptureEvent; + prototype.target = document; + prototype.directBoundListeners = {}; + // This method gets bound to the element scope in addDirectListener so that + // the currentTarget can be captured using "this". + onDirectEvent = function(e, publisher, capture) { + e.target = e.srcElement || window; + e.currentTarget = this; + if (capture) { + // Although directly attached capture listeners are not supported in IE9m + // we still need to call the handler so at least the event fires. + publisher.onDirectCaptureEvent(e); + } else { + publisher.onDirectEvent(e); + } + }; + onDirectCaptureEvent = function(e, publisher) { + e.target = e.srcElement || window; + e.currentTarget = this; + // this, not DomPublisher + publisher.onDirectCaptureEvent(e); + }; + DomPublisher.override({ + addDelegatedListener: function(eventName) { + this.delegatedListeners[eventName] = 1; + // Use attachEvent for IE9 and below. Even though IE9 strict supports + // addEventListener, it has issues with using synthetic events. + this.target.attachEvent('on' + eventName, this.onDelegatedEvent); + }, + removeDelegatedListener: function(eventName) { + delete this.delegatedListeners[eventName]; + this.target.detachEvent('on' + eventName, this.onDelegatedEvent); + }, + addDirectListener: function(eventName, element, capture) { + var me = this, + dom = element.dom, + // binding the listener to the element allows us to capture the + // "currentTarget" (see onDirectEvent) + boundFn = Ext.Function.bind(onDirectEvent, dom, [ + me, + capture + ], true), + directBoundListeners = me.directBoundListeners, + handlers = directBoundListeners[eventName] || (directBoundListeners[eventName] = {}); + handlers[dom.id] = boundFn; + // may be called with an SVG element here, which + // does not have the attachEvent method on IE 9 strict + if (dom.attachEvent) { + dom.attachEvent('on' + eventName, boundFn); + } else { + me.callParent([ + eventName, + element, + capture + ]); + } + }, + removeDirectListener: function(eventName, element, capture) { + var dom = element.dom; + if (dom.detachEvent) { + dom.detachEvent('on' + eventName, this.directBoundListeners[eventName][dom.id]); + } else { + this.callParent([ + eventName, + element, + capture + ]); + } + }, + doDelegatedEvent: function(e) { + e.target = e.srcElement || window; + if (e.type === 'focusin') { + // IE8 sometimes happen to focus element instead of the body + e.relatedTarget = e.fromElement === docBody || e.fromElement === docElement ? null : e.fromElement; + } else if (e.type === 'focusout') { + e.relatedTarget = e.toElement === docBody || e.toElement === docElement ? null : e.toElement; + } + return this.callParent([ + e + ]); + } + }); + // can't capture any events without addEventListener. Have to have direct + // listeners for every event that does not bubble. + Ext.apply(prototype.directEvents, prototype.captureEvents); + // These do not bubble in IE9m so have to attach direct listeners as well. + Ext.apply(prototype.directEvents, { + change: 1, + input: 1, + paste: 1 + }); + prototype.captureEvents = {}; + } +}); + +/** + * @private + */ +Ext.define('Ext.event.publisher.Gesture', { + extend: 'Ext.event.publisher.Dom', + requires: [ + 'Ext.util.Point', + 'Ext.AnimationQueue' + ], + uses: 'Ext.event.gesture.*', + type: 'gesture', + isCancelEvent: { + touchcancel: 1, + pointercancel: 1, + MSPointerCancel: 1 + }, + isEndEvent: { + mouseup: 1, + touchend: 1, + pointerup: 1, + MSPointerUp: 1 + }, + handledEvents: [], + handledDomEvents: [], + constructor: function(config) { + var me = this, + handledDomEvents = me.handledDomEvents, + supports = Ext.supports, + supportsTouchEvents = supports.TouchEvents, + onTouchStart = me.onTouchStart, + onTouchMove = me.onTouchMove, + onTouchEnd = me.onTouchEnd; + me.handlers = { + touchstart: onTouchStart, + touchmove: onTouchMove, + touchend: onTouchEnd, + touchcancel: onTouchEnd, + pointerdown: onTouchStart, + pointermove: onTouchMove, + pointerup: onTouchEnd, + pointercancel: onTouchEnd, + MSPointerDown: onTouchStart, + MSPointerMove: onTouchMove, + MSPointerUp: onTouchEnd, + MSPointerCancel: onTouchEnd, + mousedown: onTouchStart, + mousemove: onTouchMove, + mouseup: onTouchEnd + }; + me.activeTouchesMap = {}; + me.activeTouches = []; + me.changedTouches = []; + me.recognizers = []; + me.eventToRecognizer = {}; + me.cancelEvents = []; + if (supportsTouchEvents) { + // bind handlers that are only invoked when the browser has touchevents + me.onTargetTouchMove = me.onTargetTouchMove.bind(me); + me.onTargetTouchEnd = me.onTargetTouchEnd.bind(me); + } + if (supports.PointerEvents) { + handledDomEvents.push('pointerdown', 'pointermove', 'pointerup', 'pointercancel'); + me.mousePointerType = 'mouse'; + } else if (supports.MSPointerEvents) { + // IE10 uses vendor prefixed pointer events, IE11+ use unprefixed names. + handledDomEvents.push('MSPointerDown', 'MSPointerMove', 'MSPointerUp', 'MSPointerCancel'); + me.mousePointerType = 4; + } else if (supportsTouchEvents) { + handledDomEvents.push('touchstart', 'touchmove', 'touchend', 'touchcancel'); + } + if (!handledDomEvents.length || (supportsTouchEvents && Ext.os.is.Desktop)) { + // If the browser doesn't have pointer events or touch events we use mouse events + // to trigger gestures. The exception to this rule is touch enabled desktop + // browsers such as chrome and firefox on Windows touch screen devices. These + // browsers accept both touch and mouse input, so we need to listen for both + // touch events and mouse events. + handledDomEvents.push('mousedown', 'mousemove', 'mouseup'); + } + me.initConfig(config); + return me.callParent(); + }, + onReady: function() { + this.callParent(); + Ext.Array.sort(this.recognizers, function(recognizerA, recognizerB) { + var a = recognizerA.priority, + b = recognizerB.priority; + return (a > b) ? 1 : (a < b) ? -1 : 0; + }); + }, + registerRecognizer: function(recognizer) { + var me = this, + handledEvents = recognizer.handledEvents, + ln = handledEvents.length, + eventName, i; + // The recognizer will call our onRecognized method when it determines that a + // gesture has occurred. + recognizer.setOnRecognized(me.onRecognized); + recognizer.setCallbackScope(me); + // the gesture publishers handledEvents array is derived from the handledEvents + // of all of its recognizers + for (i = 0; i < ln; i++) { + eventName = handledEvents[i]; + me.handledEvents.push(eventName); + me.eventToRecognizer[eventName] = recognizer; + } + me.registerEvents(handledEvents); + me.recognizers.push(recognizer); + }, + onRecognized: function(recognizer, eventName, e, info, isCancel) { + var me = this, + touches = e.touches, + changedTouches = e.changedTouches, + ln = changedTouches.length, + events = me.events, + queueWasEmpty = !events.length, + cancelEvents = me.cancelEvents, + targetGroups, targets, i, touch; + info = info || {}; + // At this point "e" still refers to the originally dispatched Ext.event.Event that + // wraps a native browser event such as "touchend", or "mousemove". We need to + // dispatch with an an event object that has the correct "recognized" type such + // as "tap", or "drag". We don't want to change the type of the original event + // object because it may be used asynchronously by event handlers, so we create a + // new object that is chained to the original event. + info.type = eventName; + // Touch events have a handy feature - the original target of a touchstart is + // always the target of successive touchmove/touchend events event if the touch + // is dragged off of the original target. Pointer events also have this behavior + // via the setPointerCapture method, unless their target is removed from the dom + // mid-gesture, however, we do not currently use setPointerCapture because it + // can change the target of translated mouse events. Mouse events do not have this + // "capturing" feature at all - the target is always the element that was under + // the mouse at the time the event occurred. To be safe, and to ensure consistency, + // we just always set the target of recognized events to be the original target + // that was cached when the first "start" event was received. + info.target = changedTouches[0].target; + // reset stopped and claimed just in case the event that we are wrapping had + // stoppedPropagation or claimGesture called + info.stopped = false; + info.claimed = false; + info.isGesture = true; + e = e.chain(info); + if (!me.gestureTargets) { + if (ln > 1) { + targetGroups = []; + for (i = 0; i < ln; i++) { + touch = changedTouches[i]; + targetGroups.push(touch.targets); + } + targets = me.getCommonTargets(targetGroups); + } else { + targets = changedTouches[0].targets; + } + // Cache targets so that they only have to be computed once if multiple + // gestures are currently being recognized. + me.gestureTargets = targets; + } + if (isCancel && recognizer.isSingleTouch && (touches.length > 1)) { + // single touch recognizer cancelled by the start of a second touch. + // push into a separate queue which does not use the targets common to all + // touches (this.gestureTargets) as the targets for publishing but rather + // only uses the targets for the initial touch. + e.target = touches[0].target; + cancelEvents.push(e); + } else { + events.push(e); + } + if (queueWasEmpty) { + // if there were no events in the queue previously, it means the dom event + // has already been published, which means a recognizer must have recognized + // a gesture asynchronously (e.g. singletap fires on a timer) + // if this is the case we must publish now, otherwise we wait for the dom + // event handler to publish after it is finished invoking the recognizers + me.publishGestures(); + } + }, + getCommonTargets: function(targetGroups) { + var firstTargetGroup = targetGroups[0], + ln = targetGroups.length; + if (ln === 1) { + return firstTargetGroup; + } + var commonTargets = [], + i = 1, + target, targets, j; + while (true) { + target = firstTargetGroup[firstTargetGroup.length - i]; + if (!target) { + return commonTargets; + } + for (j = 1; j < ln; j++) { + targets = targetGroups[j]; + if (targets[targets.length - i] !== target) { + return commonTargets; + } + } + commonTargets.unshift(target); + i++; + } + return commonTargets; + }, + invokeRecognizers: function(methodName, e) { + var recognizers = this.recognizers, + ln = recognizers.length, + i, recognizer; + if (methodName === 'onStart') { + for (i = 0; i < ln; i++) { + recognizers[i].isActive = true; + } + } + for (i = 0; i < ln; i++) { + recognizer = recognizers[i]; + if (recognizer.isActive && recognizer[methodName].call(recognizer, e) === false) { + recognizer.isActive = false; + } + } + }, + /** + * When a gesture has been claimed this method is invoked to remove gesture events of + * other kinds. See implementation in Gesture publisher. + * @param {Ext.event.Event[]} events + * @param {String} claimedEvent + * @return {Number} The new index of the claimed event + * @private + */ + filterClaimed: function(events, claimedEvent) { + var me = this, + eventToRecognizer = me.eventToRecognizer, + claimedEventType = claimedEvent.type, + claimedRecognizer = eventToRecognizer[claimedEventType], + claimedEventIndex, recognizer, type, i; + for (i = events.length; i--; ) { + type = events[i].type; + if (type === claimedEventType) { + claimedEventIndex = i; + } else { + recognizer = eventToRecognizer[type]; + // if there is no claimed recognizer it means the user must have invoked + // claimGesture on a dom event (touchstart, touchmove etc). If this is the + // case we need to cease firing all gesture events, otherwise we allow only + // the "claimed" recognizer to continue to dispatch events. + if (!claimedRecognizer || (recognizer && (recognizer !== claimedRecognizer))) { + events.splice(i, 1); + if (claimedEventIndex) { + claimedEventIndex--; + } + } + } + } + me.claimRecognizer(claimedRecognizer, events[0]); + return claimedEventIndex; + }, + /** + * Deactivates all recognizers other than the "claimed" recognizer + * @param {Ext.event.gesture.Recognizer} claimedRecognizer + * @param {Ext.event.Event} e + * @private + */ + claimRecognizer: function(claimedRecognizer, e) { + var me = this, + recognizers = me.recognizers, + i, ln, recognizer; + for (i = 0 , ln = recognizers.length; i < ln; i++) { + recognizer = recognizers[i]; + // cancel recognition for all recognizers other than the one that was claimed + if (recognizer !== claimedRecognizer) { + recognizer.isActive = false; + recognizer.cancel(e); + } + } + if (me.events.length) { + // if any recognizers added cancelation events... + me.publishGestures(true); + } + }, + publishGestures: function(claimed) { + var me = this, + cancelEvents = me.cancelEvents, + events = me.events, + gestureTargets = me.gestureTargets; + if (cancelEvents.length) { + me.cancelEvents = []; + // Since cancellation events cannot be claimed we pass true here which + // prevents them from being claimed. + me.publish(cancelEvents, me.getPropagatingTargets(cancelEvents[0].target), true); + } + if (events.length) { + // It is important to reset the events property to an empty array before + // publishing since since events may be added to the array during publishing. + // This can happen if an event is claimed, thus triggering "cancel" gesture events. + me.events = []; + me.gestureTargets = null; + me.publish(events, gestureTargets || me.getPropagatingTargets(events[0].target), claimed); + } + }, + updateTouches: function(e) { + var me = this, + browserEvent = e.browserEvent, + type = e.type, + // the touchSource is the object from which we get data about the changed touch + // point or points related to an event object, such as identifier, target, and + // coordinates. For touch event the source is changedTouches, for mouse and + // pointer events it is the event object itself. + touchSources = browserEvent.changedTouches || [ + browserEvent + ], + activeTouches = me.activeTouches, + activeTouchesMap = me.activeTouchesMap, + changedTouches = [], + touchSource, identifier, touch, target, i, ln, x, y; + for (i = 0 , ln = touchSources.length; i < ln; i++) { + touchSource = touchSources[i]; + if ('identifier' in touchSource) { + // touch events have an identifier property on their touches objects. + // It can be 0, hence the "in" check + identifier = touchSource.identifier; + } else if ('pointerId' in touchSource) { + // Pointer events have a pointerId on the event object itself + identifier = touchSource.pointerId; + } else { + // Mouse events don't have an identifier, so we always use 1 since there + // can only be one mouse touch point active at a time + identifier = 1; + } + touch = activeTouchesMap[identifier]; + if (!touch) { + target = Ext.event.Event.resolveTextNode(touchSource.target); + touch = activeTouchesMap[identifier] = { + identifier: identifier, + target: target, + // There are 2 main advantages to caching the targets here, vs. + // waiting until onRecognized + // 1. for "move" events we don't have to construct the targets array + // for every event - a theoretical performance win + // 2. if the target is removed from the dom mid-gesture we still + // want any gestures listeners on elements that were above the + // target to complete. This means the propagating targets must reflect + // the target element's initial hierarchy when the gesture began + targets: me.getPropagatingTargets(target) + }; + activeTouches.push(touch); + } + if (me.isEndEvent[type] || me.isCancelEvent[type]) { + delete activeTouchesMap[identifier]; + Ext.Array.remove(activeTouches, touch); + } + x = touchSource.pageX; + y = touchSource.pageY; + touch.pageX = x; + touch.pageY = y; + // recognizers frequently use Point methods, so go ahead and create a Point. + touch.point = new Ext.util.Point(x, y); + changedTouches.push(touch); + } + // decorate the event object with the touch point info so that it can be used from + // within gesture recognizers (clone touches, just in case event object is used + // asynchronously since this.activeTouches is continuously modified) + e.touches = Ext.Array.clone(activeTouches); + // no need to clone changedTouches since we just created it from scratch + e.changedTouches = changedTouches; + }, + publishDelegatedDomEvent: function(e) { + var me = this; + if (!e.button || e.button < 1) { + // mouse gestures (and pointer gestures triggered by a mouse) can only be + // initiated using the left button (0). button value < 0 is also acceptable + // (e.g. pointermove has a button value of -1) + // Track the event on the instance so it can be fired after gesture recognition + // completes (if any gestures are recognized they will be added to this array) + me.events = [ + e + ]; + // This property on the browser event object indicates that the event has bubbled + // up to the window object and has begun being handled by the gesture publisher. + // If the user calls stopPropagation on an event that has not yet been "handled" + // it triggers gesture cancellation and cleanup. + e.browserEvent.$extHandled = true; + me.handlers[e.type].call(me, e); + } else { + // mouse events *with* button still need to be published. + me.callParent([ + e + ]); + } + }, + onTouchStart: function(e) { + var me = this, + target = e.target, + touches = e.browserEvent.touches; + if (e.browserEvent.type === 'touchstart') { + // When using touch events, if the target is removed from the dom mid-gesture + // the touchend event cannot be handled normally because it will not bubble + // to the top of the dom since the target el is no longer attached to the dom. + // Add some special handlers to clean everything up. (see onTargetTouchEnd) + // use addEventListener directly so that we don't have to spin up an instance + // of Ext.Element for every event target. + target.addEventListener('touchmove', me.onTargetTouchMove); + target.addEventListener('touchend', me.onTargetTouchEnd); + target.addEventListener('touchcancel', me.onTargetTouchEnd); + } + // There is a bug in IOS8 where touchstart, but not touchend event is + // fired when clicking on controls for audio/video, which can leave + // us in a bad state here. + if (touches && touches.length <= me.activeTouches.length) { + me.removeGhostTouches(touches); + } + me.updateTouches(e); + if (!me.isStarted) { + // Disable garbage collection during gestures so that if the target element + // of a gesture is removed from the dom, it does not get garbage collected + // until the gesture is complete + if (Ext.enableGarbageCollector) { + Ext.dom.GarbageCollector.pause(); + } + // this is the first active touch - invoke "onStart" which indicates the + // beginning of a gesture + me.isStarted = true; + me.invokeRecognizers('onStart', e); + } + me.invokeRecognizers('onTouchStart', e); + me.publishGestures(); + }, + onTouchMove: function(e) { + var me = this, + mousePointerType = me.mousePointerType, + isStarted = me.isStarted; + if (isStarted || (e.pointerType !== 'mouse')) { + me.updateTouches(e); + } + if (isStarted) { + // In IE10/11, the corresponding pointerup event is not fired after the pointerdown after + // the mouse is released from the scrollbar. However, it does fire a pointermove event with buttons: 0, so + // we capture that here and ensure the touch end process is completed. + if (mousePointerType && e.browserEvent.pointerType === mousePointerType && e.buttons === 0) { + e.type = Ext.dom.Element.prototype.eventMap.touchend; + e.button = 0; + me.onTouchEnd(e); + return; + } + if (e.changedTouches.length > 0) { + me.invokeRecognizers('onTouchMove', e); + } + } + me.publishGestures(); + }, + // This method serves as the handler for both "end" and "cancel" events. This is + // because they are handled identically with the exception of the recognizer method + // that is called. + onTouchEnd: function(e) { + var me = this, + isStarted = me.isStarted, + touchCount; + if (isStarted || (e.pointerType !== 'mouse')) { + me.updateTouches(e); + } + if (!isStarted) { + me.publishGestures(); + return; + } + touchCount = me.activeTouches.length; + // If an exception is thrown in any of the recognizers, we still need to run + // the cleanup. Otherwise the gesture might get "stuck" and *every* pointer event + // after that will fire the same handlers over and over, potentially spewing + // the same exceptions endlessly. See https://sencha.jira.com/browse/EXTJS-15674. + // We don't want to mask the original exception though, let it propagate. + try { + me.invokeRecognizers(me.isCancelEvent[e.type] ? 'onTouchCancel' : 'onTouchEnd', e); + } finally { + // This can throw too + try { + if (!touchCount) { + // no more active touches - invoke onEnd to indicate the end of the gesture + me.isStarted = false; + me.invokeRecognizers('onEnd', e); + } + } finally { + // Right, THIS can throw again! + try { + me.publishGestures(); + } finally { + if (!touchCount) { + // Gesture is finished, safe to resume garbage collection so that any target + // elements destroyed while gesture was in progress can be collected + if (Ext.enableGarbageCollector) { + Ext.dom.GarbageCollector.resume(); + } + } + // The parent code may not to be reached in this case + me.reEnterCountAdjusted = true; + me.reEnterCount--; + } + } + } + }, + onTargetTouchMove: function(e) { + if (Ext.elevateFunction) { + // using [e] is faster than using arguments in most browsers + // http://jsperf.com/passing-arguments + Ext.elevateFunction(this.doTargetTouchMove, this, [ + e + ]); + } else { + this.doTargetTouchMove(e); + } + }, + doTargetTouchMove: function(e) { + var me = this; + // handle touchmove if the target el was removed from dom mid-gesture. + // see onTouchStart/onTargetTouchEnd for further explanation + if (!Ext.getBody().contains(e.target)) { + me.reEnterCountAdjusted = false; + me.reEnterCount++; + this.onTouchMove(new Ext.event.Event(e)); + if (!me.reEnterCountAdjusted) { + me.reEnterCount--; + } + } + }, + onTargetTouchEnd: function(e) { + if (Ext.elevateFunction) { + // using [e] is faster than using arguments in most browsers + // http://jsperf.com/passing-arguments + Ext.elevateFunction(this.doTargetTouchEnd, this, [ + e + ]); + } else { + this.doTargetTouchEnd(e); + } + }, + doTargetTouchEnd: function(e) { + var me = this, + target = e.target; + target.removeEventListener('touchmove', me.onTargetTouchMove); + target.removeEventListener('touchend', me.onTargetTouchEnd); + target.removeEventListener('touchcancel', me.onTargetTouchEnd); + // if the target el was removed from the dom mid-gesture, then the touchend event, + // when it occurs, will not be handled because it will not bubble to the top of + // the dom. This is because the "target" of the touchend is the removed element. + // If this is the case, go ahead and trigger touchend handling now. + // Detect whether the target was removed from the DOM mid gesture by using Element.contains. + // Originally we attempted to detect this by listening for the DOMNodeRemovedFromDocument + // event, and setting a flag on the element when it was removed, however that + // approach only works when the element is removed using removedChild, and fails + // if the element is removed because some ancestor had innerHTML assigned. + // note: this handling is applicable for actual touchend events, pointer and mouse + // events will fire on whatever element is under the cursor/pointer after the + // original target has been removed. + if (!Ext.getBody().contains(target)) { + me.reEnterCountAdjusted = false; + me.reEnterCount++; + me.onTouchEnd(new Ext.event.Event(e)); + if (!me.reEnterCountAdjusted) { + me.reEnterCount--; + } + } + }, + /** + * Resets the internal state of the Gesture publisher and all of its recognizers. + * Applications will not typically need to use this method, but it is useful for + * Unit-testing situations where a clean slate is required for each test. + * + * Calling this method will also reset the state of Ext.event.publisher.Dom + */ + reset: function() { + var me = this, + recognizers = me.recognizers, + ln = recognizers.length, + i, recognizer; + me.activeTouchesMap = {}; + me.activeTouches = []; + me.changedTouches = []; + me.isStarted = false; + me.gestureTargets = null; + me.events = []; + me.cancelEvents = []; + for (i = 0; i < ln; i++) { + recognizer = recognizers[i]; + recognizer.reset(); + recognizer.isActive = false; + } + this.callParent(); + }, + privates: { + removeGhostTouches: function(touches) { + var ids = {}, + len = touches.length, + activeTouches = this.activeTouches, + map = this.activeTouchesMap, + i, id, touch; + // Collect the actual touches + for (i = 0; i < len; ++i) { + ids[touches[i].identifier] = true; + } + i = activeTouches.length; + while (i--) { + touch = activeTouches[i]; + id = touch.identifier; + if (!touches[id]) { + Ext.Array.remove(activeTouches, touch); + delete map[id]; + } + } + } + } +}, function(Gesture) { + var EventProto = Event.prototype, + stopPropagation = EventProto.stopPropagation; + if (stopPropagation) { + EventProto.stopPropagation = function() { + var me = this, + publisher = Gesture.instance, + type = me.type, + e; + if (!me.$extHandled && publisher.handles[type]) { + // User called stop propagation on a native event used by the gesture publisher + // to synthesize gesture events. Cancel gesture recognition and reset the publisher. + e = new Ext.event.Event(me); + publisher.updateTouches(e); + publisher.invokeRecognizers('onTouchCancel', e); + publisher.reset(); + publisher.reEnterCountAdjusted = true; + } + stopPropagation.apply(me, arguments); + }; + } + Gesture.instance = Ext.$gesturePublisher = new Gesture(); +}); + +Ext.define('Ext.overrides.event.publisher.Gesture', { + override: 'Ext.event.publisher.Gesture' +}, function() { + if (Ext.isIE9m) { + this.override({ + updateTouches: function(e, isEnd) { + var browserEvent = e.browserEvent, + xy = e.getXY(); + // I don't always set pageX and pageY on the event object, but when I do + // it's because the Gesture publisher expects an event object that has them. + browserEvent.pageX = xy[0]; + browserEvent.pageY = xy[1]; + this.callParent([ + e, + isEnd + ]); + }, + doDelegatedEvent: function(e) { + // Workaround IE's "Member not found" errors when accessing an event + // object asynchronously. Needed for all gesture handlers because + // they use requestAnimationFrame (see enableIEAsync for more details) + this.callParent([ + Ext.event.Event.enableIEAsync(e) + ]); + } + }); + } +}); + +/** + * + */ +Ext.define('Ext.mixin.Templatable', { + extend: 'Ext.Mixin', + mixinConfig: { + id: 'templatable' + }, + referenceAttributeName: 'reference', + referenceSelector: '[reference]', + getElementConfig: function() { + return { + reference: 'element' + }; + }, + getElementTemplate: function() { + var elementTemplate = document.createDocumentFragment(); + elementTemplate.appendChild(Ext.Element.create(this.getElementConfig(), true)); + return elementTemplate; + }, + initElement: function() { + var prototype = this.self.prototype; + prototype.elementTemplate = this.getElementTemplate(); + prototype.initElement = prototype.doInitElement; + this.initElement.apply(this, arguments); + }, + linkElement: function(reference, node) { + this.link(reference, node); + }, + doInitElement: function() { + var referenceAttributeName = this.referenceAttributeName, + renderElement, referenceNodes, i, ln, referenceNode, reference; + renderElement = this.elementTemplate.cloneNode(true); + referenceNodes = renderElement.querySelectorAll(this.referenceSelector); + for (i = 0 , ln = referenceNodes.length; i < ln; i++) { + referenceNode = referenceNodes[i]; + reference = referenceNode.getAttribute(referenceAttributeName); + referenceNode.removeAttribute(referenceAttributeName); + this.linkElement(reference, referenceNode); + } + } +}); + +/** + * @private + * Handle batch read / write of DOMs, currently used in SizeMonitor + PaintMonitor + */ +Ext.define('Ext.TaskQueue', { + requires: 'Ext.AnimationQueue', + singleton: true, + pending: false, + mode: true, + // true for 'read', false for 'write' + protectedReadQueue: [], + protectedWriteQueue: [], + readQueue: [], + writeQueue: [], + readRequestId: 0, + writeRequestId: 0, + timer: null, + constructor: function() { + var me = this; + me.run = me.run.bind(me); + // Some global things like floated wrapper are persistent and will add tasks/ + // add timers all the time, spoiling resource checks in our unit test suite. + // To work around that we're implementing a parallel queue where only trusted + // tasks will go, and fly under the radar of resource checker. + me.runProtected = Ext.Function.bind(me.run, me, [ + me.protectedReadQueue, + me.protectedWriteQueue, + 'runProtected' + ]); + me.runProtected.$skipTimerCheck = true; + // iOS has a nasty bug which causes pending requestAnimationFrame to not release + // the callback when the WebView is switched back and forth from / to being background process + // We use a watchdog timer to workaround this, and restore the pending state correctly if this happens + // This timer has to be set as an interval from the very beginning and we have to keep it running for + // as long as the app lives, setting it later doesn't seem to work. + // The watchdog timer must be accessible for environments to cancel. + if (Ext.os.is.iOS) { + me.watch.$skipTimerCheck = true; + me.watchdogTimer = Ext.interval(this.watch, 500, this); + } + }, + requestRead: function(fn, scope, args) { + var request = { + id: ++this.readRequestId, + fn: fn, + scope: scope, + args: args + }; + if (arguments[3] === true) { + this.protectedReadQueue.push(request); + this.request(true, 'runProtected'); + } else { + this.readQueue.push(request); + this.request(true); + } + return request.id; + }, + cancelRead: function(id) { + this.cancelRequest(this.readQueue, id, true); + }, + requestWrite: function(fn, scope, args) { + var me = this, + request = { + id: ++me.writeRequestId, + fn: fn, + scope: scope, + args: args + }; + if (arguments[3] === true) { + me.protectedWriteQueue.push(request); + me.request(false, 'runProtected'); + } else { + me.writeQueue.push(request); + me.request(false); + } + return request.id; + }, + cancelWrite: function(id) { + this.cancelRequest(this.writeQueue, id, false); + }, + request: function(mode, method) { + var me = this; + // Used below to cancel the correct timer. + var oldMode = me.mode; + if (!me.pending) { + me.pendingTime = Date.now(); + me.pending = true; + me.mode = mode; + if (mode) { + me.timer = Ext.defer(me[method] || me.run, 1); + } else { + me.timer = Ext.raf(me[method] || me.run); + } + } + // Last one should win + if (me.mode === mode && me.timer) { + if (oldMode) { + Ext.undefer(me.timer); + } else { + Ext.unraf(me.timer); + } + if (mode) { + me.timer = Ext.defer(me[method] || me.run, 1); + } else { + me.timer = Ext.raf(me[method] || me.run); + } + } + }, + cancelRequest: function(queue, id, mode) { + for (var i = 0; i < queue.length; i++) { + if (queue[i].id === id) { + queue.splice(i, 1); + break; + } + } + if (!queue.length && this.mode === mode && this.timer) { + Ext.undefer(this.timer); + } + }, + watch: function() { + if (this.pending && Date.now() - this.pendingTime >= 500) { + this.run(); + } + }, + run: function(readQueue, writeQueue, method) { + var me = this, + mode = null, + queue, tasks, task, fn, scope, args, i, len; + readQueue = readQueue || me.readQueue; + writeQueue = writeQueue || me.writeQueue; + me.pending = false; + me.pending = me.timer = false; + if (me.mode) { + queue = readQueue; + if (writeQueue.length > 0) { + mode = false; + } + } else { + queue = writeQueue; + if (readQueue.length > 0) { + mode = true; + } + } + tasks = queue.slice(); + queue.length = 0; + for (i = 0 , len = tasks.length; i < len; i++) { + task = tasks[i]; + fn = task.fn; + scope = task.scope; + args = task.args; + if (scope && (scope.destroying || scope.destroyed)) { + + continue; + } + if (typeof fn === 'string') { + fn = scope[fn]; + } + if (args) { + fn.apply(scope, args); + } else { + fn.call(scope); + } + } + tasks.length = 0; + if (mode !== null) { + me.request(mode, method); + } + }, + clear: function() { + var me = this, + timer = me.timer; + if (timer) { + if (me.mode) { + Ext.undefer(timer); + } else { + Ext.unraf(timer); + } + } + me.readQueue.length = me.writeQueue.length = 0; + me.pending = me.timer = false; + me.mode = true; + }, + privates: { + flush: function() { + var me = this, + mode = me.mode; + while (me.readQueue.length || me.writeQueue.length) { + if (mode) { + Ext.undefer(me.timer); + } else { + Ext.unraf(me.timer); + } + me.run(); + } + me.mode = true; + } + } +}); + +/** + * @private + */ +Ext.define('Ext.util.sizemonitor.Abstract', { + mixins: [ + 'Ext.mixin.Templatable' + ], + requires: [ + 'Ext.TaskQueue' + ], + config: { + element: null, + callback: Ext.emptyFn, + scope: null, + args: [] + }, + width: null, + height: null, + contentWidth: null, + contentHeight: null, + constructor: function(config) { + var me = this; + me.refresh = me.refresh.bind(me); + me.info = { + width: 0, + height: 0, + contentWidth: 0, + contentHeight: 0, + flag: 0 + }; + me.initElement(); + me.initConfig(config); + me.bindListeners(true); + }, + bindListeners: Ext.emptyFn, + applyElement: function(element) { + if (element) { + return Ext.get(element); + } + }, + updateElement: function(element) { + element.append(this.detectorsContainer, true); + element.addCls(Ext.baseCSSPrefix + 'size-monitored'); + }, + applyArgs: function(args) { + return args.concat([ + this.info + ]); + }, + refreshMonitors: Ext.emptyFn, + forceRefresh: function() { + Ext.TaskQueue.requestRead('refresh', this); + }, + getContentBounds: function() { + return this.detectorsContainer.getBoundingClientRect(); + }, + getContentWidth: function() { + return this.detectorsContainer.clientWidth; + }, + getContentHeight: function() { + return this.detectorsContainer.clientHeight; + }, + refreshSize: function() { + var element = this.getElement(); + if (!element || element.destroyed) { + return false; + } + var me = this, + size = element.measure(), + width = size.width, + height = size.height, + contentWidth = me.getContentWidth(), + contentHeight = me.getContentHeight(), + currentContentWidth = me.contentWidth, + currentContentHeight = me.contentHeight, + info = me.info, + resized = false, + flag; + me.width = width; + me.height = height; + me.contentWidth = contentWidth; + me.contentHeight = contentHeight; + flag = ((currentContentWidth !== contentWidth ? 1 : 0) + (currentContentHeight !== contentHeight ? 2 : 0)); + if (flag > 0) { + info.width = width; + info.height = height; + info.contentWidth = contentWidth; + info.contentHeight = contentHeight; + info.flag = flag; + resized = true; + me.getCallback().apply(me.getScope(), me.getArgs()); + } + return resized; + }, + refresh: function() { + if (this.destroying || this.destroyed) { + return; + } + this.refreshSize(); + // We should always refresh the monitors regardless of whether or not refreshSize + // resulted in a new size. This avoids race conditions in situations such as + // panel placeholder expand where we layout the panel in its expanded state momentarily + // just so we can measure its animation destination, then immediately collapse it. + // In such a scenario refreshSize() will be acting on the original size since it + // is asynchronous, so it will not detect a size change, but we still need to + // ensure that the monitoring elements are in sync, or else the next resize event + // will not fire. + Ext.TaskQueue.requestWrite('refreshMonitors', this); + }, + destroy: function() { + var me = this, + element = me.getElement(); + me.bindListeners(false); + if (element && !element.destroyed) { + element.removeCls(Ext.baseCSSPrefix + 'size-monitored'); + } + delete me._element; + // This is a closure so Base destructor won't null it + me.refresh = null; + me.callParent(); + } +}); + +/** + * @private + */ +Ext.define('Ext.util.sizemonitor.Scroll', { + extend: 'Ext.util.sizemonitor.Abstract', + getElementConfig: function() { + return { + reference: 'detectorsContainer', + classList: [ + Ext.baseCSSPrefix + 'size-monitors', + 'scroll' + ], + children: [ + { + reference: 'expandMonitor', + className: 'expand' + }, + { + reference: 'shrinkMonitor', + className: 'shrink' + } + ] + }; + }, + constructor: function(config) { + this.onScroll = this.onScroll.bind(this); + this.callParent(arguments); + }, + bindListeners: function(bind) { + var method = bind ? 'addEventListener' : 'removeEventListener'; + this.expandMonitor[method]('scroll', this.onScroll, true); + this.shrinkMonitor[method]('scroll', this.onScroll, true); + }, + onScroll: function() { + if (!this.destroyed) { + Ext.TaskQueue.requestRead('refresh', this); + } + }, + refreshMonitors: function() { + var expandMonitor = this.expandMonitor, + shrinkMonitor = this.shrinkMonitor, + end = 1000000; + if (expandMonitor && !expandMonitor.destroyed) { + expandMonitor.scrollLeft = end; + expandMonitor.scrollTop = end; + } + if (shrinkMonitor && !shrinkMonitor.destroyed) { + shrinkMonitor.scrollLeft = end; + shrinkMonitor.scrollTop = end; + } + }, + destroy: function() { + // This is a closure so Base destructor won't null it + this.onScroll = null; + this.callParent(); + } +}); + +/** + * + */ +Ext.define('Ext.util.SizeMonitor', { + requires: [ + 'Ext.util.sizemonitor.Scroll' + ], + // 'Ext.util.sizemonitor.OverflowChange' + constructor: function(config) { + return new Ext.util.sizemonitor.Scroll(config); + } +}); +// var namespace = Ext.util.sizemonitor; +// +// if (Ext.browser.is.Firefox) { +// // this one decreases the grid performance in Firefox +// return new namespace.OverflowChange(config); +// } else { +// return new namespace.Scroll(config); +// } + +/** + * @private + */ +Ext.define('Ext.event.publisher.ElementSize', { + extend: 'Ext.event.publisher.Publisher', + requires: [ + 'Ext.util.SizeMonitor' + ], + type: 'size', + handledEvents: [ + 'resize' + ], + constructor: function() { + this.monitors = {}; + this.subscribers = {}; + this.callParent(arguments); + }, + subscribe: function(element) { + var id = element.id, + subscribers = this.subscribers, + monitors = this.monitors; + if (subscribers[id]) { + ++subscribers[id]; + } else { + subscribers[id] = 1; + monitors[id] = new Ext.util.SizeMonitor({ + element: element, + callback: this.onElementResize, + scope: this, + args: [ + element + ] + }); + } + element.on('painted', 'forceRefresh', monitors[id]); + return true; + }, + unsubscribe: function(element) { + var id = element.id, + subscribers = this.subscribers, + monitors = this.monitors, + sizeMonitor; + if (subscribers[id] && !--subscribers[id]) { + delete subscribers[id]; + sizeMonitor = monitors[id]; + element.un('painted', 'forceRefresh', sizeMonitor); + sizeMonitor.destroy(); + delete monitors[id]; + } + if (element.activeRead) { + Ext.TaskQueue.cancelRead(element.activeRead); + } + }, + fireElementResize: function(element, info) { + delete element.activeRead; + this.fire(element, 'resize', [ + element, + info + ]); + }, + onElementResize: function(element, info) { + if (!element.activeRead) { + element.activeRead = Ext.TaskQueue.requestRead('fireElementResize', this, [ + element, + info + ], !!element.$skipResourceCheck); + } + }, + // This is useful for unit testing so we can force resizes + // to take place synchronously when we know they have changed + privates: { + syncRefresh: function(elements) { + elements = Ext.Array.from(elements); + var len = elements.length, + i = 0, + el, monitor; + for (i = 0; i < len; ++i) { + el = elements[i]; + if (typeof el !== 'string') { + el = el.id; + } + monitor = this.monitors[el]; + if (monitor) { + monitor.forceRefresh(); + } + } + // This just pushes onto the RAF queue. + Ext.TaskQueue.flush(); + // Flush the RAF queue to make this truly synchronous. + Ext.Function.fireElevatedHandlers(); + } + } +}, function(ElementSize) { + ElementSize.instance = new ElementSize(); +}); + +/** + * @private + */ +Ext.define('Ext.util.paintmonitor.Abstract', { + config: { + element: null, + callback: Ext.emptyFn, + scope: null, + args: [] + }, + eventName: '', + monitorClass: '', + constructor: function(config) { + this.onElementPainted = this.onElementPainted.bind(this); + this.initConfig(config); + }, + bindListeners: function(bind) { + this.monitorElement[bind ? 'addEventListener' : 'removeEventListener'](this.eventName, this.onElementPainted, true); + }, + applyElement: function(element) { + if (element) { + return Ext.get(element); + } + }, + updateElement: function(element) { + this.monitorElement = Ext.Element.create({ + classList: [ + Ext.baseCSSPrefix + 'paint-monitor', + this.monitorClass + ] + }, true); + element.appendChild(this.monitorElement, true); + element.addCls(Ext.baseCSSPrefix + 'paint-monitored'); + this.bindListeners(true); + }, + onElementPainted: function() {}, + destroy: function() { + var me = this, + monitorElement = me.monitorElement, + parentNode = monitorElement.parentNode, + element = me.getElement(); + me.bindListeners(false); + delete me.monitorElement; + if (element && !element.destroyed) { + element.removeCls(Ext.baseCSSPrefix + 'paint-monitored'); + delete me._element; + } + if (parentNode) { + parentNode.removeChild(monitorElement); + } + me.callParent(); + } +}); + +/** + * @private + */ +Ext.define('Ext.util.paintmonitor.CssAnimation', { + extend: 'Ext.util.paintmonitor.Abstract', + eventName: Ext.browser.is.WebKit ? 'webkitAnimationEnd' : 'animationend', + monitorClass: 'cssanimation', + onElementPainted: function(e) { + if (e.animationName === Ext.baseCSSPrefix + 'paint-monitor-helper') { + this.getCallback().apply(this.getScope(), this.getArgs()); + } + } +}); + +/** + * + */ +Ext.define('Ext.util.PaintMonitor', { + requires: [ + 'Ext.util.paintmonitor.CssAnimation' + ], + constructor: function(config) { + return new Ext.util.paintmonitor.CssAnimation(config); + } +}); + +/** + * @private + */ +Ext.define('Ext.event.publisher.ElementPaint', { + extend: 'Ext.event.publisher.Publisher', + requires: [ + 'Ext.util.PaintMonitor', + 'Ext.TaskQueue' + ], + type: 'paint', + handledEvents: [ + 'painted' + ], + constructor: function() { + this.monitors = {}; + this.subscribers = {}; + this.callParent(arguments); + }, + subscribe: function(element) { + var me = this, + id = element.id, + subscribers = me.subscribers; + if (subscribers[id]) { + ++subscribers[id]; + } else { + subscribers[id] = 1; + me.monitors[id] = new Ext.util.PaintMonitor({ + element: element, + callback: me.onElementPainted, + scope: me, + args: [ + element + ] + }); + } + }, + unsubscribe: function(element) { + var id = element.id, + subscribers = this.subscribers, + monitors = this.monitors; + if (subscribers[id] && !--subscribers[id]) { + delete subscribers[id]; + monitors[id].destroy(); + delete monitors[id]; + } + if (element.activeRead) { + Ext.TaskQueue.cancelRead(element.activeRead); + } + }, + fireElementPainted: function(element) { + delete element.activeRead; + this.fire(element, 'painted', [ + element + ]); + }, + onElementPainted: function(element) { + if (!element.activeRead) { + element.activeRead = Ext.TaskQueue.requestRead('fireElementPainted', this, [ + element + ], !!element.$skipResourceCheck); + } + } +}, function(ElementPaint) { + ElementPaint.instance = new ElementPaint(); +}); + +/** + * @class Ext.dom.Element + * @alternateClassName Ext.Element + * @mixins Ext.util.Positionable + * @mixins Ext.mixin.Observable + * + * Encapsulates a DOM element, adding simple DOM manipulation facilities, normalizing for browser differences. + * + * **Note:** The events included in this Class are the ones we've found to be the most commonly used. Many events are + * not listed here due to the expedient rate of change across browsers. For a more comprehensive list, please visit the + * following resources: + * + * + [Mozilla Event Reference Guide](https://developer.mozilla.org/en-US/docs/Web/Events) + * + [W3 Pointer Events](http://www.w3.org/TR/pointerevents/) + * + [W3 Touch Events](http://www.w3.org/TR/touch-events/) + * + [W3 DOM 2 Events](http://www.w3.org/TR/DOM-Level-2-Events/) + * + [W3 DOM 3 Events](http://www.w3.org/TR/DOM-Level-3-Events/) + * + * ## Usage + * + * // by id + * var el = Ext.get("my-div"); + * + * // by DOM element reference + * var el = Ext.get(myDivElement); + * + * ## Selecting Descendant Elements + * + * Ext.dom.Element instances can be used to select descendant nodes using CSS selectors. + * There are 3 methods that can be used for this purpose, each with a slightly different + * twist: + * + * - {@link #method-query} + * - {@link #method-selectNode} + * - {@link #method-select} + * + * These methods can accept any valid CSS selector since they all use + * [querySelectorAll](http://www.w3.org/TR/css3-selectors/) under the hood. The primary + * difference between these three methods is their return type: + * + * To get an array of HTMLElement instances matching the selector '.foo' use the query + * method: + * + * element.query('.foo'); + * + * This can easily be transformed into an array of Ext.dom.Element instances by setting + * the `asDom` parameter to `false`: + * + * element.query('.foo', false); + * + * If the desired result is only the first matching HTMLElement use the selectNode method: + * + * element.selectNode('.foo'); + * + * Once again, the dom node can be wrapped in an Ext.dom.Element by setting the `asDom` + * parameter to `false`: + * + * element.selectNode('.foo', false); + * + * The `select` method is used when the desired return type is a {@link + * Ext.CompositeElementLite CompositeElementLite} or a {@link Ext.CompositeElement + * CompositeElement}. These are collections of elements that can be operated on as a + * group using any of the methods of Ext.dom.Element. The only difference between the two + * is that CompositeElementLite is a collection of HTMLElement instances, while + * CompositeElement is a collection of Ext.dom.Element instances. To retrieve a + * CompositeElementLite that represents a collection of HTMLElements for selector '.foo': + * + * element.select('.foo'); + * + * For a {@link Ext.CompositeElement CompositeElement} simply pass `true` as the + * `composite` parameter: + * + * element.select('.foo', true); + * + * The query selection methods can be used even if you don't have a Ext.dom.Element to + * start with For example to select an array of all HTMLElements in the document that match the + * selector '.foo', simply wrap the document object in an Ext.dom.Element instance using + * {@link Ext#fly}: + * + * Ext.fly(document).query('.foo'); + * + * # Animations + * + * When an element is manipulated, by default there is no animation. + * + * var el = Ext.get("my-div"); + * + * // no animation + * el.setWidth(100); + * + * specified as boolean (true) for default animation effects. + * + * // default animation + * el.setWidth(100, true); + * + * To configure the effects, an object literal with animation options to use as the Element animation configuration + * object can also be specified. Note that the supported Element animation configuration options are a subset of the + * {@link Ext.fx.Anim} animation options specific to Fx effects. The supported Element animation configuration options + * are: + * + * Option Default Description + * --------- -------- --------------------------------------------- + * duration 350 The duration of the animation in milliseconds + * easing easeOut The easing method + * callback none A function to execute when the anim completes + * scope this The scope (this) of the callback function + * + * Usage: + * + * // Element animation options object + * var opt = { + * duration: 1000, + * easing: 'elasticIn', + * callback: this.foo, + * scope: this + * }; + * // animation with some options set + * el.setWidth(100, opt); + * + * The Element animation object being used for the animation will be set on the options object as "anim", which allows + * you to stop or manipulate the animation. Here is an example: + * + * // using the "anim" property to get the Anim object + * if(opt.anim.isAnimated()){ + * opt.anim.stop(); + * } + */ +Ext.define('Ext.dom.Element', function(Element) { + var WIN = window, + DOC = document, + docEl = DOC.documentElement, + WIN_TOP = WIN.top, + EMPTY = [], + elementIdCounter, windowId, documentId, + WIDTH = 'width', + HEIGHT = 'height', + MIN_WIDTH = 'min-width', + MIN_HEIGHT = 'min-height', + MAX_WIDTH = 'max-width', + MAX_HEIGHT = 'max-height', + TOP = 'top', + RIGHT = 'right', + BOTTOM = 'bottom', + LEFT = 'left', + VISIBILITY = 'visibility', + HIDDEN = 'hidden', + DISPLAY = "display", + NONE = "none", + ZINDEX = "z-index", + POSITION = "position", + RELATIVE = "relative", + STATIC = "static", + wordsRe = /\w/g, + spacesRe = /\s+/, + classNameSplitRegex = /[\s]+/, + transparentRe = /^(?:transparent|(?:rgba[(](?:\s*\d+\s*[,]){3}\s*0\s*[)]))$/i, + endsQuestionRe = /\?$/, + topRe = /top/i, + empty = {}, + borders = { + t: 'border-top-width', + r: 'border-right-width', + b: 'border-bottom-width', + l: 'border-left-width' + }, + paddings = { + t: 'padding-top', + r: 'padding-right', + b: 'padding-bottom', + l: 'padding-left' + }, + margins = { + t: 'margin-top', + r: 'margin-right', + b: 'margin-bottom', + l: 'margin-left' + }, + selectDir = { + b: 'backward', + back: 'backward', + f: 'forward' + }, + paddingsTLRB = [ + paddings.l, + paddings.r, + paddings.t, + paddings.b + ], + bordersTLRB = [ + borders.l, + borders.r, + borders.t, + borders.b + ], + numberRe = /\d+$/, + unitRe = /\d+(px|r?em|%|vh|vw|vmin|vmax|en|ch|ex|pt|in|cm|mm|pc)$/i, + defaultUnit = 'px', + msRe = /^-ms-/, + camelRe = /(-[a-z])/gi, + cssRe = /([a-z0-9\-]+)\s*:\s*([^;\s]+(?:\s*[^;\s]+)*);?/gi, + pxRe = /^\d+(?:\.\d*)?px$/i, + relativeUnitRe = /(%|r?em|auto|vh|vw|vmin|vmax|ch|ex)$/i, + propertyCache = {}, + ORIGINALDISPLAY = 'originalDisplay', + camelReplaceFn = function(m, a) { + return a.charAt(1).toUpperCase(); + }, + clearData = function(node, deep) { + var childNodes, i, len; + // Only Element nodes may have _extData and child nodes to clear. + // IE8 throws an error attempting to set expandos on non-Element nodes. + if (node.nodeType === 1) { + node._extData = null; + if (deep) { + childNodes = node.childNodes; + for (i = 0 , len = childNodes.length; i < len; ++i) { + clearData(childNodes[i], deep); + } + } + } + }, + toFloat = function(v) { + return parseFloat(v) || 0; + }, + opacityCls = Ext.baseCSSPrefix + 'hidden-opacity', + visibilityCls = Ext.baseCSSPrefix + 'hidden-visibility', + displayCls = Ext.baseCSSPrefix + 'hidden-display', + offsetsCls = Ext.baseCSSPrefix + 'hidden-offsets', + clipCls = Ext.baseCSSPrefix + 'hidden-clip', + lastFocusChange = 0, + lastKeyboardClose = 0, + editableHasFocus = false, + isVirtualKeyboardOpen = false, + inputTypeSelectionSupported = /text|password|search|tel|url/i, + visFly, scrollFly, caFly, wrapFly, grannyFly, activeElFly; + // Cross-origin access might throw an exception + try { + elementIdCounter = WIN_TOP.__elementIdCounter__; + } catch (e) { + WIN_TOP = WIN; + } + WIN_TOP.__elementIdCounter = elementIdCounter = (WIN_TOP.__elementIdCounter__ || 0) + 1; + windowId = 'ext-window-' + elementIdCounter; + documentId = 'ext-document-' + elementIdCounter; + if (Object.freeze) { + Object.freeze(EMPTY); + } + return { + alternateClassName: [ + 'Ext.Element' + ], + mixins: [ + 'Ext.util.Positionable', + 'Ext.mixin.Observable' + ], + requires: [ + 'Ext.dom.Shadow', + 'Ext.dom.Shim', + 'Ext.dom.ElementEvent', + 'Ext.event.publisher.Dom', + 'Ext.event.publisher.Gesture', + 'Ext.event.publisher.ElementSize', + 'Ext.event.publisher.ElementPaint' + ], + uses: [ + 'Ext.dom.Helper', + 'Ext.dom.CompositeElement', + 'Ext.dom.Fly', + 'Ext.dom.TouchAction', + 'Ext.event.publisher.Focus' + ], + observableType: 'element', + isElement: true, + skipGarbageCollection: true, + $applyConfigs: true, + identifiablePrefix: 'ext-element-', + _selectDir: selectDir, + styleHooks: { + transform: { + set: function(dom, value, el) { + var prop, + result = ''; + if (typeof value !== 'string') { + for (prop in value) { + if (result) { + result += ' '; + } + if (prop.indexOf('translate') === 0) { + result += prop + '(' + Element.addUnits(value[prop], 'px') + ')'; + } else { + result += prop + '(' + value[prop] + ')'; + } + } + value = result; + } + dom.style.transform = value; + } + } + }, + validIdRe: Ext.validIdRe, + blockedEvents: Ext.supports.EmulatedMouseOver ? { + // mobile safari emulates a mouseover event on clickable elements such as + // anchors. This event is useless because it runs after touchend. We block + // this event to prevent mouseover handlers from running after tap events. It + // is up to the individual component to determine if it has an analog for + // mouseover, and implement the appropriate event handlers. + mouseover: 1 + } : {}, + longpressEvents: { + longpress: 1, + taphold: 1 + }, + /** + * @property {Ext.Component} component + * A reference to the `Component` that owns this element. This is `null` if there + * is no direct owner. + */ + // Mouse events + /** + * @event click + * Fires when a mouse click is detected within the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event contextmenu + * Fires when a right click is detected within the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event dblclick + * Fires when a mouse double click is detected within the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event mousedown + * Fires when a mousedown is detected within the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event mouseup + * Fires when a mouseup is detected within the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event mouseover + * Fires when a mouseover is detected within the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event mousemove + * Fires when a mousemove is detected with the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event mouseout + * Fires when a mouseout is detected with the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event mouseenter + * Fires when the mouse enters the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event mouseleave + * Fires when the mouse leaves the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + // Keyboard events + /** + * @event keypress + * Fires when a keypress is detected within the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event keydown + * Fires when a keydown is detected within the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event keyup + * Fires when a keyup is detected within the element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + // HTML frame/object events + /** + * @event load + * Fires when the user agent finishes loading all content within the element. Only supported by window, frames, + * objects and images. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event unload + * Fires when the user agent removes all content from a window or frame. For elements, it fires when the target + * element or any of its content has been removed. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event abort + * Fires when an object/image is stopped from loading before completely loaded. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event error + * Fires when an object/image/frame cannot be loaded properly. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event painted + * Fires whenever this Element actually becomes visible (painted) on the screen. This is useful when you need to + * perform 'read' operations on the DOM element, i.e: calculating natural sizes and positioning. + * + * __Note:__ This event is not available to be used with event delegation. Instead `painted` only fires if you explicitly + * add at least one listener to it, for performance reasons. + * + * @param {Ext.dom.Element} this The component instance. + */ + /** + * @event resize + * Important note: For the best performance on mobile devices, use this only when you absolutely need to monitor + * a Element's size. + * + * __Note:__ This event is not available to be used with event delegation. Instead `resize` only fires if you explicitly + * add at least one listener to it, for performance reasons. + * + * @param {Ext.dom.Element} this The component instance. + * @param {Object} info The element's new size parameters. + */ + /** + * @event scroll + * Fires when a document view is scrolled. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + // Form events + /** + * @event select + * Fires when a user selects some text in a text field, including input and textarea. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event change + * Fires when a control loses the input focus and its value has been modified since gaining focus. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event submit + * Fires when a form is submitted. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event reset + * Fires when a form is reset. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event focus + * Fires when an element receives focus either via the pointing device or by tab navigation. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event blur + * Fires when an element loses focus either via the pointing device or by tabbing navigation. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event focusmove + * Fires when focus is moved *within* an element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {Ext.dom.Element} e.target The {@link Ext.dom.Element} element which *recieved* focus. + * @param {Ext.dom.Element} e.relatedTarget The {@link Ext.dom.Element} element which *lost* focus. + * @param {HTMLElement} t The target of the event. + */ + // User Interface events + /** + * @event DOMFocusIn + * Where supported. Similar to HTML focus event, but can be applied to any focusable element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event DOMFocusOut + * Where supported. Similar to HTML blur event, but can be applied to any focusable element. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event DOMActivate + * Where supported. Fires when an element is activated, for instance, through a mouse click or a keypress. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + // DOM Mutation events + /** + * @event DOMSubtreeModified + * Where supported. Fires when the subtree is modified. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event DOMNodeInserted + * Where supported. Fires when a node has been added as a child of another node. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event DOMNodeRemoved + * Where supported. Fires when a descendant node of the element is removed. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event DOMNodeRemovedFromDocument + * Where supported. Fires when a node is being removed from a document. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event DOMNodeInsertedIntoDocument + * Where supported. Fires when a node is being inserted into a document. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event DOMAttrModified + * Where supported. Fires when an attribute has been modified. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * @event DOMCharacterDataModified + * Where supported. Fires when the character data has been modified. + * @param {Ext.event.Event} e The {@link Ext.event.Event} encapsulating the DOM event. + * @param {HTMLElement} t The target of the event. + */ + /** + * Creates new Element directly by passing an id or the HTMLElement. This + * constructor should not be called directly. Always use {@link Ext#get Ext.get()} + * or {@link Ext#fly Ext#fly()} instead. + * + * In older versions of Ext JS and Sencha Touch this constructor checked to see if + * there was already an instance of this element in the cache and if so, returned + * the same instance. As of version 5 this behavior has been removed in order to + * avoid a redundant cache lookup since the most common path is for the Element + * constructor to be called from {@link Ext#get Ext.get()}, which has already + * checked for a cache entry. + * + * Correct way of creating a new Ext.dom.Element (or retrieving it from the cache): + * + * var el = Ext.get('foo'); // by id + * + * var el = Ext.get(document.getElementById('foo')); // by DOM reference + * + * Incorrect way of creating a new Ext.dom.Element + * + * var el = new Ext.dom.Element('foo'); + * + * For quick and easy access to Ext.dom.Element methods use a flyweight: + * + * Ext.fly('foo').addCls('foo-hovered'); + * + * This simply attaches the DOM node with id='foo' to the global flyweight Element + * instance to avoid allocating an extra Ext.dom.Element instance. If, however, + * the Element instance has already been cached by a previous call to Ext.get(), + * then Ext.fly() will return the cached Element instance. For more info see + * {@link Ext#fly}. + * + * @param {String/HTMLElement} dom + * @private + */ + constructor: function(dom) { + var me = this, + id; + if (typeof dom === 'string') { + dom = DOC.getElementById(dom); + } + if (!dom) { + Ext.raise("Invalid domNode reference or an id of an existing domNode: " + dom); + return null; + } + if (Ext.cache[dom.id]) { + Ext.raise("Element cache already contains an entry for id '" + dom.id + "'. Use Ext.get() to create or retrieve Element instances."); + } + /** + * The DOM element + * @property dom + * @type HTMLElement + */ + me.dom = dom; + id = dom.id; + if (id) { + me.id = id; + } else { + id = dom.id = me.getUniqueId(); + } + // Uncomment this when debugging orphaned Elements + // if (id === 'ext-element-5') debugger; + if (!me.validIdRe.test(me.id)) { + Ext.raise('Invalid Element "id": "' + me.id + '"'); + } + // set an "el" property that references "this". This allows + // Ext.util.Positionable methods to operate on this.el.dom since it + // gets mixed into both Element and Component + me.el = me; + Ext.cache[id] = me; + me.longpressListenerCount = 0; + me.mixins.observable.constructor.call(me); + }, + inheritableStatics: { + /** + * @property cache + * @private + * @static + * @inheritable + */ + cache: Ext.cache = {}, + /** + * @property editableSelector + * @static + * @private + * @inheritable + */ + editableSelector: 'input,textarea,[contenteditable="true"]', + /** + * @property {Number} VISIBILITY + * Visibility mode constant for use with {@link Ext.dom.Element#setVisibilityMode}. + * Use the CSS 'visibility' property to hide the element. + * + * Note that in this mode, {@link Ext.dom.Element#isVisible isVisible} may return true + * for an element even though it actually has a parent element that is hidden. For this + * reason, and in most cases, using the {@link #OFFSETS} mode is a better choice. + * @static + * @inheritable + */ + VISIBILITY: 1, + /** + * @property {Number} DISPLAY + * Visibility mode constant for use with {@link Ext.dom.Element#setVisibilityMode}. + * Use the CSS 'display' property to hide the element. + * @static + * @inheritable + */ + DISPLAY: 2, + /** + * @property {Number} OFFSETS + * Visibility mode constant for use with {@link Ext.dom.Element#setVisibilityMode}. + * Use CSS absolute positioning and top/left offsets to hide the element. + * @static + * @inheritable + */ + OFFSETS: 3, + /** + * @property {Number} CLIP + * Visibility mode constant for use with {@link Ext.dom.Element#setVisibilityMode}. + * Use CSS `clip` property to reduce element's dimensions to 0px by 0px, effectively + * making it hidden while not being truly invisible. This is useful when an element + * needs to be published to the Assistive Technologies such as screen readers. + * @static + * @inheritable + */ + CLIP: 4, + /** + * @property {Number} OPACITY + * Visibility mode constant for use with {@link Ext.dom.Element#setVisibilityMode}. + * Use CSS `opacity` property to reduce element's opacity to 0 + * @static + * @inheritable + */ + OPACITY: 5, + /** + * @property minKeyboardHeight + * @static + * @inheritable + * @private + * This property indicates a minimum threshold of vertical resize movement for + * virtual keyboard detection. + * + * On some mobile browsers the framework needs to keep track of whether window + * resize events were triggered by the opening or closing of a virtual keyboard + * so that it can prevent unnecessary re-layout of the viewport. It does this + * by detecting resize events in the horizontal direction that occur immediately + * after an editable element is focused or blurred. + */ + minKeyboardHeight: 100, + unitRe: unitRe, + /** + * @property {Boolean} useDelegatedEvents + * @private + * @static + * @inheritable + * True to globally disable the delegated event system. The results of + * setting this to false are unpredictable since the Gesture publisher relies + * on delegated events in order to work correctly. Disabling delegated events + * may cause Gestures to function incorrectly or to stop working completely. + * Use at your own risk! + */ + useDelegatedEvents: true, + /** + * @property {Object} validNodeTypes + * @private + * @static + * @inheritable + * The list of valid nodeTypes that are allowed to be wrapped + */ + validNodeTypes: { + 1: 1, + // ELEMENT_NODE + 9: 1 + }, + // DOCUMENT_NODE + selectableCls: Ext.baseCSSPrefix + 'selectable', + unselectableCls: Ext.baseCSSPrefix + 'unselectable', + /** + * Determines the maximum size for all ripples + */ + maxRippleDiameter: 75, + /** + * Test if size has a unit, otherwise appends the passed unit string, or the default for this Element. + * @param {Object} size The size to set. + * @param {String} units The units to append to a numeric size value. + * @return {String} + * @private + * @static + * @inheritable + */ + addUnits: function(size, units) { + // Most common case first: Size is set to a number + if (typeof size === 'number') { + return size + (units || defaultUnit); + } + // Values which mean "auto" + // - "" + // - "auto" + // - undefined + // - null + if (size === "" || size === "auto" || size == null) { + return size || ''; + } + // less common use case: number formatted as a string. save this case until + // last to avoid regex execution if possible. + if (numberRe.test(size)) { + return size + (units || defaultUnit); + } + // Warn if it's not a valid CSS measurement + if (!unitRe.test(size)) { + // Don't warn about calc() expressions + if (!(Ext.isString(size) && size.indexOf('calc') === 0)) { + Ext.Logger.warn("Warning, size detected (" + size + ") not a valid property value on Element.addUnits."); + } + return size || ''; + } + return size; + }, + /** + * @private + * Create method to add support for a DomHelper config. Creates + * and appends elements/children using document.createElement/appendChild. + * This method is used by the modern toolkit for a significant performance gain + * in webkit browsers as opposed to using DomQuery which generates HTML + * markup and sets it as innerHTML. + * + * However, the createElement/appendChild + * method of creating elements is significantly slower in all versions of IE + * at the time of this writing (6 - 11), so classic toolkit should not use this method, + * but should instead use DomHelper methods, or Element methods that use + * DomHelper under the hood (e.g. createChild). + * see https:*fiddle.sencha.com/#fiddle/tj + * + * @static + * @inheritable + */ + create: function(attributes, domNode) { + var me = this, + classes, element, elementStyle, tag, value, name, i, ln, tmp; + attributes = attributes || {}; + if (attributes.isElement) { + return domNode ? attributes.dom : attributes; + } else if ('nodeType' in attributes) { + return domNode ? attributes : Ext.get(attributes); + } + if (typeof attributes === 'string') { + return DOC.createTextNode(attributes); + } + tag = attributes.tag; + if (!tag) { + tag = 'div'; + } + if (attributes.namespace) { + element = DOC.createElementNS(attributes.namespace, tag); + } else { + element = DOC.createElement(tag); + } + elementStyle = element.style; + for (name in attributes) { + if (name !== 'tag') { + value = attributes[name]; + switch (name) { + case 'style': + if (typeof value === 'string') { + element.setAttribute(name, value); + } else { + for (i in value) { + if (value.hasOwnProperty(i)) { + elementStyle[i] = value[i]; + } + } + }; + break; + case 'className': + case 'cls': + tmp = value.split(spacesRe); + classes = classes ? classes.concat(tmp) : tmp; + break; + case 'classList': + classes = classes ? classes.concat(value) : value; + break; + case 'text': + element.textContent = value; + break; + case 'html': + element.innerHTML = value; + break; + case 'hidden': + if (classes) { + classes.push(displayCls); + } else { + classes = [ + displayCls + ]; + }; + break; + case 'children': + if (value != null) { + for (i = 0 , ln = value.length; i < ln; i++) { + element.appendChild(me.create(value[i], true)); + } + }; + break; + default: + if (value != null) { + // skip null or undefined values + element.setAttribute(name, value); + }; + } + } + } + if (classes) { + element.className = classes.join(' '); + } + if (domNode) { + return element; + } else { + return me.get(element); + } + }, + /** + * @method fly + * @inheritdoc Ext#method-fly + * @inheritable + * @static + */ + fly: function(dom, named) { + return Ext.fly(dom, named); + }, + /** + * Returns the top Element that is located at the passed coordinates in the current viewport. + * @param {Number} x The x coordinate + * @param {Number} y The y coordinate + * @param {Boolean} [asDom=false] `true` to return a DOM element. + * @return {Ext.dom.Element/HTMLElement} The found element. + * @static + * @inheritable + * @method + */ + fromPoint: (function() { + // IE has a weird bug where elementFromPoint can fail on the first call when inside an iframe. + // It seems to happen more consistently on older IE, but sometimes crops up even in IE11. + // This plays havoc especially while running tests. + var elementFromPointBug; + if (Ext.isIE || Ext.isEdge) { + try { + elementFromPointBug = window.self !== window.top; + } catch (e) { + elementFromPointBug = true; + } + } + return function(x, y, asDom) { + var el = null; + el = DOC.elementFromPoint(x, y); + if (!el && elementFromPointBug) { + el = DOC.elementFromPoint(x, y); + } + return asDom ? el : Ext.get(el); + }; + })(), + /** + * Returns the top Element that is located at the passed coordinates taking into account + * the scroll position of the document. + * @static + * @inheritable + * @param {Number} x The x coordinate + * @param {Number} y The y coordinate + * @param {Boolean} [asDom=false] `true` to return a DOM element. + * @return {Ext.dom.Element/HTMLElement} The found element. + * + * @since 6.2.0 + */ + fromPagePoint: function(x, y, asDom) { + var scroll = Ext.getDoc().getScroll(); + return Element.fromPoint(x - scroll.left, y - scroll.top, asDom); + }, + /** + * Retrieves Ext.dom.Element objects. {@link Ext#get} is alias for {@link Ext.dom.Element#get}. + * + * **This method does not retrieve {@link Ext.Component Component}s.** This method retrieves Ext.dom.Element + * objects which encapsulate DOM elements. To retrieve a Component by its ID, use {@link Ext.ComponentManager#get}. + * + * When passing an id, it should not include the `#` character that is used for a css selector. + * + * // For an element with id 'foo' + * Ext.get('foo'); // Correct + * Ext.get('#foo'); // Incorrect + * + * Uses simple caching to consistently return the same object. Automatically fixes if an object was recreated with + * the same id via AJAX or DOM. + * + * @param {String/HTMLElement/Ext.dom.Element} el The `id` of the node, a DOM Node or an existing Element. + * @return {Ext.dom.Element} The Element object (or `null` if no matching element was found). + * @static + * @inheritable + */ + get: function(el) { + var me = this, + cache = Ext.cache, + nodeType, dom, id, entry, isDoc, isWin, isValidNodeType; + if (!el) { + return null; + } + function warnDuplicate(id) { + Ext.raise("DOM element with id " + id + " in Element cache is not the same as element in the DOM. " + "Make sure to clean up Element instances using destroy()"); + } + // Ext.get(flyweight) must return an Element instance, not the flyweight + if (el.isFly) { + el = el.dom; + } + if (typeof el === 'string') { + id = el; + if (cache.hasOwnProperty(id)) { + entry = cache[id]; + if (entry.skipGarbageCollection || !Ext.isGarbage(entry.dom)) { + dom = Ext.getElementById ? Ext.getElementById(id) : DOC.getElementById(id); + if (dom && (dom !== entry.dom)) { + warnDuplicate(id); + } + return entry; + } else { + entry.destroy(); + } + } + if (id === windowId) { + return Element.get(WIN); + } else if (id === documentId) { + return Element.get(DOC); + } + // using Ext.getElementById() allows us to check the detached + // body in addition to the body (Ext JS only). + dom = Ext.getElementById ? Ext.getElementById(id) : DOC.getElementById(id); + if (dom) { + return new Element(dom); + } + } + nodeType = el.nodeType; + if (nodeType) { + isDoc = (nodeType === 9); + isValidNodeType = me.validNodeTypes[nodeType]; + } else { + // if an object has a window property that refers to itself we can + // reasonably assume that it is a window object. + // have to use == instead of === for IE8 + isWin = (el.window == el); + } + // check if we have a valid node type or if the el is a window object before + // proceeding. This allows elements, document fragments, and document/window + // objects (even those inside iframes) to be wrapped. + if (isValidNodeType || isWin) { + id = el.id; + if (cache.hasOwnProperty(id)) { + entry = cache[id]; + if (entry.skipGarbageCollection || el === entry.dom || !Ext.isGarbage(entry.dom)) { + if (el !== entry.dom) { + warnDuplicate(id); + } + return entry; + } else { + entry.destroy(); + } + } + if (el === DOC) { + el.id = documentId; + } + // Must use == here, otherwise IE fails to recognize the window + if (el == WIN) { + el.id = windowId; + } + el = new Element(el); + if (isWin || isDoc) { + // document and window objects can never be garbage + el.skipGarbageCollection = true; + } + return el; + } + if (el.isElement) { + return el; + } + if (el.isComposite) { + return el; + } + // Test for iterable. + // Allow the resulting Composite to be based upon an Array or HtmlCollection of nodes. + if (Ext.isIterable(el)) { + return me.select(el); + } + return null; + }, + /** + * Returns the active element in the DOM. If the browser supports activeElement + * on the document, this is returned. If not, the focus is tracked and the active + * element is maintained internally. + * @static + * @inheritable + * + * @param {Boolean} asElement Return Ext.Element instance instead of DOM node. + * + * @return {HTMLElement} The active (focused) element in the document. + */ + getActiveElement: function(asElement) { + var active = DOC.activeElement; + // The activeElement can be null, however there also appears to be a very odd + // and inconsistent bug in IE where the activeElement is simply an empty object + // literal. Test if the returned active element has focus, if not, we've hit the bug + // so just default back to the document body. + if (!active || !active.focus) { + active = DOC.body; + } + return asElement ? Ext.get(active) : active; + }, + /** + * Retrieves the document height + * @static + * @inheritable + * @return {Number} documentHeight + */ + getDocumentHeight: function() { + return Math.max(!Ext.isStrict ? DOC.body.scrollHeight : docEl.scrollHeight, this.getViewportHeight()); + }, + /** + * Retrieves the document width + * @static + * @inheritable + * @return {Number} documentWidth + */ + getDocumentWidth: function() { + return Math.max(!Ext.isStrict ? DOC.body.scrollWidth : docEl.scrollWidth, this.getViewportWidth()); + }, + /** + * Retrieves the current orientation of the window. This is calculated by + * determining if the height is greater than the width. + * @static + * @inheritable + * @return {String} Orientation of window: 'portrait' or 'landscape' + */ + getOrientation: function() { + if (Ext.supports.OrientationChange) { + return (WIN.orientation == 0) ? 'portrait' : 'landscape'; + } + return (WIN.innerHeight > WIN.innerWidth) ? 'portrait' : 'landscape'; + }, + /** + * Retrieves the viewport height of the window. + * @static + * @inheritable + * @return {Number} viewportHeight + */ + getViewportHeight: function() { + var viewportHeight = Element._viewportHeight; + if (Ext.isIE9m) { + return DOC.documentElement.clientHeight; + } + return (viewportHeight != null) ? viewportHeight : docEl.clientHeight; + }, + /** + * Retrieves the viewport width of the window. + * @static + * @inheritable + * @return {Number} viewportWidth + */ + getViewportWidth: function() { + var viewportWidth = Element._viewportWidth; + if (Ext.isIE9m) { + return DOC.documentElement.clientWidth; + } + return (viewportWidth != null) ? viewportWidth : docEl.clientWidth; + }, + /** + * Returns the current zoom level of the viewport as a ratio of page pixels to + * screen pixels. + * @private + * @static + * @return {Number} + */ + getViewportScale: function() { + // on desktop devices, the devicePixel ratio gives us the level of zoom that + // the user specified using ctrl +/- and or by selecting a zoom level from + // the menu. + // On android/iOS devicePixel ratio is a fixed number that represents the + // screen pixel density (e.g. always "2" on apple retina devices) + // WIN_TOP is guarded against cross-frame access in the closure above + var top = WIN_TOP; + return ((Ext.isiOS || Ext.isAndroid) ? 1 : (top.devicePixelRatio || // modern browsers + top.screen.deviceXDPI / top.screen.logicalXDPI)) * // IE10m + this.getViewportTouchScale(); + }, + /** + * On touch-screen devices there may be an additional level of zooming + * that occurs when the user performs a pinch or double-tap to zoom + * gesture. This is separate from and in addition to the + * devicePixelRatio. We can detect it by comparing the width + * of the documentElement to window.innerWidth + * @private + */ + getViewportTouchScale: function(forceRead) { + var scale = 1, + // WIN_TOP is guarded against cross-frame access in the closure above + top = WIN_TOP, + cachedScale; + if (!forceRead) { + cachedScale = this._viewportTouchScale; + if (cachedScale) { + return cachedScale; + } + } + if (Ext.isIE10p || Ext.isEdge || Ext.isiOS) { + scale = docEl.offsetWidth / WIN.innerWidth; + } else if (Ext.isChromeMobile) { + scale = top.outerWidth / top.innerWidth; + } + return scale; + }, + /** + * Retrieves the viewport size of the window. + * @static + * @inheritable + * @return {Object} object containing width and height properties + */ + getViewSize: function() { + return { + width: Element.getViewportWidth(), + height: Element.getViewportHeight() + }; + }, + /** + * Checks if the passed size has a css unit attached. + * @param {String} size The size. + * @return {Boolean} `true` if the size has a css unit. + * + * @since 6.2.1 + */ + hasUnit: function(size) { + return !!(size && unitRe.test(size)); + }, + /** + * Checks if the passed css unit is a relative unit. This includes: + * - `auto` + * - `%` + * - `em` + * - `rem` + * - `auto` + * - `vh` + * - `vw` + * - `vmin` + * - `vmax` + * - `ex + * - `ch` + * @param {String} size The css unit and value. + * @return {Boolean} `true` if the value is relative. + * + * @since 6.2.0 + */ + isRelativeUnit: function(size) { + return !size || relativeUnitRe.test(size); + }, + /** + * Mask iframes when shim is true. See {@link Ext.util.Floating#shim}. + * @private + */ + maskIframes: function() { + var iframes = document.getElementsByTagName('iframe'), + fly = new Ext.dom.Fly(); + Ext.each(iframes, function(iframe) { + var myMask; + myMask = fly.attach(iframe.parentNode).mask(); + myMask.setStyle('background-color', 'transparent'); + }); + }, + /** + * Normalizes CSS property keys from dash delimited to camel case JavaScript Syntax. + * For example: + * + * - border-width -> borderWidth + * - padding-top -> paddingTop + * + * @static + * @inheritable + * @param {String} prop The property to normalize + * @return {String} The normalized string + */ + normalize: function(prop) { + // For '-ms-foo' we need msFoo + return propertyCache[prop] || (propertyCache[prop] = prop.replace(msRe, 'ms-').replace(camelRe, camelReplaceFn)); + }, + /** + * @private + * @static + * @inheritable + */ + _onWindowFocusChange: function(e) { + // Tracks the timestamp of focus entering or leaving an editable element + // so that we can compare this timestamp to the time of the next window + // resize for the purpose of determining if the virtual keyboard is displayed + // see _onWindowResize for more details + if (Ext.fly(e.target).is(Element.editableSelector)) { + lastFocusChange = new Date(); + editableHasFocus = (e.type === 'focusin' || e.type === 'pointerup'); + } + }, + /** + * @private + * @static + * @inheritable + */ + _onWindowResize: function() { + var documentWidth = docEl.clientWidth, + documentHeight = docEl.clientHeight, + now = new Date(), + threshold = 1000, + deltaX, deltaY; + deltaX = documentWidth - Element._documentWidth; + deltaY = documentHeight - Element._documentHeight; + Element._documentWidth = documentWidth; + Element._documentHeight = documentHeight; + // If the focus entered or left an editable element within a brief threshold + // of time, then this resize event MAY be due to a virtual keyboard being + // shown or hidden. Let's do some additional checking to find out. + if (((now - lastFocusChange) < threshold) || ((now - lastKeyboardClose) < threshold)) { + // If the resize is ONLY in the vertical direction, and an editable + // element has the focus, and the vertical movement was significant, + // we can be reasonably certain that the resize event was due to + // a virtual keyboard being opened. + if (deltaX === 0 && (editableHasFocus && (deltaY <= -Element.minKeyboardHeight))) { + isVirtualKeyboardOpen = true; + return; + } + } + if (isVirtualKeyboardOpen && (deltaX === 0) && (deltaY >= Element.minKeyboardHeight)) { + isVirtualKeyboardOpen = false; + // when windows tablets are rotated while keyboard is open, the keyboard closes + // and then immediately reopens. Track the timestamp of the last keyboard + // close so that we can detect a successive resize event that might indicate + // reopening + lastKeyboardClose = new Date(); + } + if (isVirtualKeyboardOpen) { + return; + } + // These cached variables are used by getViewportWidth and getViewportHeight + // They do not get updated if we returned early due to detecting that the + // resize event was triggered by virtual keyboard. + Element._viewportWidth = documentWidth; + Element._viewportHeight = documentHeight; + }, + /** + * Parses a number or string representing margin sizes into an object. Supports CSS-style margin declarations + * (e.g. 10, "10", "10 10", "10 10 10" and "10 10 10 10" are all valid options and would return the same result) + * @static + * @inheritable + * @param {Number/String} box The encoded margins + * @return {Object} An object with margin sizes for top, right, bottom and left containing the unit + */ + parseBox: function(box) { + box = box || 0; + var type = typeof box, + parts, ln; + if (type === 'number') { + return { + top: box, + right: box, + bottom: box, + left: box + }; + } else if (type !== 'string') { + // If not a number or a string, assume we've been given a box config. + return box; + } + parts = box.split(' '); + ln = parts.length; + if (ln === 1) { + parts[1] = parts[2] = parts[3] = parts[0]; + } else if (ln === 2) { + parts[2] = parts[0]; + parts[3] = parts[1]; + } else if (ln === 3) { + parts[3] = parts[1]; + } + return { + top: parseFloat(parts[0]) || 0, + right: parseFloat(parts[1]) || 0, + bottom: parseFloat(parts[2]) || 0, + left: parseFloat(parts[3]) || 0 + }; + }, + /** + * Converts a CSS string into an object with a property for each style. + * + * The sample code below would return an object with 2 properties, one + * for background-color and one for color. + * + * var css = 'background-color: red; color: blue;'; + * console.log(Ext.dom.Element.parseStyles(css)); + * + * @static + * @inheritable + * @param {String} styles A CSS string + * @return {Object} styles + */ + parseStyles: function(styles) { + var out = {}, + matches; + if (styles) { + // Since we're using the g flag on the regex, we need to set the lastIndex. + // This automatically happens on some implementations, but not others, see: + // http://stackoverflow.com/questions/2645273/javascript-regular-expression-literal-persists-between-function-calls + // http://blog.stevenlevithan.com/archives/fixing-javascript-regexp + cssRe.lastIndex = 0; + while ((matches = cssRe.exec(styles))) { + out[matches[1]] = matches[2] || ''; + } + } + return out; + }, + /** + * Selects elements based on the passed CSS selector to enable + * {@link Ext.dom.Element Element} methods to be applied to many related + * elements in one statement through the returned + * {@link Ext.dom.CompositeElementLite CompositeElementLite} object. + * @static + * @inheritable + * @param {String/HTMLElement[]} selector The CSS selector or an array of + * elements + * @param {Boolean} [composite=false] Return a CompositeElement as opposed to + * a CompositeElementLite. Defaults to false. + * @param {HTMLElement/String} [root] The root element of the query or id of + * the root + * @return {Ext.dom.CompositeElementLite/Ext.dom.CompositeElement} + */ + select: function(selector, composite, root) { + return Ext.fly(root || DOC).select(selector, composite); + }, + /** + * Selects child nodes of a given root based on the passed CSS selector. + * @static + * @inheritable + * @param {String} selector The CSS selector. + * @param {Boolean} [asDom=true] `false` to return an array of Ext.dom.Element + * @param {HTMLElement/String} [root] The root element of the query or id of + * the root + * @return {HTMLElement[]/Ext.dom.Element[]} An Array of elements that match + * the selector. If there are no matches, an empty Array is returned. + */ + query: function(selector, asDom, root) { + return Ext.fly(root || DOC).query(selector, asDom); + }, + /** + * Parses a number or string representing margin sizes into an object. Supports CSS-style margin declarations + * (e.g. 10, "10", "10 10", "10 10 10" and "10 10 10 10" are all valid options and would return the same result) + * @static + * @inheritable + * @param {Number/String/Object} box The encoded margins, or an object with top, right, + * @param {String} units The type of units to add + * @return {String} An string with unitized (px if units is not specified) metrics for top, right, bottom and left + */ + unitizeBox: function(box, units) { + var me = this; + box = me.parseBox(box); + return me.addUnits(box.top, units) + ' ' + me.addUnits(box.right, units) + ' ' + me.addUnits(box.bottom, units) + ' ' + me.addUnits(box.left, units); + }, + /** + * Unmask iframes when shim is true. See {@link Ext.util.Floating#cfg-shim}. + * @private + */ + unmaskIframes: function() { + var iframes = document.getElementsByTagName('iframe'), + fly = new Ext.dom.Fly(); + Ext.each(iframes, function(iframe) { + fly.attach(iframe.parentNode).unmask(); + }); + }, + /** + * Serializes a DOM form into a url encoded string + * @param {Object} form The form + * @return {String} The url encoded form + * @static + * @inheritable + */ + serializeForm: function(form) { + var fElements = form.elements || (DOC.forms[form] || Ext.getDom(form)).elements, + hasSubmit = false, + encoder = encodeURIComponent, + data = '', + eLen = fElements.length, + element, name, type, options, hasValue, e, o, oLen, opt; + for (e = 0; e < eLen; e++) { + element = fElements[e]; + name = element.name; + type = element.type; + options = element.options; + if (!element.disabled && name) { + if (/select-(one|multiple)/i.test(type)) { + oLen = options.length; + for (o = 0; o < oLen; o++) { + opt = options[o]; + if (opt.selected) { + hasValue = opt.hasAttribute('value'); + data += Ext.String.format('{0}={1}&', encoder(name), encoder(hasValue ? opt.value : opt.text)); + } + } + } else if (!(/file|undefined|reset|button/i.test(type))) { + if (!(/radio|checkbox/i.test(type) && !element.checked) && !(type == 'submit' && hasSubmit)) { + data += encoder(name) + '=' + encoder(element.value) + '&'; + hasSubmit = /submit/i.test(type); + } + } + } + } + return data.substr(0, data.length - 1); + }, + /** + * Returns the common ancestor of the two passed elements. + * @static + * @inheritable + * + * @param {Ext.dom.Element/HTMLElement} nodeA + * @param {Ext.dom.Element/HTMLElement} nodeB + * @param {Boolean} returnDom Pass `true` to return a DOM element. Otherwise An {@link Ext.dom.Element Element} will be returned. + * @return {Ext.dom.Element/HTMLElement} The common ancestor. + */ + getCommonAncestor: function(nodeA, nodeB, returnDom) { + caFly = caFly || new Ext.dom.Fly(); + caFly.attach(Ext.getDom(nodeA)); + while (!caFly.isAncestor(nodeB)) { + if (caFly.dom.parentNode) { + caFly.attach(caFly.dom.parentNode); + } else // If Any of the nodes in in a detached state, have to use the document.body + { + caFly.attach(DOC.body); + break; + } + } + return returnDom ? caFly.dom : Ext.get(caFly); + } + }, + /** + * Enable text selection for this element (normalized across browsers) + * @return {Ext.dom.Element} this + */ + selectable: function() { + var me = this; + // We clear this property for all browsers, not just Opera. This is so that rendering templates don't need to + // condition on Opera when making elements unselectable. + me.dom.unselectable = ''; + me.removeCls(Element.unselectableCls); + me.addCls(Element.selectableCls); + return me; + }, + /** + * Disables text selection for this element (normalized across browsers) + * @return {Ext.dom.Element} this + */ + unselectable: function() { + // The approach used to disable text selection combines CSS, HTML attributes and DOM events. Importantly the + // strategy is designed to be expressible in markup, so that elements can be rendered unselectable without + // needing modifications post-render. e.g.: + // + //
+ // + // Changes to this method may need to be reflected elsewhere, e.g. ProtoElement. + var me = this; + // The unselectable property (or similar) is supported by various browsers but Opera is the only browser that + // doesn't support any of the other techniques. The problem with it is that it isn't inherited by child + // elements. Theoretically we could add it to all children but the performance would be terrible. In certain + // key locations (e.g. panel headers) we add unselectable="on" to extra elements during rendering just for + // Opera's benefit. + if (Ext.isOpera) { + me.dom.unselectable = 'on'; + } + // In Mozilla and WebKit the CSS properties -moz-user-select and -webkit-user-select prevent a selection + // originating in an element. These are inherited, which is what we want. + // + // In IE we rely on a listener for the selectstart event instead. We don't need to register a listener on the + // individual element, instead we use a single listener and rely on event propagation to listen for the event at + // the document level. That listener will walk up the DOM looking for nodes that have either of the classes + // x-selectable or x-unselectable. This simulates the CSS inheritance approach. + // + // IE 10 is expected to support -ms-user-select so the listener may not be required. + me.removeCls(Element.selectableCls); + me.addCls(Element.unselectableCls); + return me; + }, + // statics + statics: { + // This selector will be modified at runtime in the _init() method above + // to include the elements with saved tabindex in the returned set + tabbableSelector: Ext.supports.CSS3NegationSelector ? 'a[href],button,iframe,input,select,textarea,[tabindex]:not([tabindex="-1"]),[contenteditable="true"]' : 'a[href],button,iframe,input,select,textarea,[tabindex],[contenteditable="true"]', + // Anchor and link tags are special; they are only naturally focusable (and tabbable) + // if they have href attribute, and tabbabledness is further platform/browser specific. + // Thus we check it separately in the code. + naturallyFocusableTags: { + BUTTON: true, + IFRAME: true, + EMBED: true, + INPUT: true, + OBJECT: true, + SELECT: true, + TEXTAREA: true, + HTML: Ext.isIE ? true : false, + BODY: Ext.isIE ? false : true + }, + // element is naturally tabbable only in IE8 and below + naturallyTabbableTags: { + BUTTON: true, + IFRAME: true, + INPUT: true, + SELECT: true, + TEXTAREA: true, + OBJECT: Ext.isIE8m ? true : false + }, + inputTags: { + INPUT: true, + TEXTAREA: true + }, + tabbableSavedCounterAttribute: 'data-tabindex-counter', + tabbableSavedValueAttribute: 'data-tabindex-value', + splitCls: function(cls) { + if (typeof cls === 'string') { + cls = cls.split(spacesRe); + } + return cls; + } + }, + // statics + _init: function(E) { + // Allow overriding the attribute name and/or selector; this is + // done only once for performance reasons + E.tabbableSelector += ',[' + E.tabbableSavedCounterAttribute + ']'; + }, + /** + * Adds the given CSS class(es) to this Element. + * @param {String/String[]} names The CSS classes to add separated by space, + * or an array of classes + * @param {String} [prefix] Prefix to prepend to each class. The separator `-` will be + * appended to the prefix. + * @param {String} [suffix] Suffix to append to each class. The separator `-` will be + * prepended to the suffix. + * @return {Ext.dom.Element} this + */ + addCls: function(names, prefix, suffix) { + return this.replaceCls(null, names, prefix, suffix); + }, + /** + * Sets up event handlers to add and remove a css class when the mouse is down and then up on this element (a click effect) + * @param {String} className The class to add + * @param {Function} [testFn] A test function to execute before adding the class. The passed parameter + * will be the Element instance. If this functions returns false, the class will not be added. + * @param {Object} [scope] The scope to execute the testFn in. + * @return {Ext.dom.Element} this + */ + addClsOnClick: function(className, testFn, scope) { + var me = this, + hasTest = Ext.isFunction(testFn); + me.on("mousedown", function() { + if (hasTest && testFn.call(scope || me, me) === false) { + return false; + } + me.addCls(className); + Ext.getDoc().on({ + mouseup: function() { + // In case me was destroyed prior to mouseup + if (me.dom) { + me.removeCls(className); + } + }, + single: true + }); + }); + return me; + }, + /** + * Sets up event handlers to add and remove a css class when this element has the focus + * @param {String} className The class to add + * @param {Function} [testFn] A test function to execute before adding the class. The passed parameter + * will be the Element instance. If this functions returns false, the class will not be added. + * @param {Object} [scope] The scope to execute the testFn in. + * @return {Ext.dom.Element} this + */ + addClsOnFocus: function(className, testFn, scope) { + var me = this, + hasTest = Ext.isFunction(testFn); + me.on("focus", function() { + if (hasTest && testFn.call(scope || me, me) === false) { + return false; + } + me.addCls(className); + }); + me.on("blur", function() { + // In case blur is caused by destruction of me + if (me.dom) { + me.removeCls(className); + } + }); + return me; + }, + /** + * Sets up event handlers to add and remove a css class when the mouse is over this element + * @param {String} className The class to add + * @param {Function} [testFn] A test function to execute before adding the class. The passed parameter + * will be the Element instance. If this functions returns false, the class will not be added. + * @param {Object} [scope] The scope to execute the testFn in. + * @return {Ext.dom.Element} this + */ + addClsOnOver: function(className, testFn, scope) { + var me = this, + hasTest = Ext.isFunction(testFn); + me.hover(function() { + if (hasTest && testFn.call(scope || me, me) === false) { + return; + } + me.addCls(className); + }, function() { + me.removeCls(className); + }); + return me; + }, + addStyles: function(sides, styles) { + var totalSize = 0, + sidesArr = (sides || '').match(wordsRe), + i, + len = sidesArr.length, + side, + styleSides = []; + if (len === 1) { + totalSize = parseFloat(this.getStyle(styles[sidesArr[0]])) || 0; + } else if (len) { + for (i = 0; i < len; i++) { + side = sidesArr[i]; + styleSides.push(styles[side]); + } + //Gather all at once, returning a hash + styleSides = this.getStyle(styleSides); + for (i = 0; i < len; i++) { + side = sidesArr[i]; + totalSize += parseFloat(styleSides[styles[side]]) || 0; + } + } + return totalSize; + }, + addUnits: function(size, units) { + return Element.addUnits(size, units); + }, + // The following 3 methods add just enough of an animation api to make the scroller work + // in Sencha Touch + // TODO: unify touch/ext animations + animate: function(animation) { + animation = new Ext.fx.Animation(animation); + animation.setElement(this); + this._activeAnimation = animation; + animation.on({ + animationend: this._onAnimationEnd, + scope: this + }); + Ext.Animator.run(animation); + return animation; + }, + _onAnimationEnd: function() { + this._activeAnimation = null; + }, + getActiveAnimation: function() { + return this._activeAnimation; + }, + append: function() { + return this.appendChild.apply(this, arguments); + }, + /** + * Appends the passed element(s) to this element + * @param {String/HTMLElement/Ext.dom.Element/Object} el The id or element to insert + * or a DomHelper config + * @param {Boolean} [returnDom=false] True to return the raw DOM element instead + * of Ext.dom.Element + * @return {Ext.dom.Element/HTMLElement} The inserted Ext.dom.Element (or + * HTMLElement if _returnDom_ is _true_). + */ + appendChild: function(el, returnDom) { + var me = this, + insertEl, eLen, e; + if (el.nodeType || el.dom || typeof el === 'string') { + // element + el = Ext.getDom(el); + me.dom.appendChild(el); + return !returnDom ? Ext.get(el) : el; + } else if (el.length) { + // append all elements to a documentFragment + insertEl = Ext.fly(DOC.createDocumentFragment()); + eLen = el.length; + for (e = 0; e < eLen; e++) { + insertEl.appendChild(el[e], returnDom); + } + el = Ext.Array.toArray(insertEl.dom.childNodes); + me.dom.appendChild(insertEl.dom); + return returnDom ? el : new Ext.dom.CompositeElementLite(el); + } else { + // dh config + return me.createChild(el, null, returnDom); + } + }, + /** + * Appends this element to the passed element. + * @param {String/HTMLElement/Ext.dom.Element} el The new parent element. + * The id of the node, a DOM Node or an existing Element. + * @return {Ext.dom.Element} This element. + */ + appendTo: function(el) { + Ext.getDom(el).appendChild(this.dom); + return this; + }, + /** + * More flexible version of {@link #setStyle} for setting style properties. + * + * Styles in object form should be a valid DOM element style property. + * [Valid style property names](http://www.w3schools.com/jsref/dom_obj_style.asp) + * (_along with the supported CSS version for each_) + * + * //
Phineas Flynn
+ * + * var el = Ext.get('my-el'); + * + * el.applyStyles('color: white;'); + * + * el.applyStyles({ + * fontWeight: 'bold', + * backgroundColor: 'gray', + * padding: '10px' + * }); + * + * el.applyStyles(function () { + * if (name.initialConfig.html === 'Phineas Flynn') { + * return 'font-style: italic;'; + * // OR return { fontStyle: 'italic' }; + * } + * }); + * + * @param {String/Object/Function} styles A style specification string, e.g. "width:100px", or object in the form `{width:"100px"}`, or + * a function which returns such a specification. + * @return {Ext.dom.Element} this + */ + applyStyles: function(styles) { + if (styles) { + if (typeof styles === "function") { + styles = styles.call(); + } + if (typeof styles === "string") { + styles = Element.parseStyles(styles); + } + if (typeof styles === "object") { + this.setStyle(styles); + } + } + return this; + }, + /** + * Tries to blur the element. Any exceptions are caught and ignored. + * @return {Ext.dom.Element} this + */ + blur: function() { + var me = this, + dom = me.dom; + // In IE, blurring the body can cause the browser window to hide. + // Blurring the body is redundant, so instead we just focus it + if (dom !== DOC.body) { + try { + dom.blur(); + } catch (e) {} + return me; + } else { + return me.focus(undefined, dom); + } + }, + /** + * When an element is moved around in the DOM, or is hidden using `display:none`, it loses layout, and therefore + * all scroll positions of all descendant elements are lost. + * + * This function caches them, and returns a function, which when run will restore the cached positions. + * In the following example, the Panel is moved from one Container to another which will cause it to lose all scroll positions: + * + * var restoreScroll = myPanel.el.cacheScrollValues(); + * myOtherContainer.add(myPanel); + * restoreScroll(); + * + * @return {Function} A function which will restore all descendant elements of this Element to their scroll + * positions recorded when this function was executed. Be aware that the returned function is a closure which has + * captured the scope of `cacheScrollValues`, so take care to dereference it as soon as not needed - if is it is a `var` + * it will drop out of scope, and the reference will be freed. + */ + cacheScrollValues: function() { + var me = this, + scrollValues = [], + scrolledDescendants = [], + descendants, descendant, i, len; + scrollFly = scrollFly || new Ext.dom.Fly(); + descendants = me.query('*'); + for (i = 0 , len = descendants.length; i < len; i++) { + descendant = descendants[i]; + // use !== 0 for scrollLeft because it can be a negative number + // in RTL mode in some browsers. + if (descendant.scrollTop > 0 || descendant.scrollLeft !== 0) { + scrolledDescendants.push(descendant); + scrollValues.push(scrollFly.attach(descendant).getScroll()); + } + } + return function() { + var scroll, i, len; + for (i = 0 , len = scrolledDescendants.length; i < len; i++) { + scroll = scrollValues[i]; + scrollFly.attach(scrolledDescendants[i]); + scrollFly.setScrollLeft(scroll.left); + scrollFly.setScrollTop(scroll.top); + } + }; + }, + /** + * Centers the Element in either the viewport, or another Element. + * @param {String/HTMLElement/Ext.dom.Element} centerIn element in + * which to center the element. + * @return {Ext.dom.Element} This element + * + * @chainable + */ + center: function(centerIn) { + return this.alignTo(centerIn || DOC, 'c-c'); + }, + /** + * Selects a single *direct* child based on the passed CSS selector (the selector should not contain an id). + * @param {String} selector The CSS selector. + * @param {Boolean} [returnDom=false] `true` to return the DOM node instead of Ext.dom.Element. + * @return {HTMLElement/Ext.dom.Element} The child Ext.dom.Element (or DOM node if `returnDom` is `true`) + */ + child: function(selector, returnDom) { + var me = this, + id; + // If possible, avoid caching the root element. + if (Ext.supports.Selectors2) { + return me.selectNode(':scope>' + selector, !!returnDom); + } else { + // Pull the ID from the DOM (Ext.id also ensures that there *is* an ID). + // If this object is a Flyweight, it will not have an ID + id = me.id != null ? me.id : Ext.get(me).id; + return me.selectNode(Ext.makeIdSelector(id) + " > " + selector, !!returnDom); + } + }, + /** + * Clone this element. + * @param {Boolean} [deep=false] `true` if the children of the node should also be cloned. + * @param {Boolean} [returnDom=false] `true` to return the DOM node instead of Ext.dom.Element. + * @return {HTMLElement/Ext.dom.Element} The newly cloned Ext.dom.Element (or DOM node if `returnDom` is `true`). + */ + clone: function(deep, returnDom) { + var clone = this.dom.cloneNode(deep); + if (Ext.supports.CloneNodeCopiesExpando) { + clearData(clone, deep); + } + return returnDom ? clone : Ext.get(clone); + }, + constrainScrollLeft: function(left) { + var dom = this.dom; + return Math.max(Math.min(left, dom.scrollWidth - dom.clientWidth), 0); + }, + constrainScrollTop: function(top) { + var dom = this.dom; + return Math.max(Math.min(top, dom.scrollHeight - dom.clientHeight), 0); + }, + /** + * Creates the passed DomHelper config and appends it to this element or optionally + * inserts it before the passed child element. + * @param {Object} config DomHelper element config object. If no tag is specified + * (e.g., {tag:'input'}) then a div will be automatically generated with the specified + * attributes. + * @param {HTMLElement} [insertBefore] a child element of this element + * @param {Boolean} [returnDom=false] true to return the dom node instead of creating + * an Element + * @return {Ext.dom.Element/HTMLElement} The new child element (or HTMLElement if + * _returnDom_ is _true_) + */ + createChild: function(config, insertBefore, returnDom) { + config = config || { + tag: 'div' + }; + if (insertBefore) { + return Ext.DomHelper.insertBefore(insertBefore, config, returnDom !== true); + } else { + return Ext.DomHelper.append(this.dom, config, returnDom !== true); + } + }, + /** + * Returns `true` if this element is an ancestor of the passed element, or is + * the element. + * @param {String/HTMLElement/Ext.dom.Element} element The dom element, + * Ext.dom.Element, or id (string) of the dom element to check. + * @return {Boolean} True if this element is an ancestor of el or the el itself, else false + */ + contains: function(element) { + if (!element) { + return false; + } + var me = this, + dom = Ext.getDom(element); + // we need el-contains-itself logic here because isAncestor does not do that: + // https://developer.mozilla.org/en-US/docs/Web/API/Node.contains + return (dom === me.dom) || me.isAncestor(dom); + }, + /** + * Destroys this element by removing it from the cache, removing its DOM reference, + * and removing all of its event listeners. + */ + destroy: function() { + var me = this, + dom = me.dom; + if (me.destroyed) { + Ext.Logger.warn("Cannot destroy Element \"" + me.id + "\". Already destroyed."); + return; + } + if (me.resumeFocusEventsTimer) { + Ext.unasap(me.resumeFocusEventsTimer); + me.resumeFocusEventsTimer = null; + } + if (me.repaintTimer) { + me.repaintTimer = Ext.undefer(me.repaintTimer); + } + if (me.deferFocusTimer) { + me.deferFocusTimer = Ext.undefer(me.deferFocusTimer); + } + if (dom) { + if (dom === DOC.body) { + Ext.raise("Cannot destroy body element."); + } else if (dom === DOC) { + Ext.raise("Cannot destroy document object."); + } else if (dom === WIN) { + Ext.raise("Cannot destroy window object"); + } + } + if (dom && dom.parentNode) { + dom.parentNode.removeChild(dom); + } + if (me.$ripples) { + me.destroyAllRipples(); + } + me.collect(); + }, + detach: function() { + var dom = this.dom, + component = this.component; + if (dom && dom.parentNode && dom.tagName !== 'BODY') { + // Ensure focus is never lost + if (component) { + component.revertFocus(); + } + dom.parentNode.removeChild(dom); + } + return this; + }, + /** + * Disables the shadow element created by {@link #enableShadow}. + * @private + */ + disableShadow: function() { + var shadow = this.shadow; + if (shadow) { + shadow.hide(); + shadow.disabled = true; + } + }, + /** + * Disables the shim element created by {@link #enableShim}. + * @private + */ + disableShim: function() { + var shim = this.shim; + if (shim) { + shim.hide(); + shim.disabled = true; + } + }, + /** + * @private + */ + doReplaceWith: function(element) { + var dom = this.dom; + dom.parentNode.replaceChild(Ext.getDom(element), dom); + }, + /** + * @private + * A scrollIntoView implementation for scrollIntoView/rtlScrollIntoView to call + * after current scrollX has been determined. + */ + doScrollIntoView: function(container, hscroll, animate, highlight, getScrollX, scrollTo) { + scrollFly = scrollFly || new Ext.dom.Fly(); + var me = this, + dom = me.dom, + scrollX = scrollFly.attach(container)[getScrollX](), + scrollY = container.scrollTop, + position = me.getScrollIntoViewXY(container, scrollX, scrollY), + newScrollX = position.x, + newScrollY = position.y; + // Highlight upon end of scroll + if (highlight) { + if (animate) { + animate = Ext.apply({ + listeners: { + afteranimate: function() { + scrollFly.attach(dom).highlight(); + } + } + }, animate); + } else { + scrollFly.attach(dom).highlight(); + } + } + if (newScrollY !== scrollY) { + scrollFly.attach(container).scrollTo('top', newScrollY, animate); + } + if (hscroll !== false && (newScrollX !== scrollX)) { + scrollFly.attach(container)[scrollTo]('left', newScrollX, animate); + } + return me; + }, + /** + * Selects a single child at any depth below this element based on the passed + * CSS selector (the selector should not contain an id). + * + * Use {@link #getById} if you need to get a reference to a child element via id. + * + * @param {String} selector The CSS selector + * @param {Boolean} [returnDom=false] `true` to return the DOM node instead of Ext.dom.Element + * @return {HTMLElement/Ext.dom.Element} The child Ext.dom.Element (or DOM node if `returnDom` is `true`) + */ + down: function(selector, returnDom) { + return this.selectNode(selector, !!returnDom); + }, + /** + * Enables a shadow element that will always display behind this element + * @param {Object} [options] Configuration options for the shadow + * @param {Number} [options.offset=4] Number of pixels to offset the shadow + * @param {String} [options.mode='sides'] The shadow display mode. Supports the following + * options: + * + * - `'sides'`: Shadow displays on both sides and bottom only + * - `'frame'`: Shadow displays equally on all four sides + * - `'drop'`: Traditional bottom-right drop shadow + * - `'bottom'`: Shadow is offset to the bottom + * + * @param {Boolean} [options.animate=false] `true` to animate the shadow while + * the element is animating. By default the shadow will be hidden during animation. + * @param {Boolean} isVisible (private) + * @private + */ + enableShadow: function(options, isVisible) { + var me = this, + shadow = me.shadow || (me.shadow = new Ext.dom.Shadow(Ext.apply({ + target: me + }, options))), + shim = me.shim; + if (shim) { + shim.offsets = shadow.outerOffsets; + shim.shadow = shadow; + shadow.shim = shim; + } + // Components pass isVisible to avoid the extra dom read to determine + // whether or not this element is visible. + if (isVisible === true || (isVisible !== false && me.isVisible())) { + // the shadow element may have just been retrieved from an OverlayPool, so + // we need to explicitly show it to be sure hidden styling is removed + shadow.show(); + } else { + shadow.hide(); + } + shadow.disabled = false; + }, + /** + * Enables an iframe shim for this element to keep windowed objects from + * showing through. The position, size, and visibility of the shim will be + * automatically synchronized as the position, size, and visibility of this + * Element are changed. + * @param {Object} [options] Configuration options for the shim + * @param {Boolean} isVisible (private) + * @return {Ext.dom.Shim} The new Shim + * @private + */ + enableShim: function(options, isVisible) { + var me = this, + shim = me.shim || (me.shim = new Ext.dom.Shim(Ext.apply({ + target: me + }, options))), + shadow = me.shadow; + if (shadow) { + shim.offsets = shadow.outerOffsets; + shim.shadow = shadow; + shadow.shim = shim; + } + // Components pass isVisible to avoid the extra dom read to determine + // whether or not this element is visible. + if (isVisible === true || (isVisible !== false && me.isVisible())) { + // the shim element may have just been retrieved from an OverlayPool, so + // we need to explicitly show it to be sure hidden styling is removed + shim.show(); + } else { + shim.hide(); + } + shim.disabled = false; + return shim; + }, + /** + * Looks at this node and then at parent nodes for a match of the passed simple selector. + * @param {String} simpleSelector The simple selector to test. See {@link Ext.dom.Query} + * for information about simple selectors. + * @param {Number/String/HTMLElement/Ext.dom.Element} [limit] + * The max depth to search as a number or an element which causes the upward traversal to stop + * and is **not** considered for inclusion as the result. (defaults to 50 || document.documentElement) + * @param {Boolean} [returnEl=false] True to return a Ext.dom.Element object instead of DOM node + * @return {HTMLElement/Ext.dom.Element} The matching DOM node (or + * Ext.dom.Element if _returnEl_ is _true_). Or null if no match was found. + */ + findParent: function(simpleSelector, limit, returnEl) { + var me = this, + target = me.dom, + topmost = docEl, + depth = 0; + if (limit || limit === 0) { + if (typeof limit !== 'number') { + topmost = Ext.getDom(limit); + limit = Number.MAX_VALUE; + } + } else { + // No limit passed, default to 50 + limit = 50; + } + while (target && target.nodeType === 1 && depth < limit && target !== topmost) { + if (Ext.fly(target).is(simpleSelector)) { + return returnEl ? Ext.get(target) : target; + } + depth++; + target = target.parentNode; + } + return null; + }, + /** + * Looks at parent nodes for a match of the passed simple selector. + * @param {String} simpleSelector The simple selector to test. See {@link Ext.dom.Query} + * for information about simple selectors. + * @param {Number/String/HTMLElement/Ext.dom.Element} [limit] + * The max depth to search as a number or an element which causes the upward traversal to stop + * and is **not** considered for inclusion as the result. (defaults to 50 || document.documentElement) + * @param {Boolean} [returnEl=false] True to return a Ext.dom.Element object instead of DOM node + * @return {HTMLElement/Ext.dom.Element} The matching DOM node (or + * Ext.dom.Element if _returnEl_ is _true_). Or null if no match was found. + */ + findParentNode: function(simpleSelector, limit, returnEl) { + var p = Ext.fly(this.dom.parentNode); + return p ? p.findParent(simpleSelector, limit, returnEl) : null; + }, + /** + * Gets the first child, skipping text nodes + * @param {String} [selector] Find the next sibling that matches the passed simple selector. + * See {@link Ext.dom.Query} for information about simple selectors. + * @param {Boolean} [returnDom=false] `true` to return a raw DOM node instead of an Ext.dom.Element + * @return {Ext.dom.Element/HTMLElement} The first child or null + */ + first: function(selector, returnDom) { + return this.matchNode('nextSibling', 'firstChild', selector, returnDom); + }, + /** + * Try to focus the element either immediately or after a timeout + * if `defer` argument is specified. + * + * @param {Number} [defer] Milliseconds to defer the focus + * @param {HTMLElement} [dom] (private) + * + * @return {Ext.dom.Element} this + */ + focus: function(defer, dom) { + var me = this; + dom = dom || me.dom; + if (Number(defer)) { + Ext.defer(me.focus, defer, me, [ + null, + dom + ]); + } else { + Ext.GlobalEvents.fireEvent('beforefocus', dom); + dom.focus(); + } + return me; + }, + /** + * @private + * Removes the element from the cache and removes listeners. + * Used for cleaning up orphaned elements after they have been removed from the dom. + * Similar to {@link #destroy} except it assumes the element has already been + * removed from the dom. + */ + collect: function() { + var me = this, + dom = me.dom, + shadow = me.shadow, + shim = me.shim; + // The parent destroy sets the destroy to emptyFn, which we don't + // want on a shared fly + if (!me.isFly) { + me.mixins.observable.destroy.call(me); + delete Ext.cache[me.id]; + me.el = null; + } + if (dom) { + dom._extData = me.dom = null; + } + // we do not destroy the shadow and shim because they are returned to their + // OverlayPools for reuse. + if (shadow) { + shadow.hide(); + me.shadow = null; + } + if (shim) { + shim.hide(); + me.shim = null; + } + }, + getAnchorToXY: function(el, anchor, local, mySize) { + return el.getAnchorXY(anchor, local, mySize); + }, + /** + * Returns the value of an attribute from the element's underlying DOM node. + * @param {String} name The attribute name. + * @param {String} [namespace] The namespace in which to look for the attribute. + * @return {String} The attribute value. + */ + getAttribute: function(name, namespace) { + var dom = this.dom; + return namespace ? (dom.getAttributeNS(namespace, name) || dom.getAttribute(namespace + ":" + name)) : (dom.getAttribute(name) || dom[name] || null); + }, + /** + * Returns an object containing a map of all attributes of this element's DOM node. + * + * @return {Object} Key/value pairs of attribute names and their values. + */ + getAttributes: function() { + var attributes = this.dom.attributes, + result = {}, + attr, i, len; + for (i = 0 , len = attributes.length; i < len; i++) { + attr = attributes[i]; + result[attr.name] = attr.value; + } + return result; + }, + /** + * Gets the bottom Y coordinate of the element (element Y position + element height) + * @param {Boolean} local True to get the local css position instead of page + * coordinate + * @return {Number} + */ + getBottom: function(local) { + return (local ? this.getLocalY() : this.getY()) + this.getHeight(); + }, + /** + * Returns a child element of this element given its `id`. + * @param {String} id The id of the desired child element. + * @param {Boolean} [asDom=false] True to return the DOM element, false to return a + * wrapped Element object. + * @return {Ext.dom.Element/HTMLElement} The child element (or HTMLElement if + * _asDom_ is _true_). Or null if no match was found. + */ + getById: function(id, asDom) { + // for normal elements getElementById is the best solution, but if the el is + // not part of the document.body, we have to resort to querySelector + var dom = DOC.getElementById(id) || this.dom.querySelector(Ext.makeIdSelector(id)); + return asDom ? dom : (dom ? Ext.get(dom) : null); + }, + getBorderPadding: function() { + var paddingWidth = this.getStyle(paddingsTLRB), + bordersWidth = this.getStyle(bordersTLRB); + return { + beforeX: (parseFloat(bordersWidth[borders.l]) || 0) + (parseFloat(paddingWidth[paddings.l]) || 0), + afterX: (parseFloat(bordersWidth[borders.r]) || 0) + (parseFloat(paddingWidth[paddings.r]) || 0), + beforeY: (parseFloat(bordersWidth[borders.t]) || 0) + (parseFloat(paddingWidth[paddings.t]) || 0), + afterY: (parseFloat(bordersWidth[borders.b]) || 0) + (parseFloat(paddingWidth[paddings.b]) || 0) + }; + }, + /** + * @private + */ + getBorders: function() { + var bordersWidth = this.getStyle(bordersTLRB); + return { + beforeX: (parseFloat(bordersWidth[borders.l]) || 0), + afterX: (parseFloat(bordersWidth[borders.r]) || 0), + beforeY: (parseFloat(bordersWidth[borders.t]) || 0), + afterY: (parseFloat(bordersWidth[borders.b]) || 0) + }; + }, + /** + * Gets the width of the border(s) for the specified side(s) + * @param {String} side Can be t, l, r, b or any combination of those to add + * multiple values. For example, passing `'lr'` would get the border **l**eft + * width + the border **r**ight width. + * @return {Number} The width of the sides passed added together + */ + getBorderWidth: function(side) { + return this.addStyles(side, borders); + }, + /** + * Returns an object holding as properties this element's CSS classes. The object + * can be modified to effect arbitrary class manipulations that won't immediately + * go to the DOM. When completed, the DOM node can be updated by calling + * {@link #setClassMap setClassMap}. The values of the properties should either + * be set to truthy values (such as `1` or `true`) or removed via `delete`. + * + * var classes = el.getClassMap(); + * + * // Add the 'foo' class: + * classes.foo = 1; + * + * // Remove the 'bar' class: + * delete classes.bar; + * + * // Update the DOM in one step: + * el.setClassMap(classes); + * + * @param {Boolean} [clone=true] (private) Pass `false` to return the underlying + * (readonly) object. + * @return {Object} + * @since 6.5.0 + */ + getClassMap: function(clone) { + var data = this.getData(); + if (data) { + data = data.classMap; + if (clone !== false) { + data = Ext.apply({}, data); + } + } + return data; + }, + /** + * Returns this element's data object. This object holds options that may be + * needed by an `Ext.fly()` call when there is no (cached) `Ext.dom.Element` + * instance tracked. + * + * This method will only return `null` if this instance has no associated DOM + * node. If the DOM node does not have a data object, one will be created. To + * avoid this creation, use {@link #peekData peekData()} instead. + * + * @param {Boolean} [sync=true] (private) Pass `false` to skip synchronization. + * @return {Object} + * @private + */ + getData: function(sync) { + var dom = this.dom, + data; + if (dom) { + data = dom._extData || (dom._extData = {}); + if (sync !== false && !data.isSynchronized) { + this.synchronize(); + } + } + return data || null; + }, + getFirstChild: function() { + return Ext.get(this.dom.firstElementChild); + }, + getLastChild: function() { + return Ext.get(this.dom.lastElementChild); + }, + /** + * Returns the offset height of the element. + * @param {Boolean} [contentHeight] `true` to get the height minus borders and padding. + * @param {Boolean} [preciseHeight] `true` to get the precise height + * @return {Number} The element's height. + */ + getHeight: function(contentHeight, preciseHeight) { + var me = this, + dom = me.dom, + hidden = me.isStyle('display', 'none'), + height, floating; + if (hidden) { + return 0; + } + // Use the viewport height if they are asking for body height + if (dom.nodeName === 'BODY') { + height = Element.getViewportHeight(); + } else { + if (preciseHeight) { + height = dom.getBoundingClientRect().height; + } else { + height = dom.offsetHeight; + // SVG nodes do not have offsetHeight, so use boundingClientRect instead. + if (height == null) { + height = dom.getBoundingClientRect().height; + } + } + } + // IE9/10 Direct2D dimension rounding bug + if (Ext.supports.Direct2DBug) { + floating = me.adjustDirect2DDimension(HEIGHT); + if (preciseHeight) { + height += floating; + } else if (floating > 0 && floating < 0.5) { + height++; + } + } + if (contentHeight) { + height -= me.getBorderWidth("tb") + me.getPadding("tb"); + } + return (height < 0) ? 0 : height; + }, + /** + * Returns the `innerHTML` of an Element or an empty string if the element's + * dom no longer exists. + * @return {String} + */ + getHtml: function() { + return this.dom ? this.dom.innerHTML : ''; + }, + /** + * Gets the left X coordinate + * @param {Boolean} local True to get the local css position instead of + * page coordinate + * @return {Number} + */ + getLeft: function(local) { + return local ? this.getLocalX() : this.getX(); + }, + getLocalX: function() { + var me = this, + offsetParent, + x = me.getStyle('left'); + if (!x || x === 'auto') { + x = 0; + } else if (pxRe.test(x)) { + x = parseFloat(x); + } else { + x = me.getX(); + // Reading offsetParent causes forced async layout. + // Do not do it unless needed. + offsetParent = me.dom.offsetParent; + if (offsetParent) { + x -= Ext.fly(offsetParent).getX(); + } + } + return x; + }, + getLocalXY: function() { + var me = this, + offsetParent, + style = me.getStyle([ + 'left', + 'top' + ]), + x = style.left, + y = style.top; + if (!x || x === 'auto') { + x = 0; + } else if (pxRe.test(x)) { + x = parseFloat(x); + } else { + x = me.getX(); + // Reading offsetParent causes forced async layout. + // Do not do it unless needed. + offsetParent = me.dom.offsetParent; + if (offsetParent) { + x -= Ext.fly(offsetParent).getX(); + } + } + if (!y || y === 'auto') { + y = 0; + } else if (pxRe.test(y)) { + y = parseFloat(y); + } else { + y = me.getY(); + // Reading offsetParent causes forced async layout. + // Do not do it unless needed. + offsetParent = me.dom.offsetParent; + if (offsetParent) { + y -= Ext.fly(offsetParent).getY(); + } + } + return [ + x, + y + ]; + }, + getLocalY: function() { + var me = this, + offsetParent, + y = me.getStyle('top'); + if (!y || y === 'auto') { + y = 0; + } else if (pxRe.test(y)) { + y = parseFloat(y); + } else { + y = me.getY(); + // Reading offsetParent causes forced async layout. + // Do not do it unless needed. + offsetParent = me.dom.offsetParent; + if (offsetParent) { + y -= Ext.fly(offsetParent).getY(); + } + } + return y; + }, + /** + * @method + * + * Returns an object with properties top, left, right and bottom representing the margins of this element unless sides is passed, + * then it returns the calculated width of the sides (see {@link #getPadding}). + * @param {String} [sides] Any combination of 'l', 'r', 't', 'b' to get the sum of those sides. + * @return {Object/Number} + */ + getMargin: (function() { + var hash = { + t: "top", + l: "left", + r: "right", + b: "bottom" + }, + allMargins = [ + 'margin-top', + 'margin-left', + 'margin-right', + 'margin-bottom' + ]; + return function(side) { + var me = this, + style, key, o; + if (!side) { + style = me.getStyle(allMargins); + o = {}; + if (style && typeof style === 'object') { + o = {}; + for (key in margins) { + o[key] = o[hash[key]] = parseFloat(style[margins[key]]) || 0; + } + } + } else { + o = me.addStyles(side, margins); + } + return o; + }; + })(), + /** + * Gets the width of the padding(s) for the specified side(s). + * @param {String} side Can be t, l, r, b or any combination of those to add + * multiple values. For example, passing `'lr'` would get the padding **l**eft + + * the padding **r**ight. + * @return {Number} The padding of the sides passed added together. + */ + getPadding: function(side) { + return this.addStyles(side, paddings); + }, + getParent: function() { + return Ext.get(this.dom.parentNode); + }, + /** + * Gets the right X coordinate of the element (element X position + element width) + * @param {Boolean} local True to get the local css position instead of page + * coordinates + * @return {Number} + */ + getRight: function(local) { + return (local ? this.getLocalX() : this.getX()) + this.getWidth(); + }, + /** + * Returns the current scroll position of the element. + * @return {Object} An object containing the scroll position in the format + * `{left: (scrollLeft), top: (scrollTop)}` + */ + getScroll: function() { + var me = this, + dom = me.dom, + docElement = docEl, + left, top, + body = DOC.body; + if (dom === DOC || dom === body) { + // the scrollLeft/scrollTop may be either on the body or documentElement, + // depending on browser. It is possible to use window.pageXOffset/pageYOffset + // in most modern browsers but this complicates things when in rtl mode because + // pageXOffset does not always behave the same as scrollLeft when direction is + // rtl. (e.g. pageXOffset can be an offset from the right, while scrollLeft + // is offset from the left, one can be positive and the other negative, etc.) + // To avoid adding an extra layer of feature detection in rtl mode to deal with + // these differences, it's best just to always use scrollLeft/scrollTop + left = docElement.scrollLeft || (body ? body.scrollLeft : 0); + top = docElement.scrollTop || (body ? body.scrollTop : 0); + } else { + left = dom.scrollLeft; + top = dom.scrollTop; + } + return { + left: left, + top: top + }; + }, + /** + * Gets the x and y coordinates needed for scrolling an element into view within + * a given container. These coordinates translate into the scrollLeft and scrollTop + * positions that will need to be set on an ancestor of the element in order to make + * this element visible within its container. + * @param {String/HTMLElement/Ext.Element/Ext.util.Region} container The container + * @param {Number} scrollX The container's current scroll position on the x axis + * @param {Number} scrollY The container's current scroll position on the y axis + * @param {Object} [align] The alignment for the scroll. + * @param {'start'/'center'/'end'} [align.x] The alignment of the x scroll. If not + * specified, the minimum will be done to make the element visible. The behavior is undefined + * if the request cannot be honored. If the alignment is suffixed with a ?, the alignment will + * only take place if the item is not already in the visible area. + * @param {'start'/'center'/'end'} [align.y] The alignment of the x scroll. If not + * specified, the minimum will be done to make the element visible. The behavior is undefined + * if the request cannot be honored. If the alignment is suffixed with a ?, the alignment will + * only take place if the item is not already in the visible area. + * @return {Object} An object with "x" and "y" properties + * @private + */ + getScrollIntoViewXY: function(container, scrollX, scrollY, align) { + align = align || empty; + var me = this, + dom = me.dom, + offsets, clientWidth, clientHeight; + if (container.isRegion) { + clientHeight = container.height; + clientWidth = container.width; + } else { + container = Ext.getDom(container); + clientHeight = container.clientHeight; + clientWidth = container.clientWidth; + } + offsets = me.getOffsetsTo(container); + return { + y: me.calcScrollPos(offsets[1] + scrollY, dom.offsetHeight, scrollY, clientHeight, align.y), + x: me.calcScrollPos(offsets[0] + scrollX, dom.offsetWidth, scrollX, clientWidth, align.x) + }; + }, + calcScrollPos: function(start, size, viewStart, viewSize, align) { + var end = start + size, + viewEnd = viewStart + viewSize, + force = align && !endsQuestionRe.test(align), + ret = viewStart; + if (!force) { + if (align) { + align = align.slice(0, -1); + } + if (size > viewSize || start < viewStart) { + align = align || 'start'; + force = true; + } else if (end > viewEnd) { + align = align || 'end'; + force = true; + } + } + if (force) { + if (align === 'start') { + ret = start; + } else if (align === 'center') { + ret = Math.max(0, start - Math.floor((viewSize / 2))); + } else if (align === 'end') { + ret = Math.max(0, end - viewSize); + } + } + return ret; + }, + /** + * Gets the left scroll position + * @return {Number} The left scroll position + */ + getScrollLeft: function() { + var dom = this.dom; + if (dom === DOC || dom === DOC.body) { + return this.getScroll().left; + } else { + return dom.scrollLeft; + } + }, + /** + * Gets the top scroll position + * @return {Number} The top scroll position + */ + getScrollTop: function() { + var dom = this.dom; + if (dom === DOC || dom === DOC.body) { + return this.getScroll().top; + } else { + return dom.scrollTop; + } + }, + /** + * Returns the size of the element. + * @param {Boolean} [contentSize] `true` to get the width/size minus borders and padding. + * @return {Object} An object containing the element's size: + * @return {Number} return.width + * @return {Number} return.height + */ + getSize: function(contentSize) { + return { + width: this.getWidth(contentSize), + height: this.getHeight(contentSize) + }; + }, + /** + * Returns a named style property based on computed/currentStyle (primary) and + * inline-style if primary is not available. + * + * @param {String/String[]} property The style property (or multiple property names + * in an array) whose value is returned. + * @param {Boolean} [inline=false] if `true` only inline styles will be returned. + * @return {String/Object} The current value of the style property for this element + * (or a hash of named style values if multiple property arguments are requested). + * @method + */ + getStyle: function(property, inline) { + var me = this, + dom = me.dom, + multiple = typeof property !== 'string', + hooks = me.styleHooks, + prop = property, + props = prop, + len = 1, + domStyle, camel, values, hook, out, style, i; + if (multiple) { + values = {}; + prop = props[0]; + i = 0; + if (!(len = props.length)) { + return values; + } + } + if (!dom || dom.documentElement) { + return values || ''; + } + domStyle = dom.style; + if (inline) { + style = domStyle; + } else { + // Caution: Firefox will not render "presentation" (i.e. computed styles) in + // iframes that are display:none or those inheriting display:none. Similar + // issues with legacy Safari. + // + style = dom.ownerDocument.defaultView.getComputedStyle(dom, null); + // fallback to inline style if rendering context not available + if (!style) { + inline = true; + style = domStyle; + } + } + do { + hook = hooks[prop]; + if (!hook) { + hooks[prop] = hook = { + name: Element.normalize(prop) + }; + } + if (hook.get) { + out = hook.get(dom, me, inline, style); + } else { + camel = hook.name; + out = style[camel]; + } + if (!multiple) { + return out; + } + values[prop] = out; + prop = props[++i]; + } while (i < len); + return values; + }, + getStyleValue: function(name) { + return this.dom.style.getPropertyValue(name); + }, + getCaretPos: function() { + var dom = this.dom, + pos, selection; + if (inputTypeSelectionSupported.test(dom.type)) { + pos = dom.selectionStart; + selection = (typeof pos !== 'number') && this.getTextSelection(); + if (selection) { + pos = selection[0]; + } + } else { + Ext.raise('Input type of "' + dom.type + '" does not support selectionStart'); + } + return pos; + }, + setCaretPos: function(pos) { + this.selectText(pos, pos); + }, + /** + * Returns the selection range of an input element as an array of three values: + * + * [ start, end, direction ] + * + * These have the same meaning as the parameters to `selectText`. + * @return {Array} + * @since 6.5.0 + */ + getTextSelection: function() { + var dom = this.dom; + if (inputTypeSelectionSupported.test(dom.type)) { + return [ + dom.selectionStart, + dom.selectionEnd, + dom.selectionDirection + ]; + } else { + Ext.raise('Input type of "' + this.dom.type + '" does not support selectionStart, selectionEnd and selectionDirection'); + return []; + } + }, + // FYI - Classic overrides this for older browsers... + /** + * Selects the specified contents of the input element (all by default). + * @param {Number} [start=0] The starting index to select. + * @param {Number} [end] The end index to select (defaults to all remaining text). + * @param {"f"/"b"/"forward"/"backward"} [direction="f"] Pass "f" for forward, + * "b" for backwards. + * @return {Ext.dom.Element} this + * @chainable + * @since 6.5.0 + */ + selectText: function(start, end, direction) { + var me = this, + range, + dom = me.dom, + len; + if (dom && inputTypeSelectionSupported.test(dom.type)) { + start = start || 0; + len = dom.value.length; + if (end === undefined) { + end = len; + } + direction = selectDir[direction] || direction || 'forward'; + if (dom.setSelectionRange) { + dom.setSelectionRange(start, end, direction); + } else if (dom.createTextRange) { + if (start > end) { + start = end; + } + range = dom.createTextRange(); + range.moveStart('character', start); + range.moveEnd('character', -(len - end)); + range.select(); + } + } else if (!inputTypeSelectionSupported.test(dom.type)) { + Ext.raise('Input type of "' + dom.type + '" does not support setSelectionRange'); + } + return me; + }, + /** + * Gets the top Y coordinate + * @param {Boolean} local True to get the local css position instead of page + * coordinates + * @return {Number} + */ + getTop: function(local) { + return local ? this.getLocalY() : this.getY(); + }, + /** + * Returns this element's touch action. (see {@link #setTouchAction}) + * + * The returned object is shared and should not be mutated. + * + * @returns {Object} + */ + getTouchAction: function() { + return Ext.dom.TouchAction.get(this.dom); + }, + /** + * Returns the value of the `value` attribute. + * @param {Boolean} asNumber `true` to parse the value as a number. + * @return {String/Number} + */ + getValue: function(asNumber) { + var value = this.dom.value; + return asNumber ? parseInt(value, 10) : value; + }, + /** + * Returns the dimensions of the element available to lay content out in. For + * most elements this is the clientHeight/clientWidth. If the element is + * the document/document.body the window's innerHeight/innerWidth is returned + * + * If the element (or any ancestor element) has CSS style `display: none`, the + * dimensions will be zero. + * + * @return {Object} Object describing width and height. + * @return {Number} return.width + * @return {Number} return.height + */ + getViewSize: function() { + var dom = this.dom; + if (dom === DOC || dom === DOC.body) { + return { + width: Element.getViewportWidth(), + height: Element.getViewportHeight() + }; + } else { + return { + width: dom.clientWidth, + height: dom.clientHeight + }; + } + }, + getVisibilityMode: function() { + var me = this, + data = me.getData(), + mode = data.visibilityMode; + if (mode === undefined) { + data.visibilityMode = mode = Element.DISPLAY; + } + return mode; + }, + /** + * Returns the offset width of the element. + * @param {Boolean} [contentWidth] `true` to get the width minus borders and padding. + * @param {Boolean} [preciseWidth] `true` to get the precise width + * @return {Number} The element's width. + */ + getWidth: function(contentWidth, preciseWidth) { + var me = this, + dom = me.dom, + hidden = me.isStyle('display', 'none'), + rect, width, floating; + if (hidden) { + return 0; + } + // Gecko will in some cases report an offsetWidth that is actually less than the width of the + // text contents, because it measures fonts with sub-pixel precision but rounds the calculated + // value down. Using getBoundingClientRect instead of offsetWidth allows us to get the precise + // subpixel measurements so we can force them to always be rounded up. See + // https://bugzilla.mozilla.org/show_bug.cgi?id=458617 + // Rounding up ensures that the width includes the full width of the text contents. + if (Ext.supports.BoundingClientRect) { + rect = dom.getBoundingClientRect(); + width = (me.vertical && !Ext.supports.RotatedBoundingClientRect) ? (rect.bottom - rect.top) : (rect.right - rect.left); + width = preciseWidth ? width : Math.ceil(width); + } else { + width = dom.offsetWidth; + } + // IE9/10 Direct2D dimension rounding bug: https://sencha.jira.com/browse/EXTJSIV-603 + // there is no need make adjustments for this bug when the element is vertically + // rotated because the width of a vertical element is its rotated height + if (Ext.supports.Direct2DBug && !me.vertical) { + // get the fractional portion of the sub-pixel precision width of the element's text contents + floating = me.adjustDirect2DDimension(WIDTH); + if (preciseWidth) { + width += floating; + } + // IE9 also measures fonts with sub-pixel precision, but unlike Gecko, instead of rounding the offsetWidth down, + // it rounds to the nearest integer. This means that in order to ensure that the width includes the full + // width of the text contents we need to increment the width by 1 only if the fractional portion is less than 0.5 + else if (floating > 0 && floating < 0.5) { + width++; + } + } + if (contentWidth) { + width -= me.getBorderWidth("lr") + me.getPadding("lr"); + } + return (width < 0) ? 0 : width; + }, + /** + * Gets element X position in page coordinates + * + * @return {Number} + */ + getX: function() { + return this.getXY()[0]; + }, + /** + * Gets element X and Y positions in page coordinates + * + * @return {Array} [x, y] + */ + getXY: function() { + var round = Math.round, + dom = this.dom, + body = DOC.body, + x = 0, + y = 0, + bodyRect, rect; + if (dom !== DOC && dom !== body) { + // IE (including IE10) throws an error when getBoundingClientRect + // is called on an element not attached to dom + try { + bodyRect = body.getBoundingClientRect(); + rect = dom.getBoundingClientRect(); + x = rect.left - bodyRect.left; + y = rect.top - bodyRect.top; + } catch (ex) {} + } + return [ + round(x), + round(y) + ]; + }, + /** + * Gets element Y position in page coordinates + * + * @return {Number} + */ + getY: function() { + return this.getXY()[1]; + }, + /** + * Returns this element's z-index + * @return {Number} + */ + getZIndex: function() { + return parseInt(this.getStyle('z-index'), 10); + }, + /** + * Checks if the specified CSS class exists on this element's DOM node. + * @param {String} name The CSS class to check for. + * @return {Boolean} `true` if the class exists, else `false`. + */ + hasCls: function(name) { + var classMap = this.getClassMap(); + return classMap.hasOwnProperty(name); + }, + /** + * Hide this element - Uses display mode to determine whether to use "display", + * "visibility", or "offsets". See {@link #setVisible}. + * @return {Ext.dom.Element} this + */ + hide: function() { + return this.setVisible(false); + }, + /** + * Sets up event handlers to call the passed functions when the mouse is moved into and out of the Element. + * @param {Function} overFn The function to call when the mouse enters the Element. + * @param {Function} outFn The function to call when the mouse leaves the Element. + * @param {Object} [scope] The scope (`this` reference) in which the functions are executed. Defaults + * to the Element's DOM element. + * @param {Object} [options] Options for the listener. See {@link Ext.util.Observable#addListener the + * options parameter}. + * @return {Ext.dom.Element} this + */ + hover: function(overFn, outFn, scope, options) { + var me = this; + me.on('mouseenter', overFn, scope || me.dom, options); + me.on('mouseleave', outFn, scope || me.dom, options); + return me; + }, + /** + * Returns the index of the given element in the `childNodes` of this element. If + * not present, `-1` is returned. + * + * @param {String/HTMLElement/Ext.dom.Element} childEl The potential child element. + * @return {number} The index of `childEl` in `childNodes` or `-1` if not found. + * @since 6.5.0 + */ + indexOf: function(childEl) { + var children = this.dom, + c = childEl && Ext.getDom(childEl); + children = children && children.childNodes; + return (c && children) ? Array.prototype.indexOf.call(children, c) : -1; + }, + /** + * Inserts this element after the passed element in the DOM. + * @param {String/HTMLElement/Ext.dom.Element} el The element to insert after. + * The `id` of the node, a DOM Node or an existing Element. + * @return {Ext.dom.Element} This element. + */ + insertAfter: function(el) { + el = Ext.getDom(el); + el.parentNode.insertBefore(this.dom, el.nextSibling); + return this; + }, + /** + * Inserts this element before the passed element in the DOM. + * @param {String/HTMLElement/Ext.dom.Element} el The element before which this element will be inserted. + * The id of the node, a DOM Node or an existing Element. + * @return {Ext.dom.Element} This element. + */ + insertBefore: function(el) { + el = Ext.getDom(el); + el.parentNode.insertBefore(this.dom, el); + return this; + }, + /** + * Inserts (or creates) an element as the first child of this element + * @param {String/HTMLElement/Ext.dom.Element/Object} el The id or element to insert + * or a DomHelper config to create and insert + * @param {Boolean} [returnDom=false] True to return the raw DOM element instead + * of Ext.dom.Element + * @return {Ext.dom.Element/HTMLElement} The new child element (or HTMLElement if + * _returnDom_ is _true_). + */ + insertFirst: function(el, returnDom) { + el = el || {}; + if (el.nodeType || el.dom || typeof el === 'string') { + // element + el = Ext.getDom(el); + this.dom.insertBefore(el, this.dom.firstChild); + return !returnDom ? Ext.get(el) : el; + } else { + // dh config + return this.createChild(el, this.dom.firstChild, returnDom); + } + }, + /** + * Inserts an html fragment into this element + * @param {String} where Where to insert the html in relation to this element - beforeBegin, afterBegin, beforeEnd, afterEnd. + * See {@link Ext.dom.Helper#insertHtml} for details. + * @param {String} html The HTML fragment + * @param {Boolean} [returnEl=false] True to return an Ext.dom.Element + * @return {HTMLElement/Ext.dom.Element} The inserted node (or nearest related if more than 1 inserted) + */ + insertHtml: function(where, html, returnEl) { + var el = Ext.DomHelper.insertHtml(where, this.dom, html); + return returnEl ? Ext.get(el) : el; + }, + /** + * Inserts (or creates) the passed element (or DomHelper config) as a sibling of this element + * @param {String/HTMLElement/Ext.dom.Element/Object/Array} el The id, element to insert or a DomHelper config + * to create and insert *or* an array of any of those. + * @param {String} [where='before'] 'before' or 'after' + * @param {Boolean} [returnDom=false] True to return the raw DOM element instead of Ext.dom.Element + * @return {Ext.dom.Element/HTMLElement} The inserted Ext.dom.Element (or + * HTMLElement if _returnDom_ is _true_). If an array is passed, the last + * inserted element is returned. + */ + insertSibling: function(el, where, returnDom) { + var me = this, + DomHelper = Ext.DomHelper, + isAfter = (where || 'before').toLowerCase() === 'after', + rt, insertEl, eLen, e; + if (Ext.isIterable(el)) { + eLen = el.length; + insertEl = Ext.fly(DOC.createDocumentFragment()); + // append all elements to a documentFragment + if (Ext.isArray(el)) { + for (e = 0; e < eLen; e++) { + rt = insertEl.appendChild(el[e], returnDom); + } + } else // Iterable, but not an Array, must be an HtmlCollection + { + for (e = 0; e < eLen; e++) { + insertEl.dom.appendChild(rt = el[0]); + } + if (returnDom === false) { + rt = Ext.get(rt); + } + } + // Insert fragment into document + me.dom.parentNode.insertBefore(insertEl.dom, isAfter ? me.dom.nextSibling : me.dom); + return rt; + } + el = el || {}; + if (el.nodeType || el.dom) { + rt = me.dom.parentNode.insertBefore(Ext.getDom(el), isAfter ? me.dom.nextSibling : me.dom); + if (!returnDom) { + rt = Ext.get(rt); + } + } else { + if (isAfter && !me.dom.nextSibling) { + rt = DomHelper.append(me.dom.parentNode, el, !returnDom); + } else { + rt = DomHelper[isAfter ? 'insertAfter' : 'insertBefore'](me.dom, el, !returnDom); + } + } + return rt; + }, + /** + * Returns `true` if this element matches the passed simple selector + * (e.g. 'div.some-class' or 'span:first-child'). + * @param {String/Function} selector The simple selector to test or a function which is passed + * candidate nodes, and should return `true` for nodes which match. + * @return {Boolean} `true` if this element matches the selector, else `false`. + */ + is: function(selector) { + var dom = this.dom, + is; + if (!selector) { + // In Ext 4 is() called through to DomQuery methods, and would always + // return true if the selector was ''. The new query() method in v5 uses + // querySelector/querySelectorAll() which consider '' to be an invalid + // selector and throw an error as a result. To maintain compatibility + // with the various users of is() we have to return true if the selector + // is an empty string. For example: el.up('') should return the element's + // direct parent. + is = true; + } else if (!dom.tagName) { + // document and window objects can never match a selector + is = false; + } else if (Ext.isFunction(selector)) { + is = selector(dom); + } else { + is = dom[Ext.supports.matchesSelector](selector); + } + return is; + }, + /** + * Returns `true` if this element is an ancestor of the passed element + * @param {String/HTMLElement/Ext.dom.Element} el The element or id of the element + * to search for in this elements descendants. + * @return {Boolean} + */ + isAncestor: function(el) { + var ret = false, + dom = this.dom, + child = Ext.getDom(el); + if (dom && child) { + // This handles the window object, which is not a Node and throws an error + if (!child.nodeType) { + return false; + } + if (dom.contains) { + return dom.contains(child); + } else if (dom.compareDocumentPosition) { + return !!(dom.compareDocumentPosition(child) & 16); + } else { + while ((child = child.parentNode)) { + ret = child === dom || ret; + } + } + } + return ret; + }, + isPainted: (function() { + return !Ext.browser.is.IE ? function() { + var dom = this.dom; + return Boolean(dom && dom.offsetParent); + } : function() { + var dom = this.dom; + return Boolean(dom && (dom.offsetHeight !== 0 || dom.offsetWidth !== 0)); + }; + })(), + /** + * Returns true if this element is scrollable. + * @return {Boolean} + */ + isScrollable: function() { + var dom = this.dom; + return dom.scrollHeight > dom.clientHeight || dom.scrollWidth > dom.clientWidth; + }, + /** + * Checks if the current value of a style is equal to a given value. + * @param {String} style property whose value is returned. + * @param {String} val to check against. + * @return {Boolean} `true` for when the current value equals the given value. + */ + isStyle: function(style, val) { + return this.getStyle(style) === val; + }, + /** + * Checks whether the element is currently visible using both visibility and display properties. + * @param {Boolean} [deep=false] True to walk the dom and see if parent elements are hidden. + * If false, the function only checks the visibility of the element itself and it may return + * `true` even though a parent is not visible. + * @param {Number} [mode=3] Bit flag indicating which CSS properties to test: + * + * - `1` - check display only + * - `2` - check visibility only + * - `3` - check both visibility and display + * + * @return {Boolean} `true` if the element is currently visible, else `false` + */ + isVisible: function(deep, mode) { + var dom = this.dom, + visible = true, + end; + if (!dom) { + return false; + } + mode = mode || 3; + if (!visFly) { + visFly = new Ext.dom.Fly(); + } + for (end = dom.ownerDocument.documentElement; dom !== end; dom = dom.parentNode) { + if (!dom || dom.nodeType === 11) { + //parent node does not exist or is a document fragment + visible = false; + } + if (visible) { + visFly.attach(dom); + if (mode & 1) { + visible = !visFly.isStyle(DISPLAY, NONE); + } + if (visible && (mode & 2)) { + visible = !visFly.isStyle(VISIBILITY, HIDDEN); + } + } + if (!visible || !deep) { + break; + } + } + return visible; + }, + /** + * Gets the last child, skipping text nodes + * @param {String} [selector] Find the previous sibling that matches the passed simple selector. + * See {@link Ext.dom.Query} for information about simple selectors. + * @param {Boolean} [returnDom=false] `true` to return a raw DOM node instead of an Ext.dom.Element + * @return {Ext.dom.Element/HTMLElement} The last child Ext.dom.Element (or + * HTMLElement if _returnDom_ is _true_). Or null if no match is found. + */ + last: function(selector, returnDom) { + return this.matchNode('previousSibling', 'lastChild', selector, returnDom); + }, + /** + * @cfg listeners + * @hide + */ + matchNode: function(dir, start, selector, returnDom) { + var dom = this.dom, + n; + if (!dom) { + return null; + } + n = dom[start]; + while (n) { + if (n.nodeType === 1 && (!selector || Ext.fly(n, '_matchNode').is(selector))) { + return !returnDom ? Ext.get(n) : n; + } + n = n[dir]; + } + return null; + }, + /** + * Measures and returns the size of this element. When `dimension` is `null` (or + * not specified), this will be an object with `width` and `height` properties. + * + * If `dimension` is `'w'` the value returned will be this element's width. If + * `dimension` is `'h'` the returned value will be this element's height. + * + * Unlike `getWidth` and `getHeight` this method only returns "precise" (sub-pixel) + * sizes based on the `getBoundingClientRect` API. + * + * @param {'w'/'h'} [dimension] Specifies which dimension is desired. If omitted + * then an object with `width` and `height` properties is returned. + * @return {Number/Object} This element's width, height or both as a readonly + * object. This object may be the direct result of `getBoundingClientRect` and + * hence immutable on some browsers. + * @private + * @since 6.5.0 + */ + measure: function(dimension) { + // This method doesn't use getBoundingClientRect because + // the values it returns are affected by transforms (scale etc). + // For this method we want the real size that's not affected by + // transforms. + var me = this, + dom = me.dom, + includeWidth = dimension !== 'h', + includeHeight = dimension !== 'w', + width = 0, + height = 0, + addPadding = !Ext.supports.ComputedSizeIncludesPadding, + style, rect, offsetParent; + // Use the viewport height if they are asking for body height + if (dom.nodeName === 'BODY') { + height = includeHeight && Element.getViewportHeight(); + width = includeWidth && Element.getViewportWidth(); + } else { + offsetParent = dom.offsetParent; + style = dom.ownerDocument.defaultView.getComputedStyle(dom, null); + // We also have to add the padding if the element uses content-box sizing + addPadding |= style.boxSizing === 'content-box'; + // offsetParent will be null with position fixed + if (offsetParent !== null || style.position === 'fixed') { + if (includeHeight) { + height = toFloat(style.height); + if (addPadding) { + height += toFloat(style.paddingTop) + toFloat(style.paddingBottom) + toFloat(style.borderTopWidth) + toFloat(style.borderBottomWidth); + } + } + if (includeWidth) { + width = toFloat(style.width); + if (addPadding) { + width += toFloat(style.paddingLeft) + toFloat(style.paddingRight) + toFloat(style.borderLeftWidth) + toFloat(style.borderRightWidth); + } + } + } + } + // Don't create a temporary object unless we need to return it... + rect = dimension ? null : { + width: width, + height: height + }; + // NOTE: The modern override ignores all these IE8/9/10 issues + return dimension ? (includeWidth ? width : height) : rect; + }, + /** + * Measures and returns this element's content. When `dimension` is `null` (or + * not specified), this will be an object with `width` and `height` properties. + * + * If `dimension` is `'w'` the value returned will be this element's width. If + * `dimension` is `'h'` the returned value will be this element's height. + * + * Unlike `getWidth` and `getHeight` this method only returns "precise" (sub-pixel) + * sizes based on the `getBoundingClientRect` API. + * + * @param {'w'/'h'} [dimension] Specifies which dimension is desired. If omitted + * then an object with `width` and `height` properties is returned. + * @return {Number/Object} This element's width, height or both as a readonly + * object. This object may be the direct result of `getBoundingClientRect` and + * hence immutable on some browsers. + * @private + * @since 6.5.0 + */ + measureContent: function(dimension) { + var me = this, + includeWidth = dimension !== 'h', + size = me.measure(dimension), + // see modern/classic overrides + h = dimension ? size : size.height, + w = dimension ? size : size.width; + if (dimension !== 'w') { + h -= me.getBorderWidth('tb') + me.getPadding('tb'); + } + if (includeWidth) { + w -= me.getBorderWidth('lr') + me.getPadding('lr'); + } + return dimension ? (includeWidth ? w : h) : { + width: w, + height: h + }; + }, + /** + * Monitors this Element for the mouse leaving. Calls the function after the specified delay only if + * the mouse was not moved back into the Element within the delay. If the mouse *was* moved + * back in, the function is not called. + * @param {Number} delay The delay **in milliseconds** to wait for possible mouse re-entry before calling the handler function. + * @param {Function} handler The function to call if the mouse remains outside of this Element for the specified time. + * @param {Object} [scope] The scope (`this` reference) in which the handler function executes. Defaults to this Element. + * @return {Object} The listeners object which was added to this element so that monitoring can be stopped. Example usage: + * + * // Hide the menu if the mouse moves out for 250ms or more + * this.mouseLeaveMonitor = this.menuEl.monitorMouseLeave(250, this.hideMenu, this); + * + * ... + * // Remove mouseleave monitor on menu destroy + * this.mouseLeaveMonitor.destroy(); + * + */ + monitorMouseLeave: function(delay, handler, scope) { + var me = this, + timer, + listeners = { + mouseleave: function(e) { + if (Ext.isIE9m) { + e.enableIEAsync(); + } + timer = Ext.defer(handler, delay, scope || me, [ + e + ]); + }, + mouseenter: function() { + Ext.undefer(timer); + }, + destroy: function() { + Ext.undefer(timer); + if (!me.destroyed) { + me.un(listeners); + } + } + }; + me.on(listeners); + return listeners; + }, + /** + * Gets the next sibling, skipping text nodes + * @param {String} [selector] Find the next sibling that matches the passed simple selector. + * See {@link Ext.dom.Query} for information about simple selectors. + * @param {Boolean} [returnDom=false] `true` to return a raw dom node instead of an Ext.dom.Element + * @return {Ext.dom.Element/HTMLElement} The next sibling Ext.dom.Element (or + * HTMLElement if _asDom_ is _true_). Or null if no match is found. + */ + next: function(selector, returnDom) { + return this.matchNode('nextSibling', 'nextSibling', selector, returnDom); + }, + /** + * Gets the parent node for this element, optionally chaining up trying to match a selector + * @param {String} [selector] Find a parent node that matches the passed simple selector. + * See {@link Ext.dom.Query} for information about simple selectors. + * @param {Boolean} [returnDom=false] True to return a raw dom node instead of an Ext.dom.Element + * @return {Ext.dom.Element/HTMLElement} The parent node (Ext.dom.Element or + * HTMLElement if _returnDom_ is _true_). Or null if no match is found. + */ + parent: function(selector, returnDom) { + return this.matchNode('parentNode', 'parentNode', selector, returnDom); + }, + peekData: function() { + var dom = this.dom; + return dom && dom._extData || null; + }, + /** + * Initializes positioning on this element. If a desired position is not passed, + * it will make the the element positioned relative IF it is not already positioned. + * @param {String} [pos] Positioning to use "relative", "absolute" or "fixed" + * @param {Number} [zIndex] The zIndex to apply + * @param {Number} [x] Set the page X position + * @param {Number} [y] Set the page Y position + */ + position: function(pos, zIndex, x, y) { + var me = this; + if (me.dom.tagName !== 'BODY') { + if (!pos && me.isStyle(POSITION, STATIC)) { + me.setStyle(POSITION, RELATIVE); + } else if (pos) { + me.setStyle(POSITION, pos); + } + if (zIndex) { + me.setStyle(ZINDEX, zIndex); + } + if (x || y) { + me.setXY([ + x || false, + y || false + ]); + } + } + }, + /** + * Gets the previous sibling, skipping text nodes + * @param {String} [selector] Find the previous sibling that matches the passed simple selector. + * See {@link Ext.dom.Query} for information about simple selectors. + * @param {Boolean} [returnDom=false] `true` to return a raw DOM node instead of an Ext.dom.Element + * @return {Ext.dom.Element/HTMLElement} The previous sibling (Ext.dom.Element or + * HTMLElement if _returnDom_ is _true_). Or null if no match is found. + */ + prev: function(selector, returnDom) { + return this.matchNode('previousSibling', 'previousSibling', selector, returnDom); + }, + /** + * Selects child nodes based on the passed CSS selector. + * Delegates to document.querySelectorAll. More information can be found at + * [http://www.w3.org/TR/css3-selectors/](http://www.w3.org/TR/css3-selectors/) + * + * All selectors, attribute filters and pseudos below can be combined infinitely + * in any order. For example `div.foo:nth-child(odd)[@foo=bar].bar:first` would be + * a perfectly valid selector. + * + * ## Element Selectors: + * + * * \* any element + * * E an element with the tag E + * * E F All descendant elements of E that have the tag F + * * E > F or E/F all direct children elements of E that have the tag F + * * E + F all elements with the tag F that are immediately preceded by an element with the tag E + * * E ~ F all elements with the tag F that are preceded by a sibling element with the tag E + * + * ## Attribute Selectors: + * + * The use of @ and quotes are optional. For example, div[@foo='bar'] is also a valid attribute selector. + * + * * E[foo] has an attribute "foo" + * * E[foo=bar] has an attribute "foo" that equals "bar" + * * E[foo^=bar] has an attribute "foo" that starts with "bar" + * * E[foo$=bar] has an attribute "foo" that ends with "bar" + * * E[foo*=bar] has an attribute "foo" that contains the substring "bar" + * * E[foo%=2] has an attribute "foo" that is evenly divisible by 2 + * * E[foo!=bar] has an attribute "foo" that does not equal "bar" + * + * ## Pseudo Classes: + * + * * E:first-child E is the first child of its parent + * * E:last-child E is the last child of its parent + * * E:nth-child(n) E is the nth child of its parent (1 based as per the spec) + * * E:nth-child(odd) E is an odd child of its parent + * * E:nth-child(even) E is an even child of its parent + * * E:only-child E is the only child of its parent + * * E:checked E is an element that is has a checked attribute that is true (e.g. a radio or checkbox) + * * E:first the first E in the resultset + * * E:last the last E in the resultset + * * E:nth(n) the nth E in the resultset (1 based) + * * E:odd shortcut for :nth-child(odd) + * * E:even shortcut for :nth-child(even) + * * E:not(S) an E element that does not match simple selector S + * * E:has(S) an E element that has a descendant that matches simple selector S + * * E:next(S) an E element whose next sibling matches simple selector S + * * E:prev(S) an E element whose previous sibling matches simple selector S + * * E:any(S1|S2|S2) an E element which matches any of the simple selectors S1, S2 or S3//\\ + * + * ## CSS Value Selectors: + * + * * E{display=none} CSS value "display" that equals "none" + * * E{display^=none} CSS value "display" that starts with "none" + * * E{display$=none} CSS value "display" that ends with "none" + * * E{display*=none} CSS value "display" that contains the substring "none" + * * E{display%=2} CSS value "display" that is evenly divisible by 2 + * * E{display!=none} CSS value "display" that does not equal "none" + * + * @param {String} selector The CSS selector. + * @param {Boolean} [asDom=true] `false` to return an array of Ext.dom.Element + * @param {Boolean} single (private) + * @return {HTMLElement[]/Ext.dom.Element[]} An Array of elements ( + * HTMLElement or Ext.dom.Element if _asDom_ is _false_) that match the selector. + * If there are no matches, an empty Array is returned. + */ + query: function(selector, asDom, single) { + var dom = this.dom, + results, len, nlen, node, nodes, i, j; + if (!dom) { + return null; + } + asDom = (asDom !== false); + selector = selector.split(","); + if (!single) { + // only allocate the results array if the full result set is being + // requested. selectNode() uses the 'single' param. + results = []; + } + for (i = 0 , len = selector.length; i < len; i++) { + if (typeof selector[i] === 'string') { + if (single) { + // take the "fast path" if single was requested (selectNode) + node = dom.querySelector(selector[i]); + return asDom ? node : Ext.get(node); + } + nodes = dom.querySelectorAll(selector[i]); + for (j = 0 , nlen = nodes.length; j < nlen; j++) { + results.push(asDom ? nodes[j] : Ext.get(nodes[j])); + } + } + } + return results; + }, + /** + * Adds one or more CSS classes to this element and removes the same class(es) from all siblings. + * @param {String/String[]} className The CSS class to add, or an array of classes. + * @return {Ext.dom.Element} this + */ + radioCls: function(className) { + var cn = this.dom.parentNode.childNodes, + v; + className = Ext.isArray(className) ? className : [ + className + ]; + for (var i = 0, + len = cn.length; i < len; i++) { + v = cn[i]; + if (v && v.nodeType === 1) { + Ext.fly(v).removeCls(className); + } + } + return this.addCls(className); + }, + redraw: function() { + var dom = this.dom, + domStyle = dom.style; + domStyle.display = 'none'; + dom.offsetHeight; + domStyle.display = ''; + }, + /** + * @method remove + * @inheritdoc Ext.dom.Element#method-destroy + * @deprecated 5.0.0 Please use {@link #destroy} instead. + */ + remove: function() { + this.destroy(); + }, + removeChild: function(element) { + this.dom.removeChild(Ext.getDom(element)); + return this; + }, + /** + * Removes the given CSS class(es) from this Element. + * @param {String/String[]} names The CSS classes to remove separated by space, + * or an array of classes + * @param {String} [prefix] Prefix to prepend to each class. The separator `-` will be + * appended to the prefix. + * @param {String} [suffix] Suffix to append to each class. The separator `-` will be + * prepended to the suffix. + * return {Ext.dom.Element} this + */ + removeCls: function(names, prefix, suffix) { + return this.replaceCls(names, null, prefix, suffix); + }, + /** + * Forces the browser to repaint this element. + * @return {Ext.dom.Element} this + */ + repaint: function() { + var me = this; + me.addCls(Ext.baseCSSPrefix + 'repaint'); + if (!me.repaintTimer) { + me.repaintTimer = Ext.defer(function() { + me.repaintTimer = null; + if (me.dom) { + // may have been removed already on slower UAs + me.removeCls(Ext.baseCSSPrefix + 'repaint'); + } + }, 1); + } + return me; + }, + /** + * Replaces the passed element with this element + * @param {String/HTMLElement/Ext.dom.Element} el The element to replace. + * The id of the node, a DOM Node or an existing Element. + * @param {Boolean} [destroy=true] `false` to prevent destruction of the replaced + * element + * @return {Ext.dom.Element} This element + */ + replace: function(el, destroy) { + el = Ext.getDom(el); + var parentNode = el.parentNode, + id = el.id, + dom = this.dom; + if (!parentNode) { + Ext.raise('Cannot replace element "' + id + '". It is not attached to a parent node.'); + } + if (destroy !== false && id && Ext.cache[id]) { + parentNode.insertBefore(dom, el); + Ext.get(el).destroy(); + } else { + parentNode.replaceChild(dom, el); + } + return this; + }, + /** + * Replaces one or more CSS classes on this element with other classes. If the old + * name does not exist, the new name will simply be added. + * + * @param {String/String[]} [remove] The CSS class(es) to be removed. + * @param {String/String[]} [add] The CSS class(es) to be added. + * @param {String} [prefix] The string to prepend to each class name. + * @param {String} [suffix] The string to append to each class name. + * @return {Ext.dom.Element} this + */ + replaceCls: function(remove, add, prefix, suffix) { + var me = this, + added = 0, + removed = 0, + rem = remove, + data = (add || remove) && me.getData(), + list, map, i, n, name; + if (data) { + list = data.classList; + map = data.classMap; + add = add ? ((typeof add === 'string') ? add.split(spacesRe) : add) : EMPTY; + rem = rem ? ((typeof rem === 'string') ? rem.split(spacesRe) : rem) : EMPTY; + // Include the '-' but only if the caller hasn't already... + prefix = prefix || ''; + if (prefix && prefix[prefix.length - 1] !== '-') { + prefix += '-'; + } + suffix = suffix || ''; + if (suffix && suffix[0] !== '-') { + suffix = '-' + suffix; + } + for (i = 0 , n = rem.length; i < n; i++) { + if (!(name = rem[i])) { + // Sadly ... 'foo '.split(spacesRe) == ['foo', ''] + + continue; + } + name = prefix + name + suffix; + if (spacesRe.test(name)) { + Ext.raise('Class names in arrays must not contain spaces'); + } + if (map[name]) { + delete map[name]; + ++removed; + } + } + for (i = 0 , n = add.length; i < n; i++) { + if (!(name = add[i])) { + + continue; + } + name = prefix + name + suffix; + if (spacesRe.test(name)) { + Ext.raise('Class names in arrays must not contain spaces'); + } + if (!map[name]) { + map[name] = true; + // If we are only adding, we can be more efficient... + if (!removed) { + list.push(name); + ++added; + } + } + } + if (removed) { + me.setClassMap(map, /*keep=*/ + true); + } else if (added) { + me.dom.className = list.join(' '); + } + } + return me; + }, + /** + * Replaces this element with the passed element + * @param {String/HTMLElement/Ext.dom.Element/Object} el The new element (id of the + * node, a DOM Node or an existing Element) or a DomHelper config of an element to create + * @return {Ext.dom.Element} This element + */ + replaceWith: function(el) { + var me = this, + dom = me.dom, + parent = dom.parentNode, + cache = Ext.cache, + newDom; + me.clearListeners(); + if (el.nodeType || el.dom || typeof el === 'string') { + el = Ext.get(el); + newDom = parent.insertBefore(el.dom, dom); + } else { + // domhelper config + newDom = Ext.DomHelper.insertBefore(dom, el); + } + parent.removeChild(dom); + me.dom = newDom; + if (!me.isFly) { + delete cache[me.id]; + cache[me.id = Ext.id(newDom)] = me; + } + return me; + }, + resolveListenerScope: function(defaultScope) { + // Override this to pass along to our owning component (if we have one). + var component = this.component; + return component ? component.resolveListenerScope(defaultScope) : this; + }, + /** + * Scrolls this element the specified direction. Does bounds checking to make sure the scroll is + * within this element's scrollable range. + * @param {String} direction Possible values are: + * + * - `"l"` (or `"left"`) + * - `"r"` (or `"right"`) + * - `"t"` (or `"top"`, or `"up"`) + * - `"b"` (or `"bottom"`, or `"down"`) + * + * @param {Number} distance How far to scroll the element in pixels + * @param {Boolean/Object} [animate] true for the default animation or a standard Element + * animation config object + * @return {Boolean} Returns true if a scroll was triggered or false if the element + * was scrolled as far as it could go. + */ + scroll: function(direction, distance, animate) { + if (!this.isScrollable()) { + return false; + } + // Allow full word, or initial to be sent. + // (Ext.dd package uses full word) + direction = direction.charAt(0); + var me = this, + dom = me.dom, + side = direction === 'r' || direction === 'l' ? 'left' : 'top', + scrolled = false, + currentScroll, constrainedScroll; + if (direction === 'l' || direction === 't' || direction === 'u') { + distance = -distance; + } + if (side === 'left') { + currentScroll = dom.scrollLeft; + constrainedScroll = me.constrainScrollLeft(currentScroll + distance); + } else { + currentScroll = dom.scrollTop; + constrainedScroll = me.constrainScrollTop(currentScroll + distance); + } + if (constrainedScroll !== currentScroll) { + this.scrollTo(side, constrainedScroll, animate); + scrolled = true; + } + return scrolled; + }, + /** + * Scrolls this element by the passed delta values, optionally animating. + * + * All of the following are equivalent: + * + * el.scrollBy(10, 10, true); + * el.scrollBy([10, 10], true); + * el.scrollBy({ x: 10, y: 10 }, true); + * + * @param {Number/Number[]/Object} deltaX Either the x delta, an Array specifying x and y deltas or + * an object with "x" and "y" properties. + * @param {Number/Boolean/Object} deltaY Either the y delta, or an animate flag or config object. + * @param {Boolean/Object} animate Animate flag/config object if the delta values were passed separately. + * @return {Ext.dom.Element} this + */ + scrollBy: function(deltaX, deltaY, animate) { + var me = this, + dom = me.dom; + // Extract args if deltas were passed as an Array. + if (deltaX.length) { + animate = deltaY; + deltaY = deltaX[1]; + deltaX = deltaX[0]; + } else if (typeof deltaX != 'number') { + // or an object + animate = deltaY; + deltaY = deltaX.y; + deltaX = deltaX.x; + } + if (deltaX) { + me.scrollTo('left', me.constrainScrollLeft(dom.scrollLeft + deltaX), animate); + } + if (deltaY) { + me.scrollTo('top', me.constrainScrollTop(dom.scrollTop + deltaY), animate); + } + return me; + }, + /** + * @private + */ + scrollChildIntoView: function(child, hscroll) { + // scrollFly is used inside scrollInfoView, must use a method-unique fly here + Ext.fly(child).scrollIntoView(this, hscroll); + }, + /** + * Scrolls this element into view within the passed container. + * + * Ext.create('Ext.data.Store', { + * storeId:'simpsonsStore', + * fields:['name', 'email', 'phone'], + * data:{'items':[ + * { 'name': 'Lisa', "email":"lisa@simpsons.com", "phone":"555-111-1224" }, + * { 'name': 'Bart', "email":"bart@simpsons.com", "phone":"555-222-1234" }, + * { 'name': 'Homer', "email":"homer@simpsons.com", "phone":"555-222-1244" }, + * { 'name': 'Marge', "email":"marge@simpsons.com", "phone":"555-222-1254" }, + * { 'name': 'Milhouse', "email":"milhouse@simpsons.com", "phone":"555-222-1244" }, + * { 'name': 'Willy', "email":"willy@simpsons.com", "phone":"555-222-1254" }, + * { 'name': 'Skinner', "email":"skinner@simpsons.com", "phone":"555-222-1244" }, + * { 'name': 'Hank (last row)', "email":"hank@simpsons.com", "phone":"555-222-1254" } + * ]}, + * proxy: { + * type: 'memory', + * reader: { + * type: 'json', + * rootProperty: 'items' + * } + * } + * }); + * + * var grid = Ext.create('Ext.grid.Panel', { + * title: 'Simpsons', + * store: Ext.data.StoreManager.lookup('simpsonsStore'), + * columns: [ + * { text: 'Name', dataIndex: 'name', width: 125 }, + * { text: 'Email', dataIndex: 'email', flex: 1 }, + * { text: 'Phone', dataIndex: 'phone' } + * ], + * height: 190, + * width: 400, + * renderTo: Ext.getBody(), + * tbar: [{ + * text: 'Scroll row 7 into view', + * handler: function () { + * var view = grid.getView(); + * + * Ext.get(view.getRow(7)).scrollIntoView(view.getEl(), null, true); + * } + * }] + * }); + * + * @param {String/HTMLElement/Ext.Element} [container=document.body] The container element + * to scroll. Should be a string (id), dom node, or Ext.Element. + * @param {Boolean} [hscroll=true] False to disable horizontal scroll. + * @param {Boolean/Object} [animate] true for the default animation or a standard Element + * animation config object + * @param {Boolean} [highlight=false] true to {@link #highlight} the element when it is in view. + * @return {Ext.dom.Element} this + */ + scrollIntoView: function(container, hscroll, animate, highlight) { + container = Ext.getDom(container) || Ext.getBody().dom; + return this.doScrollIntoView(container, hscroll, animate, highlight, 'getScrollLeft', 'scrollTo'); + }, + /** + * Scrolls this element the specified scroll point. It does NOT do bounds checking so + * if you scroll to a weird value it will try to do it. For auto bounds checking, use #scroll. + * @param {String} side Either "left" for scrollLeft values or "top" for scrollTop values. + * @param {Number} value The new scroll value + * @param {Boolean/Object} [animate] true for the default animation or a standard Element + * animation config object + * @return {Ext.dom.Element} this + */ + scrollTo: function(side, value, animate) { + //check if we're scrolling top or left + var top = topRe.test(side), + me = this, + prop = top ? 'scrollTop' : 'scrollLeft', + dom = me.dom, + animCfg; + if (!animate || !me.anim) { + // just setting the value, so grab the direction + dom[prop] = value; + // corrects IE, other browsers will ignore + dom[prop] = value; + } else { + animCfg = { + to: {} + }; + animCfg.to[prop] = value; + if (Ext.isObject(animate)) { + Ext.applyIf(animCfg, animate); + } + me.animate(animCfg); + } + return me; + }, + /** + * Selects descendant elements of this element based on the passed CSS selector to + * enable {@link Ext.dom.Element Element} methods to be applied to many related + * elements in one statement through the returned + * {@link Ext.dom.CompositeElementLite CompositeElementLite} object. + * + * @param {String/HTMLElement[]} selector The CSS selector or an array of elements + * @param {Boolean} composite Return a CompositeElement as opposed to a + * CompositeElementLite. Defaults to false. + * @return {Ext.dom.CompositeElementLite/Ext.dom.CompositeElement} + */ + select: function(selector, composite) { + var isElementArray, elements; + if (typeof selector === "string") { + elements = this.query(selector, !composite); + } else if (selector.length === undefined) { + Ext.raise("Invalid selector specified: " + selector); + } else { + // if selector is not a string, assume it is already an array of + // HTMLElement + elements = selector; + isElementArray = true; + } + // if the selector parameter was a string we will have called through + // to query, and it will have constructed either an array of + // HTMLElement or Ext.Element, depending on the composite param we gave + // it. If this is the case we can take the fast path through the + // CompositeElementLite constructor to avoid calling getDom() or get() + // on every element in the array. + return composite ? new Ext.CompositeElement(elements, !isElementArray) : new Ext.CompositeElementLite(elements, true); + }, + /** + * Selects a single descendant element of this element using a CSS selector + * (see {@link #method-query}). + * @param {String} selector The selector query + * @param {Boolean} [asDom=true] `false` to return an Ext.dom.Element + * @return {HTMLElement/Ext.dom.Element} The DOM element (or Ext.dom.Element if + * _asDom_ is _false_) which matched the selector. + */ + selectNode: function(selector, asDom) { + return this.query(selector, asDom, true); + }, + /** + * Sets the passed attributes as attributes of this element (a `style` attribute + * can be a string, object or function). + * + * Example component (though any Ext.dom.Element would suffice): + * + * var cmp = Ext.create({ + * xtype: 'component', + * html: 'test', + * renderTo: Ext.getBody() + * }); + * + * Once the component is rendered, you can fetch a reference to its outer + * element to use `set`: + * + * cmp.el.set({ + * foo: 'bar' + * }); + * + * This sets an attribute on the element of **foo="bar"**: + * + *
test
+ * + * To remove the attribute pass a value of **undefined**: + * + * cmp.el.set({ + * foo: undefined + * }); + * + * **Note:** + * + * - You cannot remove an attribute by passing `undefined` when the + * `expandos` param is set to **false**. + * - Passing an attribute of `style` results in the request being handed off to + * {@link #method-applyStyles}. + * - Passing an attribute of `cls` results in the element's dom's + * [className](http://www.w3schools.com/jsref/prop_html_classname.asp) property + * being set directly. For additional flexibility when setting / removing + * classes see: + * - {@link #method-addCls} + * - {@link #method-removeCls} + * - {@link #method-replaceCls} + * - {@link #method-setCls} + * - {@link #method-toggleCls} + * + * @param {Object} attributes The object with the attributes. + * @param {Boolean} [useSet=true] `false` to override the default `setAttribute` + * to use [expandos](http://help.dottoro.com/ljvovanq.php). + * @return {Ext.dom.Element} this + */ + set: function(attributes, useSet) { + var me = this, + dom = me.dom, + attribute, value; + for (attribute in attributes) { + if (attributes.hasOwnProperty(attribute)) { + value = attributes[attribute]; + if (attribute === 'style') { + me.applyStyles(value); + } else if (attribute === 'cls') { + dom.className = value; + } else if (useSet !== false) { + if (value === undefined) { + dom.removeAttribute(attribute); + } else { + dom.setAttribute(attribute, value); + } + } else { + dom[attribute] = value; + } + } + } + return me; + }, + /** + * Sets the element's CSS bottom style. + * @param {Number/String} bottom Number of pixels or CSS string value to set as + * the bottom CSS property value + * @return {Ext.dom.Element} this + */ + setBottom: function(bottom) { + this.dom.style[BOTTOM] = Element.addUnits(bottom); + return this; + }, + /** + * Sets the CSS classes of this element to the keys of the given object. The + * `classMap` object is typically returned by {@link #getClassMap}. The values of + * the properties in the `classMap` should be truthy (such as `1` or `true`). + * + * @param {Object} classMap The object whose keys will be the CSS classes. + * @param {Boolean} [keep=false] Pass `true` to indicate the the `classMap` + * object can be kept (instead of copied). + */ + setClassMap: function(classMap, keep) { + var data = this.getData(/*sync=*/ + false), + classList; + if (data) { + classMap = (keep && classMap) || Ext.apply({}, classMap); + data.classMap = classMap; + data.classList = classList = Ext.Object.getKeys(classMap); + data.isSynchronized = true; + // We won't get a data object if !this.dom: + this.dom.className = classList.join(' '); + } + }, + /** + * Sets the specified CSS class on this element's DOM node. + * @param {String/String[]} className The CSS class to set on this element. + */ + setCls: function(className) { + var me = this, + elementData = me.getData(/*sync=*/ + false), + i, ln, map, classList; + if (typeof className === 'string') { + className = className.split(spacesRe); + } + elementData.classList = classList = className.slice(); + elementData.classMap = map = {}; + for (i = 0 , ln = classList.length; i < ln; i++) { + map[classList[i]] = true; + } + me.dom.className = classList.join(' '); + }, + /** + * Sets the CSS display property. Uses originalDisplay if the specified value is a + * boolean true. + * @param {Boolean/String} value Boolean value to display the element using its + * default display, or a string to set the display directly. + * @return {Ext.dom.Element} this + */ + setDisplayed: function(value) { + var me = this; + if (typeof value === "boolean") { + value = value ? me._getDisplay() : NONE; + } + me.setStyle(DISPLAY, value); + if (me.shadow || me.shim) { + me.setUnderlaysVisible(value !== NONE); + } + return me; + }, + /** + * Set the height of this Element. + * @param {Number/String} height The new height. + * @return {Ext.dom.Element} this + */ + setHeight: function(height) { + var me = this; + me.dom.style[HEIGHT] = Element.addUnits(height); + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + /** + * Sets the `innerHTML` of this element. + * @param {String} html The new HTML. + * @return {Ext.dom.Element} this + */ + setHtml: function(html) { + if (this.dom) { + this.dom.innerHTML = html; + } + return this; + }, + setId: function(id) { + var me = this, + currentId = me.id, + cache = Ext.cache; + if (currentId) { + delete cache[currentId]; + } + me.dom.id = id; + /** + * The DOM element ID + * @property id + * @type String + */ + me.id = id; + cache[id] = me; + return me; + }, + /** + * Sets the element's left position directly using CSS style + * (instead of {@link #setX}). + * @param {Number/String} left Number of pixels or CSS string value to + * set as the left CSS property value + * @return {Ext.dom.Element} this + */ + setLeft: function(left) { + var me = this; + me.dom.style[LEFT] = Element.addUnits(left); + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + setLocalX: function(x) { + var me = this, + style = me.dom.style; + // clear right style just in case it was previously set by rtlSetLocalXY + style.right = ''; + style.left = (x === null) ? 'auto' : x + 'px'; + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + setLocalXY: function(x, y) { + var me = this, + style = me.dom.style; + // clear right style just in case it was previously set by rtlSetLocalXY + style.right = ''; + if (x && x.length) { + y = x[1]; + x = x[0]; + } + if (x === null) { + style.left = 'auto'; + } else if (x !== undefined) { + style.left = x + 'px'; + } + if (y === null) { + style.top = 'auto'; + } else if (y !== undefined) { + style.top = y + 'px'; + } + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + setLocalY: function(y) { + var me = this; + me.dom.style.top = (y === null) ? 'auto' : y + 'px'; + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + setMargin: function(margin) { + var me = this, + domStyle = me.dom.style; + if (margin || margin === 0) { + margin = me.self.unitizeBox((margin === true) ? 5 : margin); + domStyle.setProperty('margin', margin, 'important'); + } else { + domStyle.removeProperty('margin-top'); + domStyle.removeProperty('margin-right'); + domStyle.removeProperty('margin-bottom'); + domStyle.removeProperty('margin-left'); + } + }, + /** + * Set the maximum height of this Element. + * @param {Number/String} height The new maximum height. + * @return {Ext.dom.Element} this + */ + setMaxHeight: function(height) { + this.dom.style[MAX_HEIGHT] = Element.addUnits(height); + return this; + }, + /** + * Set the maximum width of this Element. + * @param {Number/String} width The new maximum width. + * @return {Ext.dom.Element} this + */ + setMaxWidth: function(width) { + this.dom.style[MAX_WIDTH] = Element.addUnits(width); + return this; + }, + /** + * Set the minimum height of this Element. + * @param {Number/String} height The new minimum height. + * @return {Ext.dom.Element} this + */ + setMinHeight: function(height) { + this.dom.style[MIN_HEIGHT] = Element.addUnits(height); + return this; + }, + /** + * Set the minimum width of this Element. + * @param {Number/String} width The new minimum width. + * @return {Ext.dom.Element} this + */ + setMinWidth: function(width) { + this.dom.style[MIN_WIDTH] = Element.addUnits(width); + return this; + }, + /** + * Set the opacity of the element + * @param {Number} opacity The new opacity. 0 = transparent, .5 = 50% visibile, 1 = fully visible, etc + * @return {Ext.dom.Element} this + */ + setOpacity: function(opacity) { + var me = this; + if (me.dom) { + me.setStyle('opacity', opacity); + } + return me; + }, + setPadding: function(padding) { + var me = this, + domStyle = me.dom.style; + if (padding || padding === 0) { + padding = me.self.unitizeBox((padding === true) ? 5 : padding); + domStyle.setProperty('padding', padding, 'important'); + } else { + domStyle.removeProperty('padding-top'); + domStyle.removeProperty('padding-right'); + domStyle.removeProperty('padding-bottom'); + domStyle.removeProperty('padding-left'); + } + }, + /** + * Sets the element's CSS right style. + * @param {Number/String} right Number of pixels or CSS string value to + * set as the right CSS property value + * @return {Ext.dom.Element} this + */ + setRight: function(right) { + this.dom.style[RIGHT] = Element.addUnits(right); + return this; + }, + /** + * Sets the left scroll position + * @param {Number} left The left scroll position + * @return {Ext.dom.Element} this + */ + setScrollLeft: function(left) { + this.dom.scrollLeft = left; + return this; + }, + /** + * Sets the top scroll position + * @param {Number} top The top scroll position + * @return {Ext.dom.Element} this + */ + setScrollTop: function(top) { + this.dom.scrollTop = top; + return this; + }, + /** + * Set the size of this Element. + * + * @param {Number/String} width The new width. This may be one of: + * + * - A Number specifying the new width in pixels. + * - A String used to set the CSS width style. Animation may **not** be used. + * - A size object in the format `{width: widthValue, height: heightValue}`. + * + * @param {Number/String} height The new height. This may be one of: + * + * - A Number specifying the new height in pixels. + * - A String used to set the CSS height style. Animation may **not** be used. + * @return {Ext.dom.Element} this + */ + setSize: function(width, height) { + var me = this, + style = me.dom.style; + if (Ext.isObject(width)) { + // in case of object from getSize() + height = width.height; + width = width.width; + } + if (width !== undefined) { + style.width = Element.addUnits(width); + } + if (height !== undefined) { + style.height = Element.addUnits(height); + } + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + /** + * Wrapper for setting style properties, also takes single object parameter of + * multiple styles. + * + * Styles should be a valid DOM element style property. + * [Valid style property names](http://www.w3schools.com/jsref/dom_obj_style.asp) + * (_along with the supported CSS version for each_) + * + * //
Phineas Flynn
+ * + * var el = Ext.get('my-el'); + * + * // two-param syntax + * el.setStyle('color', 'white'); + * + * // single-param syntax + * el.setStyle({ + * fontWeight: 'bold', + * backgroundColor: 'gray', + * padding: '10px' + * }); + * + * @param {String/Object} prop The style property to be set, or an object of + * multiple styles. + * @param {String} [value] The value to apply to the given property, or null if + * an object was passed. + * @return {Ext.dom.Element} this + */ + setStyle: function(prop, value) { + var me = this, + dom = me.dom, + hooks = me.styleHooks, + style = dom.style, + name = prop, + hook; + // we don't promote the 2-arg form to object-form to avoid the overhead... + if (typeof name === 'string') { + hook = hooks[name]; + if (!hook) { + hooks[name] = hook = { + name: Element.normalize(name) + }; + } + value = (value == null) ? '' : value; + // map null && undefined to '' + if (hook.set) { + hook.set(dom, value, me); + } else { + style[hook.name] = value; + } + if (hook.afterSet) { + hook.afterSet(dom, value, me); + } + } else { + for (name in prop) { + if (prop.hasOwnProperty(name)) { + hook = hooks[name]; + if (!hook) { + hooks[name] = hook = { + name: Element.normalize(name) + }; + } + value = prop[name]; + value = (value == null) ? '' : value; + // map null && undefined to '' + if (hook.set) { + hook.set(dom, value, me); + } else { + style[hook.name] = value; + } + if (hook.afterSet) { + hook.afterSet(dom, value, me); + } + } + } + } + return me; + }, + setText: function(text) { + this.dom.textContent = text; + }, + /** + * Sets the element's top position directly using CSS style + * (instead of {@link #setY}). + * @param {Number/String} top Number of pixels or CSS string value to + * set as the top CSS property value + * @return {Ext.dom.Element} this + */ + setTop: function(top) { + var me = this; + me.dom.style[TOP] = Element.addUnits(top); + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + /** + * Sets the CSS [touch-action](https://www.w3.org/TR/pointerevents/#the-touch-action-css-property) + * property on this element and emulates its behavior on browsers where touch-action + * is not supported. + * + * @param {Object} touchAction An object with touch-action names as the keys, and + * boolean values to enable or disable specific touch actions. Accepted keys are: + * + * - `panX` + * - `panY` + * - `pinchZoom` + * - `doubleTapZoom` + * + * All touch actions are enabled (`true`) by default, so it is usually only necessary + * to specify which touch actions to disable. For example, the following disables + * only vertical scrolling and double-tap-zoom on an element + * + * element.setTouchAction({ + * panY: false, + * doubleTapZoom: false + * }); + * + * @return {Ext.dom.Element} this + */ + setTouchAction: function(touchAction) { + Ext.dom.TouchAction.set(this.dom, touchAction); + }, + setUnderlaysVisible: function(visible) { + var shadow = this.shadow, + shim = this.shim; + if (shadow && !shadow.disabled) { + if (visible) { + shadow.show(); + } else { + shadow.hide(); + } + } + if (shim && !shim.disabled) { + if (visible) { + shim.show(); + } else { + shim.hide(); + } + } + }, + /** + * @private + */ + setVisibility: function(isVisible) { + var domStyle = this.dom.style; + if (isVisible) { + domStyle.removeProperty('visibility'); + } else { + domStyle.setProperty('visibility', 'hidden', 'important'); + } + }, + /** + * Use this to change the visibility mode between {@link #VISIBILITY}, + * {@link #DISPLAY}, {@link #OFFSETS}, {@link #CLIP}, or {@link #OPACITY}. + * + * @param {Ext.dom.Element.VISIBILITY/Ext.dom.Element.DISPLAY/Ext.dom.Element.OFFSETS/Ext.dom.Element.CLIP/Ext.dom.Element.OPACITY} mode + * The method by which the element will be {@link #hide hidden} (you can + * also use the {@link #setVisible} or {@link #toggle} method to toggle element + * visibility). + * + * @return {Ext.dom.Element} this + */ + setVisibilityMode: function(mode) { + if (mode !== 1 && mode !== 2 && mode !== 3 && mode !== 4 && mode !== 5) { + Ext.raise("visibilityMode must be one of the following: " + "Ext.Element.DISPLAY, Ext.Element.VISIBILITY, Ext.Element.OFFSETS, " + "Ext.Element.CLIP, or Element.OPACITY"); + } + this.getData().visibilityMode = mode; + return this; + }, + /** + * Sets the visibility of the element based on the current visibility mode. Use + * {@link #setVisibilityMode} to switch between the following visibility modes: + * + * - {@link #DISPLAY} (the default) + * - {@link #VISIBILITY} + * - {@link #OFFSETS} + * - {@link #CLIP} + * - {@link #OPACITY} + * + * @param {Boolean} visible Whether the element is visible. + * @return {Ext.dom.Element} this + */ + setVisible: function(visible) { + var me = this, + mode = me.getVisibilityMode(), + addOrRemove = visible ? 'removeCls' : 'addCls'; + switch (mode) { + case Element.DISPLAY: + me.removeCls([ + visibilityCls, + offsetsCls, + clipCls, + opacityCls + ]); + me[addOrRemove](displayCls); + break; + case Element.VISIBILITY: + me.removeCls([ + displayCls, + offsetsCls, + clipCls, + opacityCls + ]); + me[addOrRemove](visibilityCls); + break; + case Element.OFFSETS: + me.removeCls([ + visibilityCls, + displayCls, + clipCls, + opacityCls + ]); + me[addOrRemove](offsetsCls); + break; + case Element.CLIP: + me.removeCls([ + visibilityCls, + displayCls, + offsetsCls, + opacityCls + ]); + me[addOrRemove](clipCls); + break; + case Element.OPACITY: + me.removeCls([ + visibilityCls, + displayCls, + offsetsCls, + clipCls + ]); + me[addOrRemove](opacityCls); + break; + } + if (me.shadow || me.shim) { + me.setUnderlaysVisible(visible); + } + if (!visible && me.$ripples) { + me.destroyAllRipples(); + } + return me; + }, + /** + * Set the width of this Element. + * @param {Number/String} width The new width. + * @return {Ext.dom.Element} this + */ + setWidth: function(width) { + var me = this; + me.dom.style[WIDTH] = Element.addUnits(width); + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + /** + * Sets this Element's page-level x coordinate + * @param {Number} x + * @return {Ext.dom.Element} this + */ + setX: function(x) { + return this.setXY([ + x, + false + ]); + }, + /** + * Sets this Element's page-level x and y coordinates + * @param {Number[]} xy + * @return {Ext.dom.Element} this + */ + setXY: function(xy) { + var me = this, + pts = me.translatePoints(xy), + style = me.dom.style, + pos; + me.position(); + // right position may have been previously set by rtlSetLocalXY + // so clear it here just in case. + style.right = ''; + for (pos in pts) { + if (!isNaN(pts[pos])) { + style[pos] = pts[pos] + 'px'; + } + } + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + /** + * Sets this Element's page-level y coordinate + * @param {Number} y + * @return {Ext.dom.Element} this + */ + setY: function(y) { + return this.setXY([ + false, + y + ]); + }, + /** + * Sets the z-index of this Element and synchronizes the z-index of shadow and/or + * shim if present. + * + * @param {Number} zindex The new z-index to set + * @return {Ext.dom.Element} this + */ + setZIndex: function(zindex) { + var me = this; + if (me.shadow) { + me.shadow.setZIndex(zindex); + } + if (me.shim) { + me.shim.setZIndex(zindex); + } + return me.setStyle('z-index', zindex); + }, + /** + * Show this element - Uses display mode to determine whether to use "display", + * "visibility", "offsets", or "clip". See {@link #setVisible}. + * + * @return {Ext.dom.Element} this + */ + show: function() { + return this.setVisible(true); + }, + /** + * Stops the specified event(s) from bubbling and optionally prevents the default action + * + * var store = Ext.create('Ext.data.Store', { + * fields: ['name', 'email'], + * data: [{ + * 'name': 'Finn', + * "email": "finn@adventuretime.com" + * }] + * }); + * + * Ext.create('Ext.grid.Panel', { + * title: 'Land of Ooo', + * store: store, + * columns: [{ + * text: 'Name', + * dataIndex: 'name' + * }, { + * text: 'Email ', + * dataIndex: 'email', + * flex: 1, + * listeners: { + * render: function(col) { + * // Swallow the click event when the click occurs on the + * // help icon - preventing the sorting of data by that + * // column and instead performing an action specific to + * // the help icon + * var img = col.getEl().down('img'); + * img.swallowEvent(['click', 'mousedown'], true); + * col.on('click', function() { + * // logic to show a help dialog + * console.log('image click handler'); + * }, col); + * } + * } + * }], + * height: 200, + * width: 400, + * renderTo: document.body + * }); + * + * @param {String/String[]} eventName an event / array of events to stop from bubbling + * @param {Boolean} [preventDefault] true to prevent the default action too + * @return {Object} Object with a destroy method to unswallow events + * @return {Function} return.destroy method to clean up any listeners that are swallowing events + */ + swallowEvent: function(eventName, preventDefault) { + var me = this, + e, eLen, + listeners = { + destroyable: true + }, + fn = function(e) { + e.stopPropagation(); + if (preventDefault) { + e.preventDefault(); + } + }; + if (Ext.isArray(eventName)) { + eLen = eventName.length; + for (e = 0; e < eLen; e++) { + listeners[eventName[e]] = fn; + } + } else { + listeners[eventName] = fn; + } + return me.on(listeners); + }, + /** + * @private + * @param {String} firstClass + * @param {String} secondClass + * @param {Boolean} flag + * @param {String} prefix + * @return {Mixed} + */ + swapCls: function(firstClass, secondClass, flag, prefix) { + if (flag === undefined) { + flag = true; + } + var me = this, + addedClass = flag ? firstClass : secondClass, + removedClass = flag ? secondClass : firstClass; + if (removedClass) { + me.removeCls(prefix ? prefix + '-' + removedClass : removedClass); + } + if (addedClass) { + me.addCls(prefix ? prefix + '-' + addedClass : addedClass); + } + return me; + }, + /** + * @private + */ + synchronize: function() { + var me = this, + dom = me.dom, + hasClassMap = {}, + className = dom.className, + classList, i, ln, name, + elementData = me.getData(/*sync=*/ + false); + if (className && className.length > 0) { + classList = dom.className.split(classNameSplitRegex); + for (i = 0 , ln = classList.length; i < ln; i++) { + name = classList[i]; + hasClassMap[name] = true; + } + } else { + classList = []; + } + elementData.classList = classList; + elementData.classMap = hasClassMap; + elementData.isSynchronized = true; + return me; + }, + /** + * @private + */ + syncUnderlays: function() { + var me = this, + shadow = me.shadow, + shim = me.shim, + dom = me.dom, + xy, x, y, w, h; + if (me.isVisible()) { + xy = me.getXY(); + x = xy[0]; + y = xy[1]; + w = dom.offsetWidth; + h = dom.offsetHeight; + if (shadow && !shadow.hidden) { + shadow.realign(x, y, w, h); + } + if (shim && !shim.hidden) { + shim.realign(x, y, w, h); + } + } + }, + /** + * Toggles the specified CSS class on this element (removes it if it already exists, otherwise adds it). + * @param {String} className The CSS class to toggle. + * @param {Boolean} [state] If specified as `true`, causes the class to be added. If specified as `false`, causes + * the class to be removed. + * @return {Ext.dom.Element} this + */ + toggleCls: function(className, state) { + if (state == null) { + state = !this.hasCls(className); + } + return state ? this.addCls(className) : this.removeCls(className); + }, + /** + * Toggles the element's visibility, depending on visibility mode. + * @return {Ext.dom.Element} this + */ + toggle: function() { + this.setVisible(!this.isVisible()); + return this; + }, + translate: function() { + var transformStyleName = 'webkitTransform' in DOC.createElement('div').style ? 'webkitTransform' : 'transform'; + return function(x, y, z) { + x = Math.round(x); + y = Math.round(y); + z = Math.round(z); + this.dom.style[transformStyleName] = 'translate3d(' + (x || 0) + 'px, ' + (y || 0) + 'px, ' + (z || 0) + 'px)'; + }; + }(), + /** + * @private + */ + unwrap: function() { + var dom = this.dom, + parentNode = dom.parentNode, + activeElement = (activeElFly || (activeElFly = new Ext.dom.Fly())).attach(Ext.Element.getActiveElement()), + grandparentNode, cached, resumeFocus, tabIndex; + grannyFly = grannyFly || new Ext.dom.Fly(); + cached = Ext.cache[activeElement.dom.id]; + // If the element is in the cache, we need to get the instance so + // we can suspend events on it. If it's not in the cache, it can't + // have any events so we don't need to suspend on it. + if (cached) { + activeElement = cached; + } + if (this.contains(activeElement)) { + if (cached) { + cached.suspendFocusEvents(); + } + resumeFocus = true; + } + if (parentNode) { + grandparentNode = parentNode.parentNode; + // See wrap() for the explanation of this jiggery-trickery + if (resumeFocus) { + tabIndex = grandparentNode.getAttribute('tabIndex'); + grannyFly.attach(grandparentNode); + grannyFly.set({ + tabIndex: -1 + }); + grannyFly.suspendFocusEvents(); + grannyFly.focus(); + } + grandparentNode.insertBefore(dom, parentNode); + grandparentNode.removeChild(parentNode); + } else { + grandparentNode = DOC.createDocumentFragment(); + grandparentNode.appendChild(dom); + } + if (resumeFocus) { + if (cached) { + cached.focus(); + cached.resumeFocusEvents(); + } else { + activeElement.focus(); + } + if (grannyFly) { + grannyFly.resumeFocusEvents(); + grannyFly.set({ + tabIndex: tabIndex + }); + } + } + return this; + }, + /**. + * Walks up the dom looking for a parent node that matches the passed simple selector + * (e.g. 'div.some-class' or 'span:first-child'). + * This is a shortcut for findParentNode() that always returns an Ext.dom.Element. + * @param {String} simpleSelector The simple selector to test. See {@link Ext.dom.Query} + * for information about simple selectors. + * @param {Number/String/HTMLElement/Ext.dom.Element} [limit] + * The max depth to search as a number or an element that causes the upward + * traversal to stop and is **not** considered for inclusion as the result. + * (defaults to 50 || document.documentElement) + * @param {Boolean} [returnDom=false] True to return the DOM node instead of Ext.dom.Element + * @return {Ext.dom.Element/HTMLElement} The matching DOM node (or HTMLElement if + * _returnDom_ is _true_). Or null if no match was found. + */ + up: function(simpleSelector, limit, returnDom) { + return this.findParentNode(simpleSelector, limit, !returnDom); + }, + /** + * @method update + * @inheritdoc Ext.dom.Element#method-setHtml + * @deprecated 5.0.0 Please use {@link #setHtml} instead. + */ + update: function(html) { + return this.setHtml(html); + }, + /** + * Creates and wraps this element with another element + * @param {Object} [config] DomHelper element config object for the wrapper element or null for an empty div + * @param {Boolean} [returnDom=false] True to return the raw DOM element instead of Ext.dom.Element + * @param {String} [selector] A CSS selector to select a descendant node within the created element to use as the wrapping element. + * @return {HTMLElement/Ext.dom.Element} The newly created wrapper element + */ + wrap: function(config, returnDom, selector) { + var me = this, + dom = me.dom, + result = Ext.DomHelper.insertBefore(dom, config || { + tag: "div" + }, !returnDom), + newEl = (wrapFly || (wrapFly = new Ext.dom.Fly())).attach(Ext.getDom(result)), + // In case they pass returnDom: true + target = newEl, + activeElement = (activeElFly || (activeElFly = new Ext.dom.Fly())).attach(Ext.Element.getActiveElement()), + cached, resumeFocus, tabIndex; + cached = Ext.cache[activeElement.dom.id]; + // If the element is in the cache, we need to get the instance so + // we can suspend events on it. If it's not in the cache, it can't + // have any events so we don't need to suspend on it. + if (cached) { + activeElement = cached; + } + if (selector) { + target = newEl.selectNode(selector, returnDom); + } + if (me.contains(activeElement)) { + if (cached) { + cached.suspendFocusEvents(); + } + // This is workaround for the nasty IE behavior w/r/t removing and adding + // DOM nodes that contain focus. When this happens, focus will fall back + // to the document body *after* the present code execution path finishes, + // with no way to control this. Instead of trying to refocus the element + // asynchronously in a callback, we're focusing the wrapper instead, + // adding the dom to the wrapper, and then refocusing the dom; + // all synchronous and dandy. + // The only side effect of all this focus juggling is that focus/blur + // events will fire asynchronously after this code path finishes (in IE), + // but we deal with that by ignoring these events *on particular elements*. + // Focus event publisher will look for focus suspension flag on the element, + // and since the flag is cleared asynchronously in the immediate callback, + // we have enough cycles to ignore unwanted events to get away with it + // but not too many to step on someone else's toes (hopefully). + tabIndex = Ext.getDom(newEl).getAttribute('tabIndex'); + newEl.set({ + tabIndex: -1 + }); + newEl.suspendFocusEvents(); + newEl.focus(); + resumeFocus = true; + } + (target.dom || target).appendChild(dom); + if (resumeFocus) { + if (cached) { + cached.focus(); + cached.resumeFocusEvents(); + } else { + activeElement.focus(); + } + newEl.resumeFocusEvents(); + // Most often tabIndex will be undefined, and we don't want to + // make the wrapper focusable by accident. + newEl.set({ + tabIndex: tabIndex + }); + } + return result; + }, + /** + * Checks whether this element can be focused programmatically or by clicking. + * To check if an element is in the document tab flow, use {@link #isTabbable}. + * + * @return {Boolean} True if the element is focusable + */ + isFocusable: function(skipVisibility) { + var dom = this.dom, + focusable = false, + nodeName; + if (dom && !dom.disabled) { + nodeName = dom.nodeName; + /* + * An element is focusable if: + * - It is naturally focusable, or + * - It is an anchor or link with href attribute, or + * - It has a tabIndex, or + * - It is an editing host (contenteditable="true") + * + * Also note that we can't check dom.tabIndex because IE will return 0 + * for elements that have no tabIndex attribute defined, regardless of + * whether they are naturally focusable or not. + */ + focusable = !!Ext.Element.naturallyFocusableTags[nodeName] || ((nodeName === 'A' || nodeName === 'LINK') && !!dom.href) || dom.getAttribute('tabIndex') != null || dom.contentEditable === 'true'; + // In IE8, does not have a corresponding style + // so isVisible() will assume that it's not hidden. + if (Ext.isIE8 && nodeName === 'INPUT' && dom.type === 'hidden') { + focusable = false; + } + // Invisible elements cannot be focused, so check that as well + // uness the caller doesn't care. + focusable = focusable && (skipVisibility || this.isVisible(true)); + } + return focusable; + }, + /** + * Returns `true` if this Element is an input field, or is editable in any way. + * @return {Boolean} `true` if this Element is an input field, or is editable in any way. + */ + isInputField: function() { + var dom = this.dom, + contentEditable = dom.contentEditable; + // contentEditable will default to inherit if not specified, only check if the + // attribute has been set or explicitly set to true + // http://html5doctor.com/the-contenteditable-attribute/ + // Also skip tags of type="button", we use them for checkboxes + // and radio buttons + if ((Ext.Element.inputTags[dom.tagName] && dom.type !== 'button') || (contentEditable === '' || contentEditable === 'true')) { + return true; + } + return false; + }, + /** + * Checks whether this element participates in the sequential focus navigation, + * and can be reached by using Tab key. + * + * @param {Boolean} [includeHidden=false] pass `true` if hidden, or unattached elements should be returned. + * @return {Boolean} True if the element is tabbable. + */ + isTabbable: function(includeHidden) { + var dom = this.dom, + tabbable = false, + nodeName, hasIndex, tabIndex; + if (dom && !dom.disabled) { + nodeName = dom.nodeName; + // Can't use dom.tabIndex here because IE will return 0 for elements + // that have no tabindex attribute defined, regardless of whether they are + // naturally tabbable or not. + tabIndex = dom.getAttribute('tabIndex'); + hasIndex = tabIndex != null; + tabIndex -= 0; + // Anchors and links are only naturally tabbable if they have href attribute + // See http://www.w3.org/TR/html5/editing.html#specially-focusable + if (nodeName === 'A' || nodeName === 'LINK') { + if (dom.href) { + // It is also possible to make an anchor untabbable by setting + // tabIndex < 0 on it + tabbable = hasIndex && tabIndex < 0 ? false : true; + } else // Anchor w/o href is tabbable if it has tabIndex >= 0, + // or if it's editable + { + if (dom.contentEditable === 'true') { + tabbable = !hasIndex || (hasIndex && tabIndex >= 0) ? true : false; + } else { + tabbable = hasIndex && tabIndex >= 0 ? true : false; + } + } + } + // If an element has contenteditable="true" or is naturally tabbable, + // then it is a potential candidate unless its tabIndex is < 0. + else if (dom.contentEditable === 'true' || Ext.Element.naturallyTabbableTags[nodeName]) { + tabbable = hasIndex && tabIndex < 0 ? false : true; + } else // That leaves non-editable elements that can only be made tabbable + // by slapping tabIndex >= 0 on them + { + if (hasIndex && tabIndex >= 0) { + tabbable = true; + } + } + // In IE8, does not have a corresponding style + // so isVisible() will assume that it's not hidden. + if (Ext.isIE8 && nodeName === 'INPUT' && dom.type === 'hidden') { + tabbable = false; + } + // Invisible elements can't be tabbed into. If we have a component ref + // we'll also check if the component itself is visible before incurring + // the expense of DOM style reads. + // Allow caller to specify that hiddens should be included. + tabbable = tabbable && (includeHidden || ((!this.component || this.component.isVisible(true)) && this.isVisible(true))); + } + return tabbable; + }, + ripplingCls: Ext.baseCSSPrefix + 'rippling', + ripplingTransitionCls: Ext.baseCSSPrefix + 'ripple-transition', + ripplingUnboundCls: Ext.baseCSSPrefix + 'rippling-unbound', + rippleBubbleCls: Ext.baseCSSPrefix + 'ripple-bubble', + rippleContainerCls: Ext.baseCSSPrefix + 'ripple-container', + rippleWrapperCls: Ext.baseCSSPrefix + 'ripple-wrapper', + // elements with 'display' property in this map cannot act as ripple container + noRippleDisplayMap: { + table: 1, + 'table-row': 1, + 'table-row-group': 1 + }, + // elements with tag name in this map cannot act as ripple container + noRippleTagMap: { + TABLE: 1, + TR: 1, + TBODY: 1 + }, + /** + * Creates a ripple effect over this element. The element should be positioned + * (either `relative` or `absolute`) prior to calling this method. + * + * @param {String/Event/Ext.event.Event} [event] The event to use for ripple + * positioning. + * + * @param {Object/String} [options] Ripple options object or color to use for ripple + * @param {String} [options.color] The color to use for the ripple effect or + * `'default'` to use the stylesheet default color + * {@link Global_CSS#$ripple-background-color}. When no `color` is given, the + * element's `color` style is used. + * @param {Boolean} [options.release] Optional determines if the ripple should happen on release. Defaults to down/start + * @param {String} [options.delegate] Optional selector for which child to add the ripple into + * @param {String} [options.measureSelector] Optional selector for which child to use to measure for ripple size + * @param {Number[]} [options.position] The [x,y] position in which to start the ripple. + * @param {Boolean} [options.centered] Set to `true` to override all position + * information and forces the ripple to be centered inside its parent. + * @param {Boolean/String} [options.bound] Determines if the ripple is bound to + * the parent container (default). If false ripple will expand outside of container. + * @param {Boolean/Number} [options.diameterLimit] Maximum size, in pixels, that a ripple can be. + * A value of false or 0 will cause the ripple to fill its container. A value of true will cause + * the ripple to use the default maximum size. + * @param {Boolean/String} [options.fit] For bound ripples only. Determines if + * ripple should search up the dom for an element that will fit the ripple + * without clipping. Setting to false will force the unbound ripple into the specified container + * Defaults to true + * @param {Number} [options.destroyTime] The time (in milliseconds) to wait until + * the ripple is destroyed. + */ + ripple: function(event, options) { + if (options === true || !options) { + options = {}; + } else if (Ext.isString(options)) { + options = { + color: options + }; + } + var me = this, + rippleParent = Ext.isString(options.delegate) ? me.down(options.delegate) : me, + rippleMeasureEl = Ext.isString(options.measureSelector) ? me.down(options.measureSelector) : null, + color = window.getComputedStyle(rippleParent.dom).color, + unbound = options.bound === false, + position = options.position, + ripplingCls = me.ripplingCls, + ripplingTransitionCls = me.ripplingTransitionCls, + ripplingUnboundCls = me.ripplingUnboundCls, + rippleBubbleCls = me.rippleBubbleCls, + rippleContainerCls = me.rippleContainerCls, + rippleWrapperCls = me.rippleWrapperCls, + offset, width, height, rippleDiameter, center, measureElWidth, measureElHeight, rippleSize, pos, posX, posY, rippleWrapper, rippleContainer, rippleBubble, rippleDestructor, rippleClearFn, rippleDestructionTimer, rippleBox, unboundEl, unboundElData, timeout; + if (rippleParent) { + offset = rippleParent.getXY(); + width = rippleParent.getWidth(); + height = rippleParent.getHeight(); + timeout = rippleParent.$rippleClearTimeout; + if (timeout) { + rippleParent.$rippleClearTimeout = Ext.undefer(timeout); + } + // If a measure element exists use that to determine the ripple diameter + // otherwise we will just use the parent + if (rippleMeasureEl) { + measureElWidth = rippleMeasureEl.getWidth(); + measureElHeight = rippleMeasureEl.getHeight(); + rippleDiameter = Math.max(measureElWidth, measureElHeight); + } else { + rippleDiameter = width > height ? width : height; + } + // Cap the diameter based on the default or provided limit + if (options.diameterLimit === undefined || options.diameterLimit === true) { + rippleDiameter = Math.min(rippleDiameter, Element.maxRippleDiameter); + } else if (options.diameterLimit && options.diameterLimit !== false && options.diameterLimit !== 0) { + rippleDiameter = Math.min(rippleDiameter, options.diameterLimit); + } + // determine the center of the element we are going to ripple over + center = [ + offset[0] + width / 2, + offset[1] + height / 2 + ]; + if (unbound) { + if (options.fit !== false) { + // Compute the bounding rippleBox that is centered over the + // target element. + rippleSize = rippleDiameter * 2.15; + // anim scales to 2.15 + rippleBox = rippleParent.getRegion(); + rippleBox.setPosition(rippleBox.getCenter()).setSize(rippleSize).translateBy(-rippleSize / 2, -rippleSize / 2); + // Find the nearest parent el that will be able to fully contain + // the ripple... we assume that the el we are rippling is not too + // close to the edge + unboundEl = me.up(function(candidate) { + var fly = Ext.fly(candidate, 'ripple'); + return !(candidate.tagName in me.noRippleTagMap) && !(fly.getStyle('display') in me.noRippleDisplayMap) && (fly.getRegion().contains(rippleBox)); + }) || Ext.getBody(); + } else { + unboundEl = rippleParent; + } + } + // if the first param was a string, it was meant to be a color + // otherwise if it an unwrapped event lets wrap it up + if (Ext.isString(event)) { + options.color = event; + event = null; + } else if (event && !event.isEvent) { + event = new Ext.event.Event(event); + } + // Check for preventRipple on the event and skip everything if its true + if (event && event.isEvent) { + // Prevent ripples from the same event + if (event.browserEvent.$preventRipple) { + return; + } + position = event.getXY(); + event.browserEvent.$preventRipple = true; + } + // unbound or centered items always center, otherwise if position is + // provided use it + pos = (!unbound && !options.centered && position) || center; + posX = pos[0] - offset[0] - (rippleDiameter / 2); + posY = pos[1] - offset[1] - (rippleDiameter / 2); + // Ripple Parent always needs to be notified that it should transition with the ripple + // bound or not + rippleParent.addCls(ripplingTransitionCls); + if (!unbound) { + rippleParent.addCls(ripplingCls); + // Is there already a container for ripples, reuse it. + rippleContainer = rippleParent.child('.' + rippleContainerCls); + } else { + // unbound ripples are added to the body inside the ripple wrapper. + // check to see if this wrapper exists, if not create it + unboundElData = unboundEl.getData(); + rippleWrapper = unboundElData.rippleWrapper; + if (!rippleWrapper) { + // insertFirst is important because of Field margin-top:0 rules + // to collapse field spacing in form panels. + unboundElData.rippleWrapper = rippleWrapper = unboundEl.insertFirst({ + style: 'position: absolute; top: 0; left: 0', + cls: rippleWrapperCls + ' ' + ripplingCls + ' ' + ripplingUnboundCls + }); + } + } + if (!rippleContainer) { + if (unbound) { + // unbound ripples are positioned inside the ripple-wrapper, + // which is inside the body + rippleContainer = rippleWrapper.append({ + cls: rippleContainerCls + }); + // position the unbound ripple over-top the element + rippleContainer.setXY(offset); + } else { + // body ripples are positioned inside the rippleParent, which is + // the element being rippled + rippleContainer = rippleParent.append({ + cls: rippleContainerCls + }); + } + } + // create the actual ripple bubble element + rippleBubble = rippleContainer.append({ + cls: rippleBubbleCls + }); + if (options.color !== 'default') { + rippleBubble.setStyle('backgroundColor', options.color || color); + } + rippleBubble.setWidth(rippleDiameter); + rippleBubble.setHeight(rippleDiameter); + rippleBubble.setTop(posY); + rippleBubble.setLeft(posX); + rippleClearFn = function() { + // Allow for transition to happen then remove classes + // we do this instead of a transtionend listener + // as we do not know which element is transitioning + if (!rippleParent.destroyed) { + rippleParent.$rippleClearTimeout = Ext.defer(function() { + rippleParent.removeCls([ + ripplingCls, + ripplingTransitionCls + ]); + rippleParent.$rippleClearTimeout = null; + }, 50); + } + }; + rippleDestructor = function() { + var ripple, timeout; + // destroy the ripple + rippleBubble.destroy(); + // remove from lookup + if (me.$ripples) { + delete me.$ripples[rippleBubble.id]; + } + timeout = rippleParent.$rippleClearTimeout; + if (timeout) { + rippleParent.$rippleClearTimeout = Ext.undefer(timeout); + } + if (unbound) { + // always destroy unbound ripple containers as they are never + // re-used. only the ripple-wrapper is reused + rippleContainer.destroy(); + // Determine if there are any other ripples still active in the wrapper + ripple = rippleWrapper.child('.' + rippleContainerCls); + // If there are no other ripples, clean up all ripple related DOM + if (!ripple) { + unboundElData.rippleWrapper = null; + rippleWrapper.destroy(); + rippleClearFn(); + } + } else { + // Determine if there are any other ripples still active in the parent + ripple = rippleContainer.child('.' + rippleBubbleCls); + // If there are no other ripples, clean up all ripple related DOM + if (!ripple) { + rippleContainer.destroy(); + rippleClearFn(); + } + } + }; + rippleDestructionTimer = Ext.defer(rippleDestructor, options.destroyTime || 1000, me); + // Keep a list of all the current ripples, for cleanup later + if (!me.$ripples) { + me.$ripples = {}; + } + me.$ripples[rippleBubble.id] = { + timerId: rippleDestructionTimer, + destructor: rippleDestructor + }; + rippleBubble.addCls(Ext.baseCSSPrefix + 'ripple'); + } + }, + destroyAllRipples: function() { + var me = this, + rippleEl, ripple; + for (rippleEl in me.$ripples) { + ripple = me.$ripples[rippleEl]; + Ext.undefer(ripple.timerId); + if (ripple.destructor) { + ripple.destructor(); + } + } + me.$ripples = null; + }, + privates: { + /** + * @private + */ + findTabbableElements: function(options) { + var skipSelf, skipChildren, excludeRoot, includeSaved, includeHidden, + dom = this.dom, + cAttr = Ext.Element.tabbableSavedCounterAttribute, + selection = [], + idx = 0, + nodes, node, fly, i, len, tabIndex; + if (!dom) { + return selection; + } + if (options) { + skipSelf = options.skipSelf; + skipChildren = options.skipChildren; + excludeRoot = options.excludeRoot; + includeSaved = options.includeSaved; + includeHidden = options.includeHidden; + } + excludeRoot = excludeRoot && Ext.getDom(excludeRoot); + if (excludeRoot && excludeRoot.contains(dom)) { + return selection; + } + if (!skipSelf && ((includeSaved && dom.hasAttribute(cAttr)) || this.isTabbable(includeHidden))) { + selection[idx++] = dom; + } + if (skipChildren) { + return selection; + } + nodes = dom.querySelectorAll(Ext.Element.tabbableSelector); + len = nodes.length; + if (!len) { + return selection; + } + fly = new Ext.dom.Fly(); + // We're only interested in the elements that an user can *tab into*, + // not all programmatically focusable elements. So we have to filter + // these out. + for (i = 0; i < len; i++) { + node = nodes[i]; + // A node with tabIndex < 0 absolutely can't be tabbable + // so we can save a function call if that is the case. + // Note that we can't use node.tabIndex here because IE + // will return 0 for elements that have no tabindex + // attribute defined, regardless of whether they are + // tabbable or not. + tabIndex = +node.getAttribute('tabIndex'); + // quicker than parseInt + // tabIndex value may be null for nodes with no tabIndex defined; + // most of those may be naturally tabbable. We don't want to + // check this here, that's isTabbable()'s job and it's not trivial. + // We explicitly check that tabIndex is not negative. The expression + // below is purposeful if hairy; this is a very hot code path so care + // is taken to minimize the amount of DOM calls that could be avoided. + // A node may have its tabindex saved by previous calls to + // saveTabbableState(); in that case we need to return that node + // so that its saved counter could be properly incremented or + // decremented. + if (((includeSaved && node.hasAttribute(cAttr)) || (!(tabIndex < 0) && fly.attach(node).isTabbable(includeHidden))) && !(excludeRoot && (excludeRoot === node || excludeRoot.contains(node)))) { + selection[idx++] = node; + } + } + return selection; + }, + /** + * @private + */ + saveTabbableState: function(options) { + var counterAttr = Ext.Element.tabbableSavedCounterAttribute, + savedAttr = Ext.Element.tabbableSavedValueAttribute, + counter, nodes, node, i, len; + // By default include already saved tabbables, and just increase their save counter. + // For example, if a View with saved tabbables is covered by a modal Window, saveTabbableState + // Must disable tabbability for the whole document. But upon unmask, the View must not + // be restored to tabbability. It must only have its save level decremented. + // AbstractView#toggleChildrenTabbability however pases this as false so that + // it may be called upon row add and it does not increment save levels on already saved tabbables. + if (!options || options.includeSaved == null) { + options = Ext.Object.chain(options || null); + options.includeSaved = true; + } + nodes = this.findTabbableElements(options); + for (i = 0 , len = nodes.length; i < len; i++) { + node = nodes[i]; + counter = +node.getAttribute(counterAttr); + if (counter > 0) { + node.setAttribute(counterAttr, ++counter); + } else { + // tabIndex could be set on both naturally tabbable and generic elements. + // Either way we need to save it to restore later. + if (node.hasAttribute('tabIndex')) { + node.setAttribute(savedAttr, node.getAttribute('tabIndex')); + } else // When no tabIndex is specified, that means a naturally tabbable element. + { + node.setAttribute(savedAttr, 'none'); + } + // We disable the tabbable state by setting tabIndex to -1. + // The element can still be focused programmatically though. + node.setAttribute('tabIndex', '-1'); + node.setAttribute(counterAttr, '1'); + } + } + return nodes; + }, + /** + * @private + */ + restoreTabbableState: function(options) { + var dom = this.dom, + counterAttr = Ext.Element.tabbableSavedCounterAttribute, + savedAttr = Ext.Element.tabbableSavedValueAttribute, + nodes = [], + skipSelf = options && options.skipSelf, + skipChildren = options && options.skipChildren, + reset = options && options.reset, + idx, counter, node, i, len; + if (!dom) { + return this; + } + if (!skipChildren) { + nodes = Ext.Array.from(dom.querySelectorAll('[' + counterAttr + ']')); + } + if (!skipSelf) { + nodes.unshift(dom); + } + for (i = 0 , len = nodes.length; i < len; i++) { + node = nodes[i]; + if (!node.hasAttribute(counterAttr) || !node.hasAttribute(savedAttr)) { + + continue; + } + counter = +node.getAttribute(counterAttr); + if (!reset && counter > 1) { + node.setAttribute(counterAttr, --counter); + + continue; + } + idx = node.getAttribute(savedAttr); + // That is a naturally tabbable element + if (idx === 'none') { + node.removeAttribute('tabIndex'); + } else { + node.setAttribute('tabIndex', idx); + } + node.removeAttribute(savedAttr); + node.removeAttribute(counterAttr); + } + return nodes; + }, + /** + * @private + */ + setTabIndex: function(tabIndex) { + var dom = this.dom, + savedAttr = Ext.Element.tabbableSavedValueAttribute; + if (dom.hasAttribute(savedAttr)) { + if (tabIndex == null) { + // Equivalent to removing tabIndex while not saved + dom.setAttribute(savedAttr, 'none'); + dom.removeAttribute('tabIndex'); + } else { + dom.setAttribute(savedAttr, tabIndex); + } + } else { + if (tabIndex == null) { + dom.removeAttribute('tabIndex'); + } else { + dom.setAttribute('tabIndex', tabIndex); + } + } + }, + doAddListener: function(eventName, fn, scope, options, order, caller, manager) { + var me = this, + originalName = eventName, + observableDoAddListener, additiveEventName, translatedEventName; + // Even though the superclass method does conversion to lowercase, we need + // to do it here because we need to use the lowercase name for lookup + // in the event translation map. + eventName = Ext.canonicalEventName(eventName); + // Blocked events (such as emulated mouseover in mobile webkit) are prevented + // from firing + if (!me.blockedEvents[eventName]) { + observableDoAddListener = me.mixins.observable.doAddListener; + options = options || {}; + if (Element.useDelegatedEvents === false) { + options.delegated = options.delegated || false; + } + if (options.translate !== false) { + // translate events where applicable. This allows applications that + // were written for desktop to work on mobile devices and vice versa. + additiveEventName = me.additiveEvents[eventName]; + if (additiveEventName) { + // additiveEvents means the translation is "additive" - meaning we + // need to attach the original event in addition to the translated + // one. An example of this is devices that have both mousedown + // and touchstart + options.type = eventName; + eventName = additiveEventName; + observableDoAddListener.call(me, eventName, fn, scope, options, order, caller, manager); + } + translatedEventName = me.eventMap[eventName]; + if (translatedEventName) { + // options.type may have already been set above + options.type = options.type || eventName; + if (manager) { + options.managedName = originalName; + } + eventName = translatedEventName; + } + } + if (observableDoAddListener.call(me, eventName, fn, scope, options, order, caller, manager)) { + if (me.longpressEvents[eventName] && (++me.longpressListenerCount === 1)) { + me.on('MSHoldVisual', 'preventMsHoldVisual', me); + } + } + if (manager && translatedEventName) { + delete options.managedName; + } + // after the listener has been added to the ListenerStack, it's original + // "type" (for translated events) will be stored on the listener object in + // the ListenerStack. We can now delete type from the options object + // since it is not a user-supplied option + delete options.type; + } + }, + doRemoveListener: function(eventName, fn, scope) { + var me = this, + observableDoRemoveListener, translatedEventName, additiveEventName, removed; + // Even though the superclass method does conversion to lowercase, we need + // to do it here because we need to use the lowercase name for lookup + // in the event translation map. + eventName = Ext.canonicalEventName(eventName); + // Blocked events (such as emulated mouseover in mobile webkit) are prevented + // from firing + if (!me.blockedEvents[eventName]) { + observableDoRemoveListener = me.mixins.observable.doRemoveListener; + // translate events where applicable. This allows applications that + // were written for desktop to work on mobile devices and vice versa. + additiveEventName = me.additiveEvents[eventName]; + if (additiveEventName) { + // additiveEvents means the translation is "additive" - meaning we + // need to remove the original event in addition to the translated + // one. An example of this is devices that have both mousedown + // and touchstart + eventName = additiveEventName; + observableDoRemoveListener.call(me, eventName, fn, scope); + } + translatedEventName = me.eventMap[eventName]; + if (translatedEventName) { + removed = observableDoRemoveListener.call(me, translatedEventName, fn, scope); + } + // no "else" here because we need to ensure that we remove translate:false + // listeners + removed = observableDoRemoveListener.call(me, eventName, fn, scope) || removed; + if (removed) { + if (me.longpressEvents[eventName] && !--me.longpressListenerCount) { + me.un('MSHoldVisual', 'preventMsHoldVisual', me); + } + } + } + }, + _initEvent: function(eventName) { + return (this.events[eventName] = new Ext.dom.ElementEvent(this, eventName)); + }, + _getDisplay: function() { + var data = this.getData(), + display = data[ORIGINALDISPLAY]; + if (display === undefined) { + data[ORIGINALDISPLAY] = display = ''; + } + return display; + }, + /** + * Returns the publisher for a given event + * @param {String} eventName + * @param {Boolean} [noTranslate] `true` if the event is a non translated event + * @private + * @return {Ext.event.publisher.Publisher} + */ + _getPublisher: function(eventName, noTranslate) { + var Publisher = Ext.event.publisher.Publisher, + publisher = Publisher.publishersByEvent[eventName], + isNative = noTranslate && !Ext.event.Event.gestureEvents[eventName]; + // Dom publisher acts as the default publisher for all events that are + // not explicitly handled by another publisher. + // ElementSize handles the 'resize' event, except on the window + // object, where it is handled by Dom publisher. + // If the event is a native event (not translated), we want to use the DOM publisher. + // For example the dragstart gesture would automatically shadow any native + // drag events, so we force the lower level publisher to be used. The exception is for touch + // events, they all need to be handled by the gesture publisher so they can be interrogated + // and produce the correct output. + if (isNative || !publisher || (this.dom === window && eventName === 'resize')) { + publisher = Publisher.publishers.dom; + } + return publisher; + }, + isFocusSuspended: function() { + var data = this.peekData(); + return data && data.suspendFocusEvents; + }, + preventMsHoldVisual: function(e) { + e.preventDefault(); + }, + suspendFocusEvents: function() { + if (!this.isFly) { + this.suspendEvent('focus', 'blur'); + } + this.getData().suspendFocusEvents = true; + }, + resumeFocusEvents: function() { + function resumeFn() { + var data; + if (!this.destroyed) { + data = this.getData(); + if (data) { + data.suspendFocusEvents = false; + } + if (!this.isFly) { + this.resumeEvent('focus', 'blur'); + } + } + } + if (!this.destroyed && this.getData().suspendFocusEvents) { + if (Ext.isIE && !this.isFly) { + this.resumeFocusEventsTimer = Ext.asap(resumeFn, this); + } else { + resumeFn.call(this); + } + } + } + }, + deprecated: { + '5.0': { + methods: { + /** + * @method getHTML + * @inheritdoc Ext.dom.Element#getHtml + * @deprecated 5.0.0 Please use {@link #getHtml} instead. + */ + getHTML: 'getHtml', + /** + * @method getPageBox + * Returns an object defining the area of this Element which can be passed to + * {@link Ext.util.Positionable#setBox} to set another Element's size/location to match this element. + * + * @param {Boolean} [getRegion] If true an Ext.util.Region will be returned + * @return {Object/Ext.util.Region} box An object in the following format: + * + * { + * left: , + * top: , + * width: , + * height: , + * bottom: , + * right: + * } + * + * The returned object may also be addressed as an Array where index 0 contains + * the X position and index 1 contains the Y position. So the result may also be + * used for {@link #setXY} + * @deprecated 5.0.0 use {@link Ext.util.Positionable#getBox} to get a box object, and + * {@link Ext.util.Positionable#getRegion} to get a {@link Ext.util.Region Region}. + */ + getPageBox: function(getRegion) { + var me = this, + dom = me.dom, + isDoc = dom.nodeName === 'BODY', + w = isDoc ? Element.getViewportWidth() : dom.offsetWidth, + h = isDoc ? Element.getViewportHeight() : dom.offsetHeight, + xy = me.getXY(), + t = xy[1], + r = xy[0] + w, + b = xy[1] + h, + l = xy[0]; + if (getRegion) { + return new Ext.util.Region(t, r, b, l); + } else { + return { + left: l, + top: t, + width: w, + height: h, + right: r, + bottom: b + }; + } + }, + /** + * @method isTransparent + * Returns `true` if the value of the given property is visually transparent. This + * may be due to a 'transparent' style value or an rgba value with 0 in the alpha + * component. + * @param {String} prop The style property whose value is to be tested. + * @return {Boolean} `true` if the style property is visually transparent. + * @deprecated 5.0.0 This method is deprecated. + */ + isTransparent: function(prop) { + var value = this.getStyle(prop); + return value ? transparentRe.test(value) : false; + }, + /** + * @method purgeAllListeners + * @inheritdoc Ext.dom.Element#clearListeners + * @deprecated 5.0.0 Please use {@link #clearListeners} instead. + */ + purgeAllListeners: 'clearListeners', + /** + * @method removeAllListeners + * @inheritdoc Ext.dom.Element#clearListeners + * @deprecated 5.0.0 Please use {@link #clearListeners} instead. + */ + removeAllListeners: 'clearListeners', + /** + * @method setHTML + * @inheritdoc Ext.dom.Element#setHtml + * @deprecated 5.0.0 Please use {@link #setHtml} instead. + */ + setHTML: 'setHtml' + } + } + } + }; +}, function(Element) { + var DOC = document, + docEl = DOC.documentElement, + prototype = Element.prototype, + supports = Ext.supports, + pointerdown = 'pointerdown', + pointermove = 'pointermove', + pointerup = 'pointerup', + pointercancel = 'pointercancel', + MSPointerDown = 'MSPointerDown', + MSPointerMove = 'MSPointerMove', + MSPointerUp = 'MSPointerUp', + MSPointerCancel = 'MSPointerCancel', + mousedown = 'mousedown', + mousemove = 'mousemove', + mouseup = 'mouseup', + mouseover = 'mouseover', + mouseout = 'mouseout', + mouseenter = 'mouseenter', + mouseleave = 'mouseleave', + touchstart = 'touchstart', + touchmove = 'touchmove', + touchend = 'touchend', + touchcancel = 'touchcancel', + click = 'click', + dblclick = 'dblclick', + tap = 'tap', + doubletap = 'doubletap', + eventMap = prototype.eventMap = {}, + additiveEvents = prototype.additiveEvents = {}, + oldId = Ext.id, + eventOptions; + prototype._init(Element); + delete prototype._init; + /** + * Generates unique ids. If the element already has an id, it is unchanged + * @member Ext + * @param {Object/HTMLElement/Ext.dom.Element} [obj] The element to generate an id for + * @param {String} prefix (optional) Id prefix (defaults "ext-gen") + * @return {String} The generated Id. + */ + Ext.id = function(obj, prefix) { + var el = obj && Ext.getDom(obj, true), + sandboxPrefix, id; + if (!el) { + id = oldId(obj, prefix); + } else if (!(id = el.id)) { + id = oldId(null, prefix || Element.prototype.identifiablePrefix); + if (Ext.isSandboxed) { + sandboxPrefix = Ext.sandboxPrefix || (Ext.sandboxPrefix = Ext.sandboxName.toLowerCase() + '-'); + id = sandboxPrefix + id; + } + el.id = id; + } + return id; + }; + if (supports.PointerEvents) { + eventMap[mousedown] = pointerdown; + eventMap[mousemove] = pointermove; + eventMap[mouseup] = pointerup; + eventMap[touchstart] = pointerdown; + eventMap[touchmove] = pointermove; + eventMap[touchend] = pointerup; + eventMap[touchcancel] = pointercancel; + // On devices that support pointer events we block pointerover, pointerout, + // pointerenter, and pointerleave when triggered by touch input (see + // Ext.event.publisher.Dom#blockedPointerEvents). This is because mouseover + // behavior is typically not desired when touching the screen. This covers the + // use case where user code requested a pointer event, however mouseover/mouseout + // events are not cancellable, period. + // http://www.w3.org/TR/pointerevents/#mapping-for-devices-that-do-not-support-hover + // To ensure mouseover/out handlers don't fire when touching the screen, we need + // to translate them to their pointer equivalents + eventMap[mouseover] = 'pointerover'; + eventMap[mouseout] = 'pointerout'; + eventMap[mouseenter] = 'pointerenter'; + // No decent way to feature detect this, pointerleave relatedTarget is + // incorrect on IE11, so force it to use mouseleave here. + // See: https://connect.microsoft.com/IE/feedback/details/851111/ev-relatedtarget-in-pointerleave-indicates-departure-element-not-destination-element + if (!Ext.isIE11) { + eventMap[mouseleave] = 'pointerleave'; + } + } else if (supports.MSPointerEvents) { + // IE10 + eventMap[pointerdown] = MSPointerDown; + eventMap[pointermove] = MSPointerMove; + eventMap[pointerup] = MSPointerUp; + eventMap[pointercancel] = MSPointerCancel; + eventMap[mousedown] = MSPointerDown; + eventMap[mousemove] = MSPointerMove; + eventMap[mouseup] = MSPointerUp; + eventMap[touchstart] = MSPointerDown; + eventMap[touchmove] = MSPointerMove; + eventMap[touchend] = MSPointerUp; + eventMap[touchcancel] = MSPointerCancel; + // translate mouseover/out so they can be prevented on touch screens. + // (see above comment in the PointerEvents section) + eventMap[mouseover] = 'MSPointerOver'; + eventMap[mouseout] = 'MSPointerOut'; + } else if (supports.TouchEvents) { + eventMap[pointerdown] = touchstart; + eventMap[pointermove] = touchmove; + eventMap[pointerup] = touchend; + eventMap[pointercancel] = touchcancel; + eventMap[mousedown] = touchstart; + eventMap[mousemove] = touchmove; + eventMap[mouseup] = touchend; + eventMap[click] = tap; + eventMap[dblclick] = doubletap; + if (Ext.os.is.Desktop) { + // Touch enabled desktop browsers on windows such as Firefox and Chrome fire + // both mouse events and touch events, so we have to attach listeners for both + // kinds when either one is requested. There are a couple rules to keep in mind: + // 1. When the mouse is used, only a mouse event is fired + // 2. When interacting with the touch screen touch events are fired. + // 3. After a touchstart/touchend sequence, if there was no touchmove in + // between, the browser will fire a mousemove/mousedown/mousup sequence + // immediately after. This can cause problems because if we are listening + // for both kinds of events, handlers may run twice. To work around this + // issue we filter out the duplicate emulated mouse events by checking their + // coordinates and timing (see Ext.event.publisher.Gesture#onDelegatedEvent) + eventMap[touchstart] = mousedown; + eventMap[touchmove] = mousemove; + eventMap[touchend] = mouseup; + eventMap[touchcancel] = mouseup; + additiveEvents[mousedown] = mousedown; + additiveEvents[mousemove] = mousemove; + additiveEvents[mouseup] = mouseup; + additiveEvents[touchstart] = touchstart; + additiveEvents[touchmove] = touchmove; + additiveEvents[touchend] = touchend; + additiveEvents[touchcancel] = touchcancel; + additiveEvents[pointerdown] = mousedown; + additiveEvents[pointermove] = mousemove; + additiveEvents[pointerup] = mouseup; + additiveEvents[pointercancel] = mouseup; + } + } else { + // browser does not support either pointer or touch events, map all pointer and + // touch events to their mouse equivalents + eventMap[pointerdown] = mousedown; + eventMap[pointermove] = mousemove; + eventMap[pointerup] = mouseup; + eventMap[pointercancel] = mouseup; + eventMap[touchstart] = mousedown; + eventMap[touchmove] = mousemove; + eventMap[touchend] = mouseup; + eventMap[touchcancel] = mouseup; + } + if (Ext.isWebKit) { + // These properties were carried forward from touch-2.x. This translation used + // do be done by DomPublisher. TODO: do we still need this? + eventMap.transitionend = Ext.browser.getVendorProperyName('transitionEnd'); + eventMap.animationstart = Ext.browser.getVendorProperyName('animationStart'); + eventMap.animationend = Ext.browser.getVendorProperyName('animationEnd'); + } + if (!Ext.supports.MouseWheel && !Ext.isOpera) { + eventMap.mousewheel = 'DOMMouseScroll'; + } + eventOptions = prototype.$eventOptions = Ext.Object.chain(prototype.$eventOptions); + eventOptions.translate = eventOptions.capture = eventOptions.delegate = eventOptions.delegated = eventOptions.stopEvent = eventOptions.preventDefault = eventOptions.stopPropagation = // Ext.Element also needs "element" as one of its event options. Even though + // it does not directly process an element option, it may receive a listeners + // object that was passed through from a Component with the "element" option + // included. Including "element" in the event options ensures we don't attempt + // to process "element" as an event name. + eventOptions.element = 1; + prototype.styleHooks.opacity = { + name: 'opacity', + afterSet: function(dom, value, el) { + var shadow = el.shadow; + if (shadow) { + shadow.setOpacity(value); + } + } + }; + /** + * @member Ext + * @private + * Returns the `X,Y` position of this element without regard to any RTL + * direction settings. + */ + prototype.getTrueXY = prototype.getXY; + /** + * @member Ext + * @method getViewportHeight + * @inheritdoc Ext.dom.Element#getViewportHeight + * @since 6.5.0 + */ + Ext.getViewportHeight = Element.getViewportHeight; + /** + * @member Ext + * @method getViewportWidth + * @inheritdoc Ext.dom.Element#getViewportWidth + * @since 6.5.0 + */ + Ext.getViewportWidth = Element.getViewportWidth; + /** + * @member Ext + * @method select + * Shorthand for {@link Ext.dom.Element#method-select Ext.dom.Element.select}

+ * @inheritdoc Ext.dom.Element#method-select + */ + Ext.select = Element.select; + /** + * @member Ext + * @method query + * Shorthand for {@link Ext.dom.Element#method-query Ext.dom.Element.query}

+ * @inheritdoc Ext.dom.Element#method-query + */ + Ext.query = Element.query; + Ext.apply(Ext, { + /** + * @member Ext + * @method get + */ + get: function(element) { + return Element.get(element); + }, + /** + * @member Ext + * @method getDom + * Return the dom node for the passed String (id), dom node, or Ext.Element. + * Here are some examples: + * + * // gets dom node based on id + * var elDom = Ext.getDom('elId'); + * + * // gets dom node based on the dom node + * var elDom1 = Ext.getDom(elDom); + * + * // If we don't know if we are working with an + * // Ext.Element or a dom node use Ext.getDom + * function(el){ + * var dom = Ext.getDom(el); + * // do something with the dom node + * } + * + * __Note:__ the dom node to be found actually needs to exist (be rendered, etc) + * when this method is called to be successful. + * + * @param {String/HTMLElement/Ext.dom.Element} el + * @return {HTMLElement} + */ + getDom: function(el) { + if (!el || !DOC) { + return null; + } + // We could be passed an Element whos dom has been nulled on destruction; use 'dom' in rather than truthiness. + return typeof el === 'string' ? Ext.getElementById(el) : 'dom' in el ? el.dom : el; + }, + /** + * @member Ext + * Returns the current document body as an {@link Ext.dom.Element}. + * @return {Ext.dom.Element} The document body. + */ + getBody: function() { + if (!Ext._bodyEl) { + if (!DOC.body) { + throw new Error("[Ext.getBody] document.body does not yet exist"); + } + Ext._bodyEl = Ext.get(DOC.body); + Ext._bodyEl.skipGarbageCollection = true; + } + return Ext._bodyEl; + }, + /** + * @member Ext + * Returns the current document head as an {@link Ext.dom.Element}. + * @return {Ext.dom.Element} The document head. + */ + getHead: function() { + if (!Ext._headEl) { + Ext._headEl = Ext.get(DOC.head || DOC.getElementsByTagName('head')[0]); + Ext._headEl.skipGarbageCollection = true; + } + return Ext._headEl; + }, + /** + * @member Ext + * Returns the current HTML document object as an {@link Ext.dom.Element}. + * Typically used for attaching event listeners to the document. Note: since + * the document object is not an HTMLElement many of the Ext.dom.Element methods + * are not applicable and may throw errors if called on the returned + * Element instance. + * @return {Ext.dom.Element} The document. + */ + getDoc: function() { + if (!Ext._docEl) { + Ext._docEl = Ext.get(DOC); + Ext._docEl.skipGarbageCollection = true; + } + return Ext._docEl; + }, + /** + * @member Ext + * Returns the current window object as an {@link Ext.dom.Element}. + * Typically used for attaching event listeners to the window. Note: since + * the window object is not an HTMLElement many of the Ext.dom.Element methods + * are not applicable and may throw errors if called on the returned + * Element instance. + * @return {Ext.dom.Element} The window. + */ + getWin: function() { + if (!Ext._winEl) { + Ext._winEl = Ext.get(window); + Ext._winEl.skipGarbageCollection = true; + } + return Ext._winEl; + }, + /** + * @member Ext + * Removes an HTMLElement from the document. If the HTMLElement was previously + * cached by a call to Ext.get(), removeNode will call the {@link Ext.Element#destroy + * destroy} method of the {@link Ext.dom.Element} instance, which removes all DOM + * event listeners, and deletes the cache reference. + * @param {HTMLElement} node The node to remove + * @method + */ + removeNode: function(node) { + node = node.dom || node; + var id = node && node.id, + el = Ext.cache[id], + parent; + if (el) { + el.destroy(); + } else if (node && (node.nodeType === 3 || node.tagName.toUpperCase() !== 'BODY')) { + parent = node.parentNode; + if (parent) { + parent.removeChild(node); + } + } + } + }); + // TODO: make @inline work - SDKTOOLS-686 + // @inline + Ext.isGarbage = function(dom) { + // determines if the dom element is in the document or in the detached body element + // use by collectGarbage and Ext.get() + return dom && // window, document, documentElement, and body can never be garbage. + dom.nodeType === 1 && dom.tagName !== 'BODY' && dom.tagName !== 'HTML' && (// if the element does not have a parent node, it is definitely not in the + // DOM - we can exit immediately + !dom.parentNode || (// If the element has an offsetParent we can bail right away, it is + // definitely in the DOM. If offsetParent is null, the element is detached. + // If offsetParent is undefined, the element doesn't support offsetParent + // (e.g. SVGElement) and is not necessarily garbage; parentNode check above + // should be sufficient in this case. + dom.offsetParent === null && // if the element does not have an offsetParent it can mean the element is + // either not in the dom or it is hidden. The next step is to check to see + // if it can be found by id using either document.all or getElementById(), + // whichever is faster for the current browser. Normally we would not + // include IE-specific checks in the core package, however, in this + // case the function will be inlined and therefore cannot be overridden in + // the ext package. + ((Ext.isIE8 ? DOC.all[dom.id] : DOC.getElementById(dom.id)) !== dom) && // finally if the element was not found in the dom by id, we need to check + // the detachedBody element + !(Ext.detachedBodyEl && Ext.detachedBodyEl.isAncestor(dom)))); + }; + Ext.onInternalReady(function() { + var bodyCls = [], + theme; + // Element.unselectable relies on this listener to prevent selection in IE. Some other browsers support the event too + // but it is only strictly required for IE. In WebKit this listener causes subtle differences to how the browser handles + // the non-selection, e.g. whether or not the mouse cursor changes when attempting to select text. + Ext.getDoc().on('selectstart', function(ev, dom) { + var selectableCls = Element.selectableCls, + unselectableCls = Element.unselectableCls, + tagName = dom && dom.tagName, + el = new Ext.dom.Fly(); + tagName = tagName && tagName.toLowerCase(); + // Element.unselectable is not really intended to handle selection within text fields and it is important that + // fields inside menus or panel headers don't inherit the unselectability. In most browsers this is automatic but in + // IE 9 the selectstart event can bubble up from text fields so we have to explicitly handle that case. + if (tagName === 'input' || tagName === 'textarea') { + return; + } + // Walk up the DOM checking the nodes. This may be 'slow' but selectstart events don't fire very often + while (dom && dom.nodeType === 1 && dom !== DOC.documentElement) { + el.attach(dom); + // If the node has the class x-selectable then stop looking, the text selection is allowed + if (el.hasCls(selectableCls)) { + return; + } + // If the node has class x-unselectable then the text selection needs to be stopped + if (el.hasCls(unselectableCls)) { + ev.stopEvent(); + return; + } + dom = dom.parentNode; + } + }); + if (Ext.os.is.Android || (Ext.os.is.Windows && Ext.supports.Touch)) { + // Some mobile devices (android and windows) fire window resize events + // When the virtual keyboard is displayed. This causes unexpected visual + // results due to extra layouts of the viewport. Here we attach a couple + // of event listeners that will help us detect if the virtual keyboard + // is open so tha getViewportWidth/getViewportHeight can report the + // original size as the viewport size while the keyboard is open + var win = Ext.getWin(); + Element._documentWidth = Element._viewportWidth = docEl.clientWidth; + Element._documentHeight = Element._viewportHeight = docEl.clientHeight; + win.on({ + // Focus in/out listeners track the last focus change so we can detect + // the proximity of the last focus change relative to window resize events + // alowing us to guess with reasonable certainty that a virtual keyboard + // is being shown. + focusin: '_onWindowFocusChange', + focusout: '_onWindowFocusChange', + // This pointerup listener is needed because in windowsthe virtual keyboard + // can be hidden manually while the editable element retains focus by tapping + // a hide button on the virtual keyboard itself. The virtual keyboard can then + // be re-shown by tapping on the editable element. In this case the editable + // element does not fire a focusin event since it already has the focus, but + // we still need to track that an event occurred which will cause the virtual + // keyboard to show momentarily. + pointerup: '_onWindowFocusChange', + capture: true, + delegated: false, + delay: 1, + scope: Element + }); + win.on({ + // Resize listener for tracking virtual keyboard state. + resize: '_onWindowResize', + priority: 2000, + scope: Element + }); + } + if (supports.Touch) { + bodyCls.push(Ext.baseCSSPrefix + 'touch'); + } + if (Ext.isIE && Ext.isIE9m) { + bodyCls.push(Ext.baseCSSPrefix + 'ie', Ext.baseCSSPrefix + 'ie9m'); + // very often CSS needs to do checks like "IE7+" or "IE6 or 7". To help + // reduce the clutter (since CSS/SCSS cannot do these tests), we add some + // additional classes: + // + // x-ie7p : IE7+ : 7 <= ieVer + // x-ie7m : IE7- : ieVer <= 7 + // x-ie8p : IE8+ : 8 <= ieVer + // x-ie8m : IE8- : ieVer <= 8 + // x-ie9p : IE9+ : 9 <= ieVer + // x-ie78 : IE7 or 8 : 7 <= ieVer <= 8 + // + bodyCls.push(Ext.baseCSSPrefix + 'ie8p'); + if (Ext.isIE8) { + bodyCls.push(Ext.baseCSSPrefix + 'ie8'); + } else { + bodyCls.push(Ext.baseCSSPrefix + 'ie9', Ext.baseCSSPrefix + 'ie9p'); + } + if (Ext.isIE8m) { + bodyCls.push(Ext.baseCSSPrefix + 'ie8m'); + } + } + if (Ext.isIE10) { + bodyCls.push(Ext.baseCSSPrefix + 'ie10'); + } + if (Ext.isIE10p) { + bodyCls.push(Ext.baseCSSPrefix + 'ie10p'); + } + if (Ext.isIE11) { + bodyCls.push(Ext.baseCSSPrefix + 'ie11'); + } + if (Ext.isEdge) { + bodyCls.push(Ext.baseCSSPrefix + 'edge'); + } + if (Ext.isGecko) { + bodyCls.push(Ext.baseCSSPrefix + 'gecko'); + } + if (Ext.isOpera) { + bodyCls.push(Ext.baseCSSPrefix + 'opera'); + } + if (Ext.isOpera12m) { + bodyCls.push(Ext.baseCSSPrefix + 'opera12m'); + } + if (Ext.isWebKit) { + bodyCls.push(Ext.baseCSSPrefix + 'webkit'); + } + if (Ext.isSafari) { + bodyCls.push(Ext.baseCSSPrefix + 'safari'); + } + if (Ext.isSafari && Ext.browser.version.isLessThan(11)) { + bodyCls.push(Ext.baseCSSPrefix + 'safari10m'); + } + if (Ext.isSafari9) { + bodyCls.push(Ext.baseCSSPrefix + 'safari9'); + } + if (Ext.isSafari && Ext.browser.version.isLessThan(9)) { + bodyCls.push(Ext.baseCSSPrefix + 'safari8m'); + } + if (Ext.isChrome) { + bodyCls.push(Ext.baseCSSPrefix + 'chrome'); + } + if (Ext.isMac) { + bodyCls.push(Ext.baseCSSPrefix + 'mac'); + } + if (Ext.isWindows) { + bodyCls.push(Ext.baseCSSPrefix + 'windows'); + } + if (Ext.isLinux) { + bodyCls.push(Ext.baseCSSPrefix + 'linux'); + } + if (!supports.CSS3BorderRadius) { + bodyCls.push(Ext.baseCSSPrefix + 'nbr'); + } + if (!supports.CSS3LinearGradient) { + bodyCls.push(Ext.baseCSSPrefix + 'nlg'); + } + if (supports.Touch) { + bodyCls.push(Ext.baseCSSPrefix + 'touch'); + } + if (Ext.os.deviceType) { + bodyCls.push(Ext.baseCSSPrefix + Ext.os.deviceType.toLowerCase()); + } + if (Ext.os.is.BlackBerry) { + bodyCls.push(Ext.baseCSSPrefix + 'bb'); + if (Ext.browser.userAgent.match(/Kbd/gi)) { + // blackberry with physical keyboard + bodyCls.push(Ext.baseCSSPrefix + 'bb-keyboard'); + } + } + if (Ext.os.is.iOS && Ext.isSafari) { + bodyCls.push(Ext.baseCSSPrefix + 'mobile-safari'); + } + if (Ext.os.is.iOS && Ext.browser.is.WebView && !Ext.browser.is.Standalone) { + // ios cordova app + bodyCls.push(Ext.baseCSSPrefix + 'ios-native'); + } + Ext.getBody().addCls(bodyCls); + theme = Ext.theme; + if (theme && theme.getDocCls) { + // hook for theme overrides to add css classes to the element + Ext.fly(document.documentElement).addCls(theme.getDocCls()); + } + }, null, { + priority: 1500 + }); +}); + +/** + * Represents a filter that can be applied to a {@link Ext.util.MixedCollection MixedCollection}. Can either simply + * filter on a property/value pair or pass in a filter function with custom logic. Filters are always used in the + * context of MixedCollections, though {@link Ext.data.Store Store}s frequently create them when filtering and searching + * on their records. Example usage: + * + * // Set up a fictional MixedCollection containing a few people to filter on + * var allNames = new Ext.util.MixedCollection(); + * allNames.addAll([ + * { id: 1, name: 'Peter', age: 25 }, + * { id: 2, name: 'Egon', age: 37 }, + * { id: 3, name: 'Ray', age: 32 }, + * { id: 4, name: 'Winston',age: 26 } + * ]); + * + * var ageFilter = new Ext.util.Filter({ + * property: 'age', + * value : 32 + * }); + * + * var longNameFilter = new Ext.util.Filter({ + * filterFn: function(item) { + * return item.name.length > 4; + * } + * }); + * + * // a new MixedCollection with the 2 names longer than 4 characters + * var longNames = allNames.filter(longNameFilter); + * + * // a new MixedCollection with the 1 person of age 32: + * var youngFolk = allNames.filter(ageFilter); + */ +Ext.define('Ext.util.Filter', { + isFilter: true, + config: { + /** + * @cfg {String} [property=null] + * The property to filter on. Required unless a {@link #filterFn} is passed. + */ + property: null, + /** + * @cfg {RegExp/Mixed} [value=null] + * The value you want to match against. Required unless a {@link #filterFn} is passed. + * + * Can be a regular expression which will be used as a matcher or any other value + * such as an object or an array of objects. This value is compared using the configured + * {@link #operator}. + */ + value: null, + /** + * @cfg {Function} filterFn + * A custom filter function which is passed each item in the {@link Ext.util.MixedCollection} in turn. Should return + * `true` to accept each item or `false` to reject it. + */ + filterFn: null, + /** + * @cfg {String} [id] + * An identifier by which this Filter is indexed in a {@link Ext.data.Store#cfg-filters Store's filters collection} + * + * Identified Filters may be individually removed from a Store's filter set by using {@link Ext.data.Store#removeFilter}. + * + * Anonymous Filters may be removed en masse by passing `null` to {@link Ext.data.Store#removeFilter}. + */ + id: null, + /** + * @cfg {Boolean} anyMatch + * True to allow any match - no regex start/end line anchors will be added. + */ + anyMatch: false, + /** + * @cfg {Boolean} [exactMatch=false] + * True to force exact match (^ and $ characters added to the regex). Ignored if anyMatch is true. + */ + exactMatch: false, + /** + * @cfg {Boolean} [caseSensitive=false] + * True to make the regex case sensitive (adds 'i' switch to regex). + */ + caseSensitive: false, + /** + * @cfg {Boolean} disabled + * Setting this property to `true` disables this individual Filter so that it no longer contributes to a {@link Ext.data.Store#cfg-filters Store's filter set} + * + * When disabled, the next time the store is filtered, the Filter plays no part in filtering and records eliminated by it may rejoin the dataset. + * + */ + disabled: false, + /** + * @cfg {Boolean} disableOnEmpty + * `true` to not have this filter participate in the filtering process when the {@link #value} of + * this the filter is empty according to {@link Ext#isEmpty}. + * + * @since 5.1.0 + */ + disableOnEmpty: false, + /** + * @cfg {String} [operator] + * The operator to use to compare the {@link #cfg-property} to this Filter's {@link #cfg-value} + * + * Possible values are: + * + * * `<` + * * `<=` + * * `=` + * * `>=` + * * `>` + * * `!=` + * * `in` + * * `notin` + * * `like` + * * /= + * + * The `in` and `notin` operator expects this filter's {@link #cfg-value} to be an array and matches + * values that are present in that array. + * + * The `like` operator matches values that contain this filter's {@link #cfg-value} as a + * substring. + * + * The `'*='` operator uses the {@link #cfg-value} as the source for a `RegExp` and tests whether the + * candidate value matches the regular expression. + */ + operator: null, + /** + * @cfg {String} [root=null] + * Optional root property. This is mostly useful when filtering a Store, in which case we set the root to 'data' to + * make the filter pull the {@link #property} out of the data object of each item + */ + root: null, + /** + * @cfg {Function} [serializer] + * A function to post-process any serialization. Accepts a filter state object + * containing `property`, `value` and `operator` properties, and may either + * mutate it, or return a completely new representation. Returning a falsey + * value does not modify the representation. + * @since 6.2.0 + */ + serializer: null, + /** + * @cfg {Function} [convert] + * A function to do any conversion on the value before comparison. For example, + * something that returns the date only part of a date. + * @cfg {Object} convert.value The value to convert. + * @cfg {Object} convert.return The converted value. + * @private + */ + convert: null + }, + /** + * @cfg {Object} [scope] + * The context (`this` property) in which the filtering function is called. Defaults + * to this Filter object. + */ + scope: null, + // Needed for scope above. If `scope` were a "config" it would be merged and lose its + // identity. + $configStrict: false, + /** + * @property {Number} generation + * Mutation counter which is incremented when the filter changes in ways that mean reevaluation of + * the filtered state is necessary. + * @readonly + * @since 6.5.0 + */ + generation: 0, + statics: { + /** + * Creates a single filter function which encapsulates the passed Filter array or + * Collection. + * @param {Ext.util.Filter[]/Ext.util.Collection} filters The filters from which to + * create a filter function. + * @return {Function} A function, which when passed a candidate object returns `true` + * if the candidate passes all the specified Filters. + */ + createFilterFn: function(filters) { + if (!filters) { + return Ext.returnTrue; + } + return function(candidate) { + var items = filters.isCollection ? filters.items : filters, + length = items.length, + match = true, + i, filter; + for (i = 0; match && i < length; i++) { + filter = items[i]; + // Skip disabled filters + if (!filter.getDisabled()) { + match = filter.filter(candidate); + } + } + return match; + }; + }, + /** + * Checks if two filters have the same properties (Property, Operator and Value). + * + * @param {Ext.util.Filter} filter1 The first filter to be compared + * @param {Ext.util.Filter} filter2 The second filter to be compared + * @return {Boolean} `true` if they have the same properties. + * @since 6.2.0 + */ + isEqual: function(filter1, filter2) { + if (filter1.getProperty() !== filter2.getProperty()) { + return false; + } + if (filter1.getOperator() !== filter2.getOperator()) { + return false; + } + if (filter1.getValue() === filter2.getValue()) { + return true; + } else if (Ext.isArray(filter1) && Ext.isArray(filter2) && Ext.Array.equals(filter1, filter2)) { + return true; + } + return false; + }, + /** + * Checks whether the filter will produce a meaningful value. Since filters + * may be used in conjunction with data binding, this is a sanity check to + * check whether the resulting filter will be able to match. + * + * @param {Object} cfg The filter config object + * @return {Boolean} `true` if the filter will produce a valid value + * + * @private + */ + isInvalid: function(cfg) { + if (!cfg.filterFn) { + // If we don't have a filterFn, we must have a property + if (!cfg.property) { + return 'A Filter requires either a property or a filterFn to be set'; + } + if (!cfg.hasOwnProperty('value') && !cfg.operator) { + return 'A Filter requires either a property and value, or a filterFn to be set'; + } + } + return false; + } + }, + /** + * Creates new Filter. + * @param {Object} config Config object + */ + constructor: function(config) { + var warn = Ext.util.Filter.isInvalid(config); + if (warn) { + Ext.log.warn(warn); + } + this.initConfig(config); + }, + preventConvert: { + 'in': 1, + notin: 1 + }, + filter: function(item) { + var me = this, + filterFn = me._filterFn || me.getFilterFn(), + convert = me.getConvert(), + value = me._value; + me._filterValue = value; + me.isDateValue = Ext.isDate(value); + if (me.isDateValue) { + me.dateValue = value.getTime(); + } + if (convert && !me.preventConvert[me.getOperator()]) { + me._filterValue = convert.call(me.scope || me, value); + } + return filterFn.call(me.scope || me, item); + }, + getId: function() { + var id = this._id; + if (!id) { + id = this.getProperty(); + if (!id) { + id = Ext.id(null, 'ext-filter-'); + } + this._id = id; + } + return id; + }, + getFilterFn: function() { + var me = this, + filterFn = me._filterFn, + operator; + if (!filterFn) { + operator = me.getOperator(); + if (operator) { + filterFn = me.operatorFns[operator]; + } else { + // This part is broken our into its own method so the function expression + // contained there does not get hoisted and created on each call this + // method. + filterFn = me.createRegexFilter(); + } + me._filterFn = filterFn; + // Mark as generated by default. This becomes important when proxies encode + // filters. See proxy.Server#encodeFilters(). + me.generatedFilterFn = true; + } + return filterFn; + }, + /** + * @private + * Creates a filter function for the configured value/anyMatch/caseSensitive options + * for this Filter. + */ + createRegexFilter: function() { + var me = this, + anyMatch = !!me.getAnyMatch(), + exact = !!me.getExactMatch(), + value = me.getValue(), + matcher = Ext.String.createRegex(value, !anyMatch, // startsWith + !anyMatch && exact, // endsWith + !me.getCaseSensitive()); + return function(item) { + var val = me.getPropertyValue(item); + return matcher ? matcher.test(val) : (val == null); + }; + }, + /** + * Returns the property of interest from the given item, based on the configured `root` + * and `property` configs. + * @param {Object} item The item. + * @return {Object} The property of the object. + * @private + */ + getPropertyValue: function(item) { + var root = this._root, + value = (root == null) ? item : item[root]; + return value[this._property]; + }, + /** + * Returns this filter's state. + * @return {Object} + */ + getState: function() { + var config = this.getInitialConfig(), + result = {}, + name; + for (name in config) { + // We only want the instance properties in this case, not inherited ones, + // so we need hasOwnProperty to filter out our class values. + if (config.hasOwnProperty(name)) { + result[name] = config[name]; + } + } + delete result.root; + result.value = this.getValue(); + return result; + }, + getScope: function() { + return this.scope; + }, + /** + * Returns this filter's serialized state. This is used when transmitting this filter + * to a server. + * @return {Object} + */ + serialize: function() { + var result = this.getState(), + serializer = this.getSerializer(), + serialized; + delete result.id; + delete result.serializer; + if (serializer) { + serialized = serializer.call(this, result); + if (serialized) { + result = serialized; + } + } + return result; + }, + updateDisabled: function() { + // Developers may use this to see if a filter has changed in ways that must cause a reevaluation of filtering + this.generation++; + }, + updateOperator: function() { + // Need to clear any generated local filter fn and increment generation + this.onConfigMutation(); + }, + updateConvert: function() { + // Need to clear any generated local filter fn and increment generation + this.onConfigMutation(); + }, + updateProperty: function() { + // Need to clear any generated local filter fn and increment generation + this.onConfigMutation(); + }, + updateAnyMatch: function() { + // Need to clear any generated local filter fn and increment generation + this.onConfigMutation(); + }, + updateExactMatch: function() { + // Need to clear any generated local filter fn and increment generation + this.onConfigMutation(); + }, + updateCaseSensitive: function() { + // Need to clear any generated local filter fn and increment generation + this.onConfigMutation(); + }, + updateValue: function(value) { + // Need to clear any generated local filter fn and increment generation + this.onConfigMutation(); + if (this.getDisableOnEmpty()) { + this.setDisabled(Ext.isEmpty(value)); + } + }, + updateFilterFn: function(filterFn) { + delete this.generatedFilterFn; + }, + onConfigMutation: function() { + // Developers may use this to see if a filter has changed in ways that must cause a reevaluation of filtering + this.generation++; + if (this.generatedFilterFn) { + this._filterFn = null; + } + }, + updateDisableOnEmpty: function(disableOnEmpty) { + // Only poke disabled if true because otherwise we'll smash the disabled + // config that may also be getting set. + if (disableOnEmpty) { + this.setDisabled(Ext.isEmpty(this.getValue())); + } + }, + privates: { + getCandidateValue: function(candidate, v, preventCoerce) { + var me = this, + convert = me._convert, + result = me.getPropertyValue(candidate); + if (convert) { + result = convert.call(me.scope || me, result); + } else if (!preventCoerce) { + result = Ext.coerce(result, v); + } + return result; + } + } +}, function() { + var prototype = this.prototype, + operatorFns = (prototype.operatorFns = { + "<": function(candidate) { + var v = this._filterValue; + return this.getCandidateValue(candidate, v) < v; + }, + "<=": function(candidate) { + var v = this._filterValue; + return this.getCandidateValue(candidate, v) <= v; + }, + "=": function(candidate) { + var me = this, + v = me._filterValue; + candidate = me.getCandidateValue(candidate, v); + if (me.isDateValue && candidate instanceof Date) { + candidate = candidate.getTime(); + v = me.dateValue; + } + return candidate == v; + }, + "===": function(candidate) { + var me = this, + v = me._filterValue; + candidate = me.getCandidateValue(candidate, v, true); + if (me.isDateValue && candidate instanceof Date) { + candidate = candidate.getTime(); + v = me.dateValue; + } + return candidate === v; + }, + ">=": function(candidate) { + var v = this._filterValue; + return this.getCandidateValue(candidate, v) >= v; + }, + ">": function(candidate) { + var v = this._filterValue; + return this.getCandidateValue(candidate, v) > v; + }, + "!=": function(candidate) { + var me = this, + v = me._filterValue; + candidate = me.getCandidateValue(candidate, v); + if (me.isDateValue && candidate instanceof Date) { + candidate = candidate.getTime(); + v = me.dateValue; + } + return candidate != v; + }, + "!==": function(candidate) { + var me = this, + v = me._filterValue; + candidate = me.getCandidateValue(candidate, v, true); + if (me.isDateValue && candidate instanceof Date) { + candidate = candidate.getTime(); + v = me.dateValue; + } + return candidate !== v; + }, + "in": function(candidate) { + var v = this._filterValue; + return Ext.Array.contains(v, this.getCandidateValue(candidate, v)); + }, + notin: function(candidate) { + var v = this._filterValue; + return !Ext.Array.contains(v, this.getCandidateValue(candidate, v)); + }, + like: function(candidate) { + var v = this._filterValue; + return v && this.getCandidateValue(candidate, v).toLowerCase().indexOf(v.toLowerCase()) > -1; + }, + "/=": function(candidate) { + var me = this, + v = me._filterValue; + candidate = me.getCandidateValue(candidate, v); + // Only compile a RegExp when the source string changes + if (v !== me.lastRegExpSource) { + me.lastRegExpSource = v; + try { + me.regex = new RegExp(v, 'i'); + } catch (e) { + me.regex = null; + } + } + return me.regex ? me.regex.test(candidate) : false; + } + }); + // Operator type '==' is the same as operator type '=' + operatorFns['=='] = operatorFns['=']; + operatorFns.gt = operatorFns['>']; + operatorFns.ge = operatorFns['>=']; + operatorFns.lt = operatorFns['<']; + operatorFns.le = operatorFns['<=']; + operatorFns.eq = operatorFns['=']; + operatorFns.ne = operatorFns['!=']; +}); + +/** + * A Ext.mixin.Observable subclass that is provided for backward compatibility. + * Applications should avoid using this class, and use Ext.mixin.Observable instead. + */ +Ext.define('Ext.util.Observable', { + extend: 'Ext.mixin.Observable', + // The constructor of Ext.util.Observable instances processes the config object by + // calling Ext.apply(this, config); instead of this.initConfig(config); + $applyConfigs: true +}, function(Observable) { + var Super = Ext.mixin.Observable; + /** + * @method releaseCapture + * @static + * @inheritdoc Ext.mixin.Observable#releaseCapture + */ + Observable.releaseCapture = Super.releaseCapture; + /** + * @method capture + * @static + * @inheritdoc Ext.mixin.Observable#capture + */ + Observable.capture = Super.capture; + /** + * @member Ext.util.Observable + * @private + */ + Observable.captureArgs = Super.captureArgs; + /** + * @method observe + * @static + * @inheritdoc Ext.mixin.Observable#observe + */ + Observable.observe = Observable.observeClass = Super.observe; +}); + +/** + * @class Ext.util.AbstractMixedCollection + * @private + */ +Ext.define('Ext.util.AbstractMixedCollection', { + requires: [ + 'Ext.util.Filter' + ], + mixins: { + observable: 'Ext.util.Observable' + }, + /** + * @property {Boolean} isMixedCollection + * `true` in this class to identify an object as an instantiated MixedCollection, or subclass thereof. + */ + isMixedCollection: true, + /** + * Mutation counter which is incremented upon add and remove. + * + * @private + */ + generation: 0, + /** + * Mutation counter for the index map which is synchronized with the collection's mutation counter + * when the index map is interrogated and found to be out of sync and needed a rebuild. + * + * @private + */ + indexGeneration: 0, + constructor: function(allowFunctions, keyFn) { + var me = this; + // Modern constructor signature using a config object + if (arguments.length === 1 && Ext.isObject(allowFunctions)) { + me.initialConfig = allowFunctions; + Ext.apply(me, allowFunctions); + } else // Old constructor signature + { + me.allowFunctions = allowFunctions === true; + if (keyFn) { + me.getKey = keyFn; + } + me.initialConfig = { + allowFunctions: me.allowFunctions, + getKey: me.getKey + }; + } + me.items = []; + me.map = {}; + me.keys = []; + me.indexMap = {}; + me.length = 0; + /** + * @event clear + * Fires when the collection is cleared. + * @since 1.1.0 + */ + /** + * @event add + * Fires when an item is added to the collection. + * @param {Number} index The index at which the item was added. + * @param {Object} o The item added. + * @param {String} key The key associated with the added item. + * @since 1.1.0 + */ + /** + * @event replace + * Fires when an item is replaced in the collection. + * @param {String} key he key associated with the new added. + * @param {Object} old The item being replaced. + * @param {Object} new The new item. + * @since 1.1.0 + */ + /** + * @event remove + * Fires when an item is removed from the collection. + * @param {Object} o The item being removed. + * @param {String} key The key associated with the removed item. + * @since 1.1.0 + */ + me.mixins.observable.constructor.call(me); + }, + destroy: function() { + var me = this; + me.items = me.map = me.keys = me.indexMap = null; + me.callParent(); + }, + /** + * @cfg {Boolean} allowFunctions Specify true if the {@link #addAll} + * function should add function references to the collection. Defaults to + * false. + * @since 3.4.0 + */ + allowFunctions: false, + /** + * Adds an item to the collection. Fires the {@link #event-add} event when complete. + * + * @param {String/Object} key The key to associate with the item, or the new item. + * + * If a {@link #getKey} implementation was specified for this MixedCollection, + * or if the key of the stored items is in a property called `id`, + * the MixedCollection will be able to *derive* the key for the new item. + * In this case just pass the new item in this parameter. + * + * @param {Object} [obj] The item to add. + * + * Note that when adding a value that is iterable, it must be wrapped in brackets, i.e.: + * + * c.add([[1, 2]]); + * + * This will be needed for any value that is iterable, i.e., an array, arguments object, + * HTML collections, etc. + * + * @return {Object} The item added. + * @since 1.1.0 + */ + add: function(key, obj) { + var len = this.length, + out; + if (arguments.length === 1) { + out = this.insert(len, key); + } else { + out = this.insert(len, key, obj); + } + return out; + }, + /** + * A function which will be called, passing a newly added object + * when the object is added without a separate id. The function + * should yield the key by which that object will be indexed. + * + * If no key is yielded, then the object will be added, but it + * cannot be accessed or removed quickly. Finding it in this + * collection for interrogation or removal will require a linear + * scan of this collection's items. + * + * The default implementation simply returns `item.id` but you can + * provide your own implementation to return a different value as + * in the following examples: + * + * // normal way + * var mc = new Ext.util.MixedCollection(); + * mc.add(someEl.dom.id, someEl); + * mc.add(otherEl.dom.id, otherEl); + * //and so on + * + * // using getKey + * var mc = new Ext.util.MixedCollection({ + * getKey: function(el){ + * return el.dom.id; + * } + * }); + * mc.add(someEl); + * mc.add(otherEl); + * + * @param {Object} item The item for which to find the key. + * @return {Object} The key for the passed item. + * @since 1.1.0 + * @template + */ + getKey: function(item) { + return item.id; + }, + /** + * Replaces an item in the collection. Fires the {@link #event-replace} event when complete. + * @param {String} key The key associated with the item to replace, or the replacement item. + * + * If you supplied a {@link #getKey} implementation for this MixedCollection, or if the key + * of your stored items is in a property called *`id`*, then the MixedCollection + * will be able to derive the key of the replacement item. If you want to replace an item + * with one having the same key value, then just pass the replacement item in this parameter. + * + * @param o {Object} o (optional) If the first parameter passed was a key, the item to associate + * with that key. + * @return {Object} The new item. + * @since 1.1.0 + */ + replace: function(key, o) { + var me = this, + old, index; + if (arguments.length == 1) { + o = arguments[0]; + key = me.getKey(o); + } + old = me.map[key]; + if (typeof key == 'undefined' || key === null || typeof old == 'undefined') { + return me.add(key, o); + } + me.generation++; + index = me.indexOfKey(key); + me.items[index] = o; + me.map[key] = o; + if (me.hasListeners.replace) { + me.fireEvent('replace', key, old, o); + } + return o; + }, + /** + * Reorders each of the items based on a mapping from old index to new index. Internally this + * just translates into a sort. The 'sort' event is fired whenever reordering has + * occurred. + * @param {Object} mapping Mapping from old item index to new item index + * + * // example of moving the last of 4 items to the front of the collection + * // and moving each one before it forward one + * collection.reorder({ + * 0: 1, + * 1: 2, + * 2: 3, + * 3: 0, + * }); + */ + reorder: function(mapping) { + var me = this, + items = me.items, + index = 0, + length = items.length, + order = [], + remaining = [], + oldIndex; + me.suspendEvents(); + //object of {oldPosition: newPosition} reversed to {newPosition: oldPosition} + for (oldIndex in mapping) { + order[mapping[oldIndex]] = items[oldIndex]; + } + for (index = 0; index < length; index++) { + if (mapping[index] == undefined) { + remaining.push(items[index]); + } + } + for (index = 0; index < length; index++) { + if (order[index] == undefined) { + order[index] = remaining.shift(); + } + } + me.clear(); + me.addAll(order); + me.resumeEvents(); + }, + /** + * Change the key for an existing item in the collection. If the old key + * does not exist this is a no-op. + * @param {Object} oldKey The old key + * @param {Object} newKey The new key + */ + updateKey: function(oldKey, newKey) { + var me = this, + map = me.map, + index = me.indexOfKey(oldKey), + // Important: Take reference to indexMap AFTER indexOf call which may rebuild it. + indexMap = me.indexMap, + item; + if (index > -1) { + item = map[oldKey]; + delete map[oldKey]; + delete indexMap[oldKey]; + map[newKey] = item; + indexMap[newKey] = index; + me.keys[index] = newKey; + // indexGeneration will be in sync since we called indexOfKey + // And we kept it all in sync, so now generation changes we keep the indexGeneration matched + me.indexGeneration = ++me.generation; + } + }, + /** + * Adds all elements of an Array or an Object to the collection. + * @param {Object/Array} objs An Object containing properties which will be added + * to the collection, or an Array of values, each of which are added to the collection. + * Functions references will be added to the collection if `{@link #allowFunctions}` + * has been set to `true`. + * @since 1.1.0 + */ + addAll: function(objs) { + var me = this, + key; + if (arguments.length > 1 || Ext.isArray(objs)) { + me.insert(me.length, arguments.length > 1 ? arguments : objs); + } else { + for (key in objs) { + if (objs.hasOwnProperty(key)) { + if (me.allowFunctions || typeof objs[key] != 'function') { + me.add(key, objs[key]); + } + } + } + } + }, + /** + * Executes the specified function once for every item in the collection. + * The function should return a boolean value. + * Returning false from the function will stop the iteration. + * + * @param {Function} fn The function to execute for each item. + * @param {Mixed} fn.item The collection item. + * @param {Number} fn.index The index of item. + * @param {Number} fn.len Total length of collection. + * @param {Object} scope (optional) The scope (this reference) + * in which the function is executed. Defaults to the current item in the iteration. + * + * @since 1.1.0 + */ + each: function(fn, scope) { + var items = Ext.Array.push([], this.items), + // each safe for removal + i = 0, + len = items.length, + item; + for (; i < len; i++) { + item = items[i]; + if (fn.call(scope || item, item, i, len) === false) { + break; + } + } + }, + /** + * Executes the specified function once for every key in the collection, passing each + * key, and its associated item as the first two parameters. + * @param {Function} fn The function to execute for each item. + * @param {String} fn.key The key of collection item. + * @param {Mixed} fn.item The collection item. + * @param {Number} fn.index The index of item. + * @param {Number} fn.len Total length of collection. + * @param {Object} scope (optional) The scope (this reference) in which the + * function is executed. Defaults to the browser window. + * + * @since 1.1.0 + */ + eachKey: function(fn, scope) { + var keys = this.keys, + items = this.items, + i = 0, + len = keys.length; + for (; i < len; i++) { + fn.call(scope || window, keys[i], items[i], i, len); + } + }, + /** + * Returns the first item in the collection which elicits a true return value from the + * passed selection function. + * @param {Function} fn The selection function to execute for each item. + * @param {Mixed} fn.item The collection item. + * @param {String} fn.key The key of collection item. + * @param {Object} scope (optional) The scope (this reference) in which the + * function is executed. Defaults to the browser window. + * @return {Object} The first item in the collection which returned true from the selection + * function, or null if none was found. + */ + findBy: function(fn, scope) { + var keys = this.keys, + items = this.items, + i = 0, + len = items.length; + for (; i < len; i++) { + if (fn.call(scope || window, items[i], keys[i])) { + return items[i]; + } + } + return null; + }, + /** + * Returns the first item in the collection which elicits a true return value from the passed selection function. + * @deprecated 4.0 Use {@link #findBy} instead. + * @since 1.1.0 + */ + find: function() { + if (Ext.isDefined(Ext.global.console)) { + Ext.global.console.warn('Ext.util.MixedCollection: find has been deprecated. Use findBy instead.'); + } + return this.findBy.apply(this, arguments); + }, + /** + * Inserts an item at the specified index in the collection. Fires the {@link #event-add} event when complete. + * @param {Number} index The index to insert the item at. + * @param {String/Object/String[]/Object[]} key The key to associate with the new item, or the item itself. + * May also be an array of either to insert multiple items at once. + * @param {Object/Object[]} obj (optional) If the second parameter was a key, the new item. + * May also be an array to insert multiple items at once. + * @return {Object} The item inserted or an array of items inserted. + * @since 1.1.0 + */ + insert: function(index, key, obj) { + var out; + if (Ext.isIterable(key)) { + out = this.doInsert(index, key, obj); + } else { + if (arguments.length > 2) { + out = this.doInsert(index, [ + key + ], [ + obj + ]); + } else { + out = this.doInsert(index, [ + key + ]); + } + out = out[0]; + } + return out; + }, + // Private multi insert implementation. + doInsert: function(index, keys, objects) { + var me = this, + itemKey, removeIndex, i, + len = keys.length, + deDupedLen = len, + fireAdd = me.hasListeners.add, + syncIndices, + newKeys = {}, + passedDuplicates, oldKeys, oldObjects; + // External key(s) passed. We cannot reliably find an object's index using the key extraction fn. + // Set a flag for use by contains, indexOf and remove + if (objects != null) { + me.useLinearSearch = true; + } else // No external keys: calculate keys array if not passed + { + objects = keys; + keys = new Array(len); + for (i = 0; i < len; i++) { + keys[i] = this.getKey(objects[i]); + } + } + // First, remove duplicates of the keys. If a removal point is less than insertion index, decr insertion index. + me.suspendEvents(); + for (i = 0; i < len; i++) { + itemKey = keys[i]; + // Must use indexOf - map might be out of sync + removeIndex = me.indexOfKey(itemKey); + if (removeIndex !== -1) { + if (removeIndex < index) { + index--; + } + me.removeAt(removeIndex); + } + if (itemKey != null) { + // If a previous new item used this key, we will have to rebuild the input arrays from the newKeys map. + if (newKeys[itemKey] != null) { + passedDuplicates = true; + deDupedLen--; + } + newKeys[itemKey] = i; + } + } + me.resumeEvents(); + // Duplicate keys were detected - rebuild the objects and keys arrays from the last values associated with each unique key + if (passedDuplicates) { + oldKeys = keys; + oldObjects = objects; + keys = new Array(deDupedLen); + objects = new Array(deDupedLen); + i = 0; + // Loop through unique key hash, properties of which point to last encountered index for that key. + // Rebuild deduped objects and keys arrays. + for (itemKey in newKeys) { + keys[i] = oldKeys[newKeys[itemKey]]; + objects[i] = oldObjects[newKeys[itemKey]]; + i++; + } + len = deDupedLen; + } + // If we are appending and the indices are in sync, its cheap to kep them that way + syncIndices = index === me.length && me.indexGeneration === me.generation; + // Insert the new items and new keys in at the insertion point + Ext.Array.insert(me.items, index, objects); + Ext.Array.insert(me.keys, index, keys); + me.length += len; + me.generation++; + if (syncIndices) { + me.indexGeneration = me.generation; + } + for (i = 0; i < len; i++ , index++) { + itemKey = keys[i]; + if (itemKey != null) { + me.map[itemKey] = objects[i]; + // If the index is still in sync, keep it that way + if (syncIndices) { + me.indexMap[itemKey] = index; + } + } + if (fireAdd) { + me.fireEvent('add', index, objects[i], itemKey); + } + } + return objects; + }, + /** + * Remove an item from the collection. + * @param {Object} o The item to remove. + * @return {Object} The item removed or false if no item was removed. + * @since 1.1.0 + */ + remove: function(o) { + var me = this, + removeKey, index; + // If + // We have not been forced into using linear lookup by a usage of the 2 arg form of add + // and + // The key extraction function yields a key + // Then use indexOfKey. This will use the indexMap - rebuilding it if necessary. + if (!me.useLinearSearch && (removeKey = me.getKey(o))) { + index = me.indexOfKey(removeKey); + } else // Otherwise we have to do it the slow way with a linear search. + { + index = Ext.Array.indexOf(me.items, o); + } + return (index === -1) ? false : me.removeAt(index); + }, + /** + * Remove all items in the collection. Can also be used + * to remove only the items in the passed array. + * @param {Array} [items] An array of items to be removed. + * @return {Ext.util.MixedCollection} this object + */ + removeAll: function(items) { + var me = this, + i; + if (items || me.hasListeners.remove) { + // Only perform expensive item-by-item removal if there's a listener or specific items + if (items) { + for (i = items.length - 1; i >= 0; --i) { + me.remove(items[i]); + } + } else { + while (me.length) { + me.removeAt(0); + } + } + } else { + me.length = me.items.length = me.keys.length = 0; + me.map = {}; + me.indexMap = {}; + me.generation++; + me.indexGeneration = me.generation; + } + }, + /** + * Remove an item from a specified index in the collection. Fires the {@link #event-remove} event when complete. + * @param {Number} index The index within the collection of the item to remove. + * @return {Object} The item removed or false if no item was removed. + * @since 1.1.0 + */ + removeAt: function(index) { + var me = this, + o, key; + if (index < me.length && index >= 0) { + me.length--; + o = me.items[index]; + Ext.Array.erase(me.items, index, 1); + key = me.keys[index]; + if (typeof key != 'undefined') { + delete me.map[key]; + } + Ext.Array.erase(me.keys, index, 1); + if (me.hasListeners.remove) { + me.fireEvent('remove', o, key); + } + me.generation++; + return o; + } + return false; + }, + /** + * Remove a range of items starting at a specified index in the collection. + * Does not fire the remove event. + * @param {Number} index The index within the collection of the item to remove. + * @param {Number} [removeCount=1] The nuber of items to remove beginning at the specified index. + * @return {Object} The last item removed or false if no item was removed. + */ + removeRange: function(index, removeCount) { + var me = this, + o, key, i, limit, syncIndices, trimming; + if (index < me.length && index >= 0) { + if (!removeCount) { + removeCount = 1; + } + limit = Math.min(index + removeCount, me.length); + removeCount = limit - index; + // If we are removing from end and the indices are in sync, its cheap to kep them that way + trimming = limit === me.length; + syncIndices = trimming && me.indexGeneration === me.generation; + // Loop through the to remove indices deleting from the key hashes + for (i = index; i < limit; i++) { + key = me.keys[i]; + if (key != null) { + delete me.map[key]; + if (syncIndices) { + delete me.indexMap[key]; + } + } + } + // Last item encountered + o = me.items[i - 1]; + me.length -= removeCount; + me.generation++; + if (syncIndices) { + me.indexGeneration = me.generation; + } + // Chop items and keys arrays. + // If trimming the trailing end, we can just truncate the array. + // We can use splice directly. The IE8 bug which Ext.Array works around only affects *insertion* + // http://social.msdn.microsoft.com/Forums/en-US/iewebdevelopment/thread/6e946d03-e09f-4b22-a4dd-cd5e276bf05a/ + if (trimming) { + me.items.length = me.keys.length = me.length; + } else { + me.items.splice(index, removeCount); + me.keys.splice(index, removeCount); + } + // Return last object removed + return o; + } + return false; + }, + /** + * Removes an item associated with the passed key fom the collection. + * @param {String} key The key of the item to remove. If `null` is passed, + * all objects which yielded no key from the configured {@link #getKey} function are removed. + * @return {Object} Only returned if removing at a specified key. The item removed or false if no item was removed. + */ + removeAtKey: function(key) { + var me = this, + keys = me.keys, + i; + // Remove objects which yielded no key from our configured getKey function + if (key == null) { + for (i = keys.length - 1; i >= 0; i--) { + if (keys[i] == null) { + me.removeAt(i); + } + } + } else // Remove object at the passed key + { + return me.removeAt(me.indexOfKey(key)); + } + }, + /** + * Returns the number of items in the collection. + * @return {Number} the number of items in the collection. + * @since 1.1.0 + */ + getCount: function() { + return this.length; + }, + /** + * Returns index within the collection of the passed Object. + * @param {Object} o The item to find the index of. + * @return {Number} index of the item. Returns -1 if not found. + * @since 1.1.0 + */ + indexOf: function(o) { + var me = this, + key; + if (o != null) { + // If + // We have not been forced into using linear lookup by a usage of the 2 arg form of add + // and + // The key extraction function yields a key + // Then use indexOfKey. This will use the indexMap - rebuilding it if necessary. + if (!me.useLinearSearch && (key = me.getKey(o))) { + return this.indexOfKey(key); + } + // Fallback: Use linear search + return Ext.Array.indexOf(me.items, o); + } + // No object passed + return -1; + }, + /** + * Returns index within the collection of the passed key. + * @param {String} key The key to find the index of. + * @return {Number} index of the key. + * @since 1.1.0 + */ + indexOfKey: function(key) { + if (!this.map.hasOwnProperty(key)) { + return -1; + } + if (this.indexGeneration !== this.generation) { + this.rebuildIndexMap(); + } + return this.indexMap[key]; + }, + rebuildIndexMap: function() { + var me = this, + indexMap = me.indexMap = {}, + keys = me.keys, + len = keys.length, + i; + for (i = 0; i < len; i++) { + indexMap[keys[i]] = i; + } + me.indexGeneration = me.generation; + }, + /** + * Returns the item associated with the passed key OR index. + * Key has priority over index. This is the equivalent + * of calling {@link #getByKey} first, then if nothing matched calling {@link #getAt}. + * @param {String/Number} key The key or index of the item. + * @return {Object} If the item is found, returns the item. If the item was not found, returns undefined. + * If an item was found, but is a Class, returns null. + * @since 1.1.0 + */ + get: function(key) { + var me = this, + mk = me.map[key], + item = mk !== undefined ? mk : (typeof key == 'number') ? me.items[key] : undefined; + return typeof item != 'function' || me.allowFunctions ? item : null; + }, + // for prototype! + /** + * Returns the item at the specified index. + * @param {Number} index The index of the item. + * @return {Object} The item at the specified index. + */ + getAt: function(index) { + return this.items[index]; + }, + /** + * Returns the item associated with the passed key. + * @param {String/Number} key The key of the item. + * @return {Object} The item associated with the passed key. + */ + getByKey: function(key) { + return this.map[key]; + }, + /** + * Returns true if the collection contains the passed Object as an item. + * @param {Object} o The Object to look for in the collection. + * @return {Boolean} True if the collection contains the Object as an item. + * @since 1.1.0 + */ + contains: function(o) { + var me = this, + key; + if (o != null) { + // If + // We have not been forced into using linear lookup by a usage of the 2 arg form of add + // and + // The key extraction function yields a key + // Then use the map to determine object presence. + if (!me.useLinearSearch && (key = me.getKey(o))) { + return this.map[key] != null; + } + // Fallback: Use linear search + return Ext.Array.indexOf(this.items, o) !== -1; + } + return false; + }, + /** + * Returns true if the collection contains the passed Object as a key. + * @param {String} key The key to look for in the collection. + * @return {Boolean} True if the collection contains the Object as a key. + * @since 1.1.0 + */ + containsKey: function(key) { + return this.map.hasOwnProperty(key); + }, + /** + * Removes all items from the collection. Fires the {@link #event-clear} event when complete. + * @since 1.1.0 + */ + clear: function() { + var me = this; + // Only clear if it has ever had any content + if (me.generation) { + me.length = 0; + me.items = []; + me.keys = []; + me.map = {}; + me.indexMap = {}; + me.generation++; + me.indexGeneration = me.generation; + } + if (me.hasListeners.clear) { + me.fireEvent('clear'); + } + }, + /** + * Returns the first item in the collection. + * @return {Object} the first item in the collection.. + * @since 1.1.0 + */ + first: function() { + return this.items[0]; + }, + /** + * Returns the last item in the collection. + * @return {Object} the last item in the collection.. + * @since 1.1.0 + */ + last: function() { + return this.items[this.length - 1]; + }, + /** + * Collects all of the values of the given property and returns their sum + * @param {String} property The property to sum by + * @param {String} [root] 'root' property to extract the first argument from. This is used mainly when + * summing fields in records, where the fields are all stored inside the 'data' object + * @param {Number} [start=0] The record index to start at + * @param {Number} [end=-1] The record index to end at + * @return {Number} The total + */ + sum: function(property, root, start, end) { + var values = this.extractValues(property, root), + length = values.length, + sum = 0, + i; + start = start || 0; + end = (end || end === 0) ? end : length - 1; + for (i = start; i <= end; i++) { + sum += values[i]; + } + return sum; + }, + /** + * Collects unique values of a particular property in this MixedCollection + * @param {String} property The property to collect on + * @param {String} root (optional) 'root' property to extract the first argument from. This is used mainly when + * summing fields in records, where the fields are all stored inside the 'data' object + * @param {Boolean} allowNull (optional) Pass true to allow null, undefined or empty string values + * @return {Array} The unique values + */ + collect: function(property, root, allowNull) { + var values = this.extractValues(property, root), + length = values.length, + hits = {}, + unique = [], + value, strValue, i; + for (i = 0; i < length; i++) { + value = values[i]; + strValue = String(value); + if ((allowNull || !Ext.isEmpty(value)) && !hits[strValue]) { + hits[strValue] = true; + unique.push(value); + } + } + return unique; + }, + /** + * @private + * Extracts all of the given property values from the items in the MC. Mainly used as a supporting method for + * functions like sum and collect. + * @param {String} property The property to extract + * @param {String} root (optional) 'root' property to extract the first argument from. This is used mainly when + * extracting field data from Model instances, where the fields are stored inside the 'data' object + * @return {Array} The extracted values + */ + extractValues: function(property, root) { + var values = this.items; + if (root) { + values = Ext.Array.pluck(values, root); + } + return Ext.Array.pluck(values, property); + }, + /** + * @private + * For API parity with Store's PageMap class. Buffered rendering checks if the Store has the range + * required to render. The Store delegates this question to its backing data object which may be an instance + * of its private PageMap class, or a MixedCollection. + */ + hasRange: function(start, end) { + return (end < this.length); + }, + /** + * Returns a range of items in this collection + * @param {Number} start (optional) The starting index. Defaults to 0. + * @param {Number} end (optional) The ending index. Defaults to the last item. + * @return {Array} An array of items + * @since 1.1.0 + */ + getRange: function(start, end) { + var me = this, + items = me.items, + range = [], + len = items.length, + tmp, reverse; + if (len < 1) { + return range; + } + if (start > end) { + reverse = true; + tmp = start; + start = end; + end = tmp; + } + if (start < 0) { + start = 0; + } + if (end == null || end >= len) { + end = len - 1; + } + range = items.slice(start, end + 1); + if (reverse && range.length) { + range.reverse(); + } + return range; + }, + /** + *

Filters the objects in this collection by a set of {@link Ext.util.Filter Filter}s, or by a single + * property/value pair with optional parameters for substring matching and case sensitivity. See + * {@link Ext.util.Filter Filter} for an example of using Filter objects (preferred). Alternatively, + * MixedCollection can be easily filtered by property like this:

+ * + * //create a simple store with a few people defined + * var people = new Ext.util.MixedCollection(); + * people.addAll([ + * {id: 1, age: 25, name: 'Ed'}, + * {id: 2, age: 24, name: 'Tommy'}, + * {id: 3, age: 24, name: 'Arne'}, + * {id: 4, age: 26, name: 'Aaron'} + * ]); + * + * //a new MixedCollection containing only the items where age == 24 + * var middleAged = people.filter('age', 24); + * + * @param {Ext.util.Filter[]/String} property A property on your objects, or an array of {@link Ext.util.Filter Filter} objects + * @param {String/RegExp} value Either string that the property values + * should start with or a RegExp to test against the property + * @param {Boolean} [anyMatch=false] True to match any part of the string, not just the beginning + * @param {Boolean} [caseSensitive=false] True for case sensitive comparison. + * @return {Ext.util.MixedCollection} The new filtered collection + * @since 1.1.0 + */ + filter: function(property, value, anyMatch, caseSensitive) { + var filters = []; + //support for the simple case of filtering by property/value + if (Ext.isString(property)) { + filters.push(new Ext.util.Filter({ + property: property, + value: value, + anyMatch: anyMatch, + caseSensitive: caseSensitive + })); + } else if (Ext.isArray(property) || property instanceof Ext.util.Filter) { + filters = filters.concat(property); + } + // At this point we have an array of zero or more Ext.util.Filter objects to filter with, + // so here we construct a function that combines these filters by ANDing them together + // and filter by that. + return this.filterBy(Ext.util.Filter.createFilterFn(filters)); + }, + /** + * Filter by a function. Returns a new collection that has been filtered. + * The passed function will be called with each object in the collection. + * If the function returns true, the value is included otherwise it is filtered. + * @param {Function} fn The function to be called. + * @param {Mixed} fn.item The collection item. + * @param {String} fn.key The key of collection item. + * @param {Object} scope (optional) The scope (this reference) in + * which the function is executed. Defaults to this MixedCollection. + * @return {Ext.util.MixedCollection} The new filtered collection + * @since 1.1.0 + */ + filterBy: function(fn, scope) { + var me = this, + newMC = new me.self(me.initialConfig), + keys = me.keys, + items = me.items, + length = items.length, + i; + newMC.getKey = me.getKey; + for (i = 0; i < length; i++) { + if (fn.call(scope || me, items[i], keys[i])) { + newMC.add(keys[i], items[i]); + } + } + // The add using an external key will make the newMC think that keys cannot be reliably extracted + // from objects, so that an indexOf call will always have to do a linear search. + // If the flag is not set in this object, we know that the clone will not need it either. + newMC.useLinearSearch = me.useLinearSearch; + return newMC; + }, + /** + * Finds the index of the first matching object in this collection by a specific property/value. + * @param {String} property The name of a property on your objects. + * @param {String/RegExp} value A string that the property values + * should start with or a RegExp to test against the property. + * @param {Number} [start=0] The index to start searching at. + * @param {Boolean} [anyMatch=false] True to match any part of the string, not just the beginning. + * @param {Boolean} [caseSensitive=false] True for case sensitive comparison. + * @return {Number} The matched index or -1 + * @since 2.3.0 + */ + findIndex: function(property, value, start, anyMatch, caseSensitive) { + if (Ext.isEmpty(value, false)) { + return -1; + } + value = this.createValueMatcher(value, anyMatch, caseSensitive); + return this.findIndexBy(function(o) { + return o && value.test(o[property]); + }, null, start); + }, + /** + * Find the index of the first matching object in this collection by a function. + * If the function returns true it is considered a match. + * @param {Function} fn The function to be called. + * @param {Mixed} fn.item The collection item. + * @param {String} fn.key The key of collection item. + * @param {Object} [scope] The scope (this reference) in which the function is executed. Defaults to this MixedCollection. + * @param {Number} [start=0] The index to start searching at. + * @return {Number} The matched index or -1 + * @since 2.3.0 + */ + findIndexBy: function(fn, scope, start) { + var me = this, + keys = me.keys, + items = me.items, + i = start || 0, + len = items.length; + for (; i < len; i++) { + if (fn.call(scope || me, items[i], keys[i])) { + return i; + } + } + return -1; + }, + /** + * Returns a regular expression based on the given value and matching options. This is used internally for finding and filtering, + * and by Ext.data.Store#filter + * @private + * @param {String} value The value to create the regex for. This is escaped using Ext.escapeRe + * @param {Boolean} anyMatch True to allow any match - no regex start/end line anchors will be added. Defaults to false + * @param {Boolean} caseSensitive True to make the regex case sensitive (adds 'i' switch to regex). Defaults to false. + * @param {Boolean} exactMatch True to force exact match (^ and $ characters added to the regex). Defaults to false. Ignored if anyMatch is true. + * @since 3.4.0 + */ + createValueMatcher: function(value, anyMatch, caseSensitive, exactMatch) { + if (!value.exec) { + // not a regex + var er = Ext.String.escapeRegex; + value = String(value); + if (anyMatch === true) { + value = er(value); + } else { + value = '^' + er(value); + if (exactMatch === true) { + value += '$'; + } + } + value = new RegExp(value, caseSensitive ? '' : 'i'); + } + return value; + }, + /** + * Creates a shallow copy of this collection + * @return {Ext.util.MixedCollection} + * @since 1.1.0 + */ + clone: function() { + var me = this, + copy = new me.self(me.initialConfig); + copy.add(me.keys, me.items); + // The add using external keys will make the clone think that keys cannot be reliably extracted + // from objects, so that an indexOf call will always have to do a linear search. + // If the flag is not set in this object, we know that the clone will not need it either. + copy.useLinearSearch = me.useLinearSearch; + return copy; + } +}); + +/** + * Represents a single sorter that can be used as part of the sorters configuration in + * Ext.mixin.Sortable. + * + * A common place for Sorters to be used are {@link Ext.data.Store Stores}. For example: + * + * @example + * var store = Ext.create('Ext.data.Store', { + * fields: ['firstName', 'level'], + * sorters: 'level', + * + * data: [ + * { firstName: 'Mitch', level: 9000}, + * { firstName: 'Seth', level: 42}, + * { firstName: 'Fred', level: 510}, + * { firstName: 'Israel', level: 690}, + * { firstName: 'Greg', level: 101}, + * { firstName: 'Pat', level: 0}, + * { firstName: 'Kevin', level: 17}, + * { firstName: 'Brandon',level: 690}, + * { firstName: 'Gary', level: 409}, + * { firstName: 'Scott', level: 789} + * ] + * }); + * + * Ext.create('Ext.grid.Panel', { + * title: 'Support', + * store: store, + * columns: [ + * { text: 'Name', dataIndex: 'firstName' }, + * { text: 'Level', dataIndex: 'level' } + * ], + * height: 300, + * width: 200, + * renderTo: Ext.getBody() + * }); + * + * In the next example, we specify a custom sorter function: + * + * @example + * var store = Ext.create('Ext.data.Store', { + * fields: ['firstName', 'spiritAnimal'], + * sorters: [ + * { + * // Sort by first letter of second word of spirit animal, in + * // descending order + * sorterFn: function(record1, record2) { + * var name1 = record1.data.spiritAnimal.split(' ')[1].substr(0,1), + * name2 = record2.data.spiritAnimal.split(' ')[1].substr(0,1); + * + * return name1 > name2 ? 1 : (name1 === name2) ? 0 : -1; + * }, + * direction: 'DESC' + * } + * ], + * + * data: [ + * { firstName: 'Mitch', spiritAnimal: "Panda Bear"}, + * { firstName: 'Seth', spiritAnimal: "Rascally Rabbit"}, + * { firstName: 'Fred', spiritAnimal: "Honey Badger"}, + * { firstName: 'Israel', spiritAnimal: "Mysterious Capybara"}, + * { firstName: 'Greg', spiritAnimal: "Majestic Platypus"}, + * { firstName: 'Kevin', spiritAnimal: "Sparkling Unicorn"}, + * { firstName: 'Brandon',spiritAnimal: "Pygmy Goat"}, + * { firstName: 'Gary', spiritAnimal: "Suri Alpaca"}, + * { firstName: 'Scott', spiritAnimal: "Ripe Armadillo"}, + * { firstName: 'Pat', spiritAnimal: "Wiley Coyote"} + * ] + * }); + * + * Ext.create('Ext.grid.Panel', { + * title: 'Support', + * store: store, + * columns: [ + * { text: 'Name', dataIndex: 'firstName' }, + * { text: 'Spirit Animal', dataIndex: 'spiritAnimal', flex: 1 } + * ], + * height: 310, + * renderTo: Ext.getBody() + * }); + */ +Ext.define('Ext.util.Sorter', { + isSorter: true, + config: { + /** + * @cfg {String} property + * The property to sort by. Required unless `sorterFn` is provided + */ + property: null, + /** + * @cfg {Function} sorterFn + * A specific sorter function to execute. Can be passed instead of {@link #property}. + * This function should compare the two passed arguments, returning -1, 0 or 1 + * depending on if item 1 should be sorted before, at the same level, or after + * item 2. + * + * sorterFn: function(person1, person2) { + * return (person1.age > person2.age) ? 1 : (person1.age === person2.age ? 0 : -1); + * } + */ + sorterFn: null, + /** + * @cfg {String} root Optional root property. This is mostly useful when sorting a Store, in which case we set the + * root to 'data' to make the filter pull the {@link #property} out of the data object of each item + */ + root: null, + /** + * @cfg {Function} transform A function that will be run on each value before + * it is compared in the sorter. The function will receive a single argument, + * the value. + */ + transform: null, + /** + * @cfg {String} direction The direction to sort by. Valid values are "ASC", and "DESC". + */ + direction: "ASC", + /** + * @cfg {Mixed} id An optional id this sorter can be keyed by in Collections. If + * no id is specified it will use the property name used in this Sorter. If no + * property is specified, e.g. when adding a custom sorter function we will generate + * a random id. + */ + id: undefined + }, + statics: { + /** + * Creates a comparator function (a function that can be passed to `Array.sort`) + * given one or more `Sorter` instances. + * + * The returned function retains a reference to the collection or array of sorters + * passed. This means the function will produce a comparison based on the current + * content of the collection or array, and not based on the content at the time of + * this call. + * + * @param {Ext.util.Sorter[]/Ext.util.Collection} sorters The `Sorter` instances. + * @param [nextFn] The next comparator function to call if all the `sorters` end + * with equality. + * @return {Function} The comparator function. + */ + createComparator: function(sorters, nextFn) { + nextFn = nextFn || 0; + return function(lhs, rhs) { + var items = sorters.isCollection ? sorters.items : sorters, + n = items.length, + comp, i; + for (i = 0; i < n; ++i) { + comp = items[i].sort(lhs, rhs); + if (comp) { + return comp; + } + } + return nextFn && nextFn(lhs, rhs); + }; + } + }, + /** + * This value is set based on the `direction` config to be either 1 or -1. This is used + * as a multiplier for the raw comparison value to factor in the direction. + * @private + * @readonly + */ + multiplier: 1, + constructor: function(config) { + if (config && !this.isGrouper) { + if (!config.property === !config.sorterFn) { + // the above is a "not XOR" - both true or both false + Ext.raise("A Sorter requires either a property or a sorterFn."); + } + } + this.initConfig(config); + }, + getId: function() { + var id = this._id; + if (!id) { + id = this.getProperty(); + if (!id) { + id = Ext.id(null, 'ext-sorter-'); + } + this._id = id; + } + return id; + }, + sort: function(lhs, rhs) { + return this.multiplier * this.sortFn(lhs, rhs); + }, + /** + * @private + * Basic default sorter function that just compares the defined property of each object. + * This is hidden by the `sorterFn` provided by the user. + */ + sortFn: function(item1, item2) { + var me = this, + transform = me._transform, + root = me._root, + property = me._property, + lhs, rhs; + if (root) { + item1 = item1[root]; + item2 = item2[root]; + } + lhs = item1[property]; + rhs = item2[property]; + if (transform) { + lhs = transform(lhs); + rhs = transform(rhs); + } + return (lhs > rhs) ? 1 : (lhs < rhs ? -1 : 0); + }, + applyDirection: function(direction) { + return direction ? direction : 'ASC'; + }, + updateDirection: function(direction) { + this.multiplier = (direction.toUpperCase() === "DESC") ? -1 : 1; + }, + updateProperty: function(property) { + if (property) { + // Unhide the default sortFn on our prototype + delete this.sortFn; + } + }, + updateSorterFn: function(sorterFn) { + // Hide the default sortFn on our prototype + this.sortFn = sorterFn; + }, + /** + * Toggles the direction of this Sorter. Note that when you call this function, + * the Collection this Sorter is part of does not get refreshed automatically. + */ + toggle: function() { + this.setDirection(Ext.String.toggle(this.getDirection(), "ASC", "DESC")); + }, + /** + * Returns this sorter's state. + * @return {Object} + */ + getState: function() { + var me = this, + result = { + root: me.getRoot(), + property: me.getProperty(), + direction: me.getDirection() + }; + // Do not use getId() which will create an identifier if we have none. + // We need to know if we really are identifiable. + if (me._id) { + result.id = me._id; + } + return result; + }, + /** + * Returns this sorter's serialized state. This is used when transmitting this sorter + * to a server. + * @return {Object} + */ + serialize: function() { + return { + property: this.getProperty(), + direction: this.getDirection() + }; + } +}); + +/** + * A mixin which allows a data component to be sorted. This is used by e.g. {@link Ext.data.Store} and {@link Ext.data.TreeStore}. + * + * **NOTE**: This mixin is mainly for internal use and most users should not need to use it directly. It + * is more likely you will want to use one of the component classes that import this mixin, such as + * {@link Ext.data.Store} or {@link Ext.data.TreeStore}. + */ +Ext.define("Ext.util.Sortable", { + /** + * @property {Boolean} isSortable + * `true` in this class to identify an object as an instantiated Sortable, or subclass thereof. + */ + isSortable: true, + $configPrefixed: false, + $configStrict: false, + config: { + /** + * @cfg {Ext.util.Sorter[]/Object[]} sorters + * The initial set of {@link Ext.util.Sorter Sorters}. + * + * sorters: [{ + * property: 'age', + * direction: 'DESC' + * }, { + * property: 'firstName', + * direction: 'ASC' + * }] + */ + sorters: null + }, + /** + * @cfg {String} defaultSortDirection + * The default sort direction to use if one is not specified. + */ + defaultSortDirection: "ASC", + requires: [ + 'Ext.util.Sorter' + ], + /** + * @event beforesort + * Fires before a sort occurs. + * @param {Ext.util.Sortable} me This object. + * @param {Ext.util.Sorter[]} sorters The collection of Sorters being used to generate the comparator function. + */ + /** + * @cfg {Number} [multiSortLimit=3] + * The maximum number of sorters which may be applied to this Sortable when using the "multi" insertion position + * when adding sorters. + * + * New sorters added using the "multi" insertion position are inserted at the top of the sorters list becoming the + * new primary sort key. + * + * If the sorters collection has grown to longer then **`multiSortLimit`**, then the it is trimmed. + * + */ + multiSortLimit: 3, + statics: { + /** + * Creates a single comparator function which encapsulates the passed Sorter array. + * @param {Ext.util.Sorter[]} sorters The sorter set for which to create a comparator function + * @return {Function} a function, which when passed two comparable objects returns the result + * of the whole sorter comparator functions. + */ + createComparator: function(sorters) { + return sorters && sorters.length ? function(r1, r2) { + var result = sorters[0].sort(r1, r2), + length = sorters.length, + i = 1; + // While we have not established a comparison value, + // loop through subsequent sorters asking for a comparison value + for (; !result && i < length; i++) { + result = sorters[i].sort.call(sorters[i], r1, r2); + } + return result; + } : function() { + return 0; + }; + } + }, + /** + * @cfg {String} sortRoot + * The property in each item that contains the data to sort. + */ + applySorters: function(sorters) { + var me = this, + sortersCollection = me.getSorters() || new Ext.util.MixedCollection(false, Ext.returnId); + // We have been configured with a non-default value. + if (sorters) { + sortersCollection.addAll(me.decodeSorters(sorters)); + } + return sortersCollection; + }, + /** + * Updates the sorters collection and triggers sorting of this Sortable. Example usage: + * + * //sort by a single field + * myStore.sort('myField', 'DESC'); + * + * //sorting by multiple fields + * myStore.sort([{ + * property : 'age', + * direction: 'ASC' + * }, { + * property : 'name', + * direction: 'DESC' + * }]); + * + * Classes which use this mixin must implement a **`soSort`** method which accepts a comparator function computed from + * the full sorter set which performs the sort in an implementation-specific way. + * + * When passing a single string argument to sort, Store maintains a ASC/DESC toggler per field, so this code: + * + * store.sort('myField'); + * store.sort('myField'); + * + * Is equivalent to this code, because Store handles the toggling automatically: + * + * store.sort('myField', 'ASC'); + * store.sort('myField', 'DESC'); + * + * @param {String/Ext.util.Sorter[]} [sorters] Either a string name of one of the fields in this Store's configured {@link Ext.data.Model Model}, or an array of sorter configurations. + * @param {String} [direction="ASC"] The overall direction to sort the data by. + * @param {String} [insertionPosition="replace"] Where to put the new sorter in the collection of sorters. + * This may take the following values: + * + * * `replace` : This means that the new sorter(s) becomes the sole sorter set for this Sortable. This is the most useful call mode + * to programatically sort by multiple fields. + * + * * `prepend` : This means that the new sorters are inserted as the primary sorters, unchanged, and the sorter list length must be controlled by the developer. + * + * * `multi` : This is mainly useful for implementing intuitive "Sort by this" user interfaces such as the {@link Ext.grid.Panel GridPanel}'s column sorting UI. + * + * This mode is only supported when passing a property name and a direction. + * + * This means that the new sorter is becomes the primary sorter. If the sorter was **already** the primary sorter, the direction + * of sort is toggled if no direction parameter is specified. + * + * The number of sorters maintained is limited by the {@link #multiSortLimit} configuration. + * + * * `append` : This means that the new sorter becomes the last sorter. + * @param {Boolean} doSort True to sort using a generated sorter function that combines all of the Sorters passed + * @return {Ext.util.Sorter[]} The new sorters. + */ + sort: function(sorters, direction, insertionPosition, doSort) { + var me = this, + sorter, overFlow, + currentSorters = me.getSorters(); + if (!currentSorters) { + me.setSorters(null); + currentSorters = me.getSorters(); + } + if (Ext.isArray(sorters)) { + doSort = insertionPosition; + insertionPosition = direction; + } else if (Ext.isObject(sorters)) { + sorters = [ + sorters + ]; + doSort = insertionPosition; + insertionPosition = direction; + } else if (Ext.isString(sorters)) { + sorter = currentSorters.get(sorters); + if (!sorter) { + sorter = { + property: sorters, + direction: direction + }; + } else if (direction == null) { + sorter.toggle(); + } else { + sorter.setDirection(direction); + } + sorters = [ + sorter + ]; + } + if (sorters && sorters.length) { + sorters = me.decodeSorters(sorters); + switch (insertionPosition) { + // multi sorting means always inserting the specified sorters + // at the top. + // If we are asked to sort by what is already the primary sorter + // then toggle its direction. + case "multi": + // Insert the new sorter at the beginning. + currentSorters.insert(0, sorters[0]); + // If we now are oversize, trim our sorters collection + overFlow = currentSorters.getCount() - me.multiSortLimit; + if (overFlow > 0) { + currentSorters.removeRange(me.multiSortLimit, overFlow); + }; + break; + case "prepend": + currentSorters.insert(0, sorters); + break; + case "append": + currentSorters.addAll(sorters); + break; + case undefined: + case null: + case "replace": + currentSorters.clear(); + currentSorters.addAll(sorters); + break; + default: + Ext.raise('Sorter insertion point must be "multi", "prepend", "append" or "replace"'); + } + } + if (doSort !== false) { + me.fireEvent('beforesort', me, sorters); + me.onBeforeSort(sorters); + if (me.getSorterCount()) { + // Sort using a generated sorter function which combines all of the Sorters passed + me.doSort(me.generateComparator()); + } + } + return sorters; + }, + /** + * @protected + * Returns the number of Sorters which apply to this Sortable. + * + * May be overridden in subclasses. {@link Ext.data.Store Store} in particlar overrides + * this because its groupers must contribute to the sorter count so that the sort method above executes doSort. + */ + getSorterCount: function() { + return this.getSorters().items.length; + }, + /** + * Returns a comparator function which compares two items and returns -1, 0, or 1 depending + * on the currently defined set of {@link #cfg-sorters}. + * + * If there are no {@link #cfg-sorters} defined, it returns a function which returns `0` meaning + * that no sorting will occur. + */ + generateComparator: function() { + var sorters = this.getSorters().getRange(); + return sorters.length ? this.createComparator(sorters) : this.emptyComparator; + }, + emptyComparator: function() { + return 0; + }, + onBeforeSort: Ext.emptyFn, + /** + * @private + * Normalizes an array of sorter objects, ensuring that they are all Ext.util.Sorter instances + * @param {Object[]} sorters The sorters array + * @return {Ext.util.Sorter[]} Array of Ext.util.Sorter objects + */ + decodeSorters: function(sorters) { + if (!Ext.isArray(sorters)) { + if (sorters === undefined) { + sorters = []; + } else { + sorters = [ + sorters + ]; + } + } + var length = sorters.length, + Sorter = Ext.util.Sorter, + model = this.getModel ? this.getModel() : this.model, + field, config, i; + for (i = 0; i < length; i++) { + config = sorters[i]; + if (!(config instanceof Sorter)) { + if (Ext.isString(config)) { + config = { + property: config + }; + } + Ext.applyIf(config, { + root: this.sortRoot, + direction: "ASC" + }); + //support for 3.x style sorters where a function can be defined as 'fn' + if (config.fn) { + config.sorterFn = config.fn; + } + //support a function to be passed as a sorter definition + if (typeof config == 'function') { + config = { + sorterFn: config + }; + } + // ensure sortType gets pushed on if necessary + if (model && !config.transform) { + field = model.getField(config.property); + config.transform = field && field.sortType !== Ext.identityFn ? field.sortType : undefined; + } + sorters[i] = new Ext.util.Sorter(config); + } + } + return sorters; + }, + /** + * Gets the first sorter from the sorters collection, excluding + * any groupers that may be in place + * @protected + * @return {Ext.util.Sorter} The sorter, null if none exist + */ + getFirstSorter: function() { + var sorters = this.getSorters().items, + len = sorters.length, + i = 0, + sorter; + for (; i < len; ++i) { + sorter = sorters[i]; + if (!sorter.isGrouper) { + return sorter; + } + } + return null; + } +}, function() { + // Reference the static implementation in prototype + this.prototype.createComparator = this.createComparator; +}); + +/** + * Represents a collection of a set of key and value pairs. Each key in the MixedCollection + * must be unique, the same key cannot exist twice. This collection is ordered, items in the + * collection can be accessed by index or via the key. Newly added items are added to + * the end of the collection. This class is similar to {@link Ext.util.HashMap} however it + * is heavier and provides more functionality. Sample usage: + * + * var coll = new Ext.util.MixedCollection(); + * coll.add('key1', 'val1'); + * coll.add('key2', 'val2'); + * coll.add('key3', 'val3'); + * + * console.log(coll.get('key1')); // prints 'val1' + * console.log(coll.indexOfKey('key3')); // prints 2 + * + * The MixedCollection also has support for sorting and filtering of the values in the collection. + * + * var coll = new Ext.util.MixedCollection(); + * coll.add('key1', 100); + * coll.add('key2', -100); + * coll.add('key3', 17); + * coll.add('key4', 0); + * var biggerThanZero = coll.filterBy(function(value){ + * return value > 0; + * }); + * console.log(biggerThanZero.getCount()); // prints 2 + * + */ +Ext.define('Ext.util.MixedCollection', { + extend: 'Ext.util.AbstractMixedCollection', + mixins: { + sortable: 'Ext.util.Sortable' + }, + /** + * @cfg {Boolean} allowFunctions + * Configure as `true` if the {@link #addAll} function should add function references + * to the collection. + */ + /** + * Creates new MixedCollection. + * @param {Object} config A configuration object. + * @param {Boolean} [config.allowFunctions=false] Specify `true` if the + * {@link #addAll} function should add function references to the collection. + * @param {Function} [config.getKey] A function that can accept an item of the + * type(s) stored in this MixedCollection and return the key value for that item. + * This is used when available to look up the key on items that were passed without + * an explicit key parameter to a MixedCollection method. Passing this parameter is + * equivalent to overriding the {@link #method-getKey} method. + */ + constructor: function() { + this.initConfig(); + this.callParent(arguments); + }, + doSort: function(sorterFn) { + this.sortBy(sorterFn); + }, + /** + * @private + * Performs the actual sorting based on a direction and a sorting function. + * Internally, this creates a temporary array of all items in the MixedCollection, + * sorts it and then writes the sorted array data back into this.items and this.keys + * @param {String} property Property to sort by ('key', 'value', or 'index') + * @param {String} dir (optional) Direction to sort 'ASC' or 'DESC'. Defaults to + * 'ASC'. + * @param {Function} fn (optional) Comparison function that defines the sort order. + * Defaults to sorting by numeric value. + */ + _sort: function(property, dir, fn) { + var me = this, + i, len, + dsc = String(dir).toUpperCase() == 'DESC' ? -1 : 1, + //this is a temporary array used to apply the sorting function + c = [], + keys = me.keys, + items = me.items, + o; + //default to a simple sorter function if one is not provided + fn = fn || function(a, b) { + return a - b; + }; + //copy all the items into a temporary array, which we will sort + for (i = 0 , len = items.length; i < len; i++) { + c[c.length] = { + key: keys[i], + value: items[i], + index: i + }; + } + //sort the temporary array + Ext.Array.sort(c, function(a, b) { + return fn(a[property], b[property]) * dsc || (// In case of equality, ensure stable sort by comparing collection index + a.index < b.index ? -1 : 1); + }); + // Copy the temporary array back into the main this.items and this.keys objects + // Repopulate the indexMap hash if configured to do so. + for (i = 0 , len = c.length; i < len; i++) { + o = c[i]; + items[i] = o.value; + keys[i] = o.key; + me.indexMap[o.key] = i; + } + me.generation++; + me.indexGeneration = me.generation; + me.fireEvent('sort', me); + }, + /** + * Sorts the collection by a single sorter function + * @param {Function} sorterFn The function to sort by + */ + sortBy: function(sorterFn) { + var me = this, + items = me.items, + item, + keys = me.keys, + key, + length = items.length, + i; + // Stamp the collection index into each item so that we can implement stable sort + for (i = 0; i < length; i++) { + items[i].$extCollectionIndex = i; + } + Ext.Array.sort(items, function(a, b) { + return sorterFn(a, b) || (// In case of equality, ensure stable sort by comparing collection index + a.$extCollectionIndex < b.$extCollectionIndex ? -1 : 1); + }); + // Update the keys array, and remove the index + for (i = 0; i < length; i++) { + item = items[i]; + key = me.getKey(item); + keys[i] = key; + me.indexMap[key] = i; + delete item.$extCollectionIndex; + } + me.generation++; + me.indexGeneration = me.generation; + me.fireEvent('sort', me, items, keys); + }, + /** + * Calculates the insertion index of the new item based upon the comparison function passed, or the current sort order. + * @param {Object} newItem The new object to find the insertion position of. + * @param {Function} [sorterFn] The function to sort by. This is the same as the sorting function + * passed to {@link #sortBy}. It accepts 2 items from this MixedCollection, and returns -1 0, or 1 + * depending on the relative sort positions of the 2 compared items. + * + * If omitted, a function {@link #generateComparator generated} from the currently defined set of + * {@link #cfg-sorters} will be used. + * + * @return {Number} The insertion point to add the new item into this MixedCollection at using {@link #insert} + */ + findInsertionIndex: function(newItem, sorterFn) { + var me = this, + items = me.items, + start = 0, + end = items.length - 1, + middle, comparison; + if (!sorterFn) { + sorterFn = me.generateComparator(); + } + while (start <= end) { + middle = (start + end) >> 1; + comparison = sorterFn(newItem, items[middle]); + if (comparison >= 0) { + start = middle + 1; + } else if (comparison < 0) { + end = middle - 1; + } + } + return start; + }, + /** + * @method reorder + * @inheritdoc Ext.util.AbstractMixedCollection#method-reorder + */ + reorder: function(mapping) { + this.callParent([ + mapping + ]); + this.fireEvent('sort', this); + }, + /** + * Sorts this collection by keys. + * @param {"ASC"/"DESC"} [dir="ASC"] 'ASC' or 'DESC'. Defaults to 'ASC'. + * @param {Function} [fn] Comparison function that defines the sort order. + * Defaults to sorting by case insensitive string. + */ + sortByKey: function(dir, fn) { + this._sort('key', dir, fn || function(a, b) { + var v1 = String(a).toUpperCase(), + v2 = String(b).toUpperCase(); + return v1 > v2 ? 1 : (v1 < v2 ? -1 : 0); + }); + } +}); + +// @tag core +/** + * Provides the ability to execute one or more arbitrary tasks in an asynchronous manner. + * + * Generally, you can use the singleton {@link Ext.TaskManager}. Or you can create + * separate TaskRunner instances to start and stop unique tasks independent of one + * another. + * + * Example usage: + * + * @example + * var runner = new Ext.util.TaskRunner(), + * clock, updateClock, task; + * + * clock = Ext.getBody().appendChild({ + * id: 'clock' + * }); + * + * // Start a simple clock task that updates a div once per second + * updateClock = function() { + * clock.setHtml(Ext.Date.format(new Date(), 'g:i:s A')); + * }; + * + * task = runner.start({ + * run: updateClock, + * interval: 1000 + * }); + * + * The equivalent using TaskManager: + * + * @example + * var clock, updateClock, task; + * + * clock = Ext.getBody().appendChild({ + * id: 'clock' + * }); + * + * // Start a simple clock task that updates a div once per second + * updateClock = function() { + * clock.setHtml(Ext.Date.format(new Date(), 'g:i:s A')); + * }; + * + * var task = Ext.TaskManager.start({ + * run: updateClock, + * interval: 1000 + * }); + * + * To end a running task: + * + * task.destroy(); + * + * If a task needs to be started and stopped repeated over time, you can create a + * {@link Ext.util.TaskRunner.Task Task} instance. + * + * var runner = new Ext.util.TaskRunner(), + * task; + * + * task = runner.newTask({ + * run: function() { + * // useful code + * }, + * interval: 1000 + * }); + * + * task.start(); + * + * // ... + * + * task.stop(); + * + * // ... + * + * task.start(); + * + * A re-usable, single-run task can be managed similar to the above: + * + * var runner = new Ext.util.TaskRunner(), + * task; + * + * task = runner.newTask({ + * run: function() { + * // useful code + * }, + * interval: 1000, + * repeat: 1 + * }); + * + * task.start(); + * + * // ... + * + * task.stop(); + * + * // ... + * + * task.start(); + * + * See the {@link #start} method for details about how to configure a Task. + * + * Also see {@link Ext.util.DelayedTask}. + * + * @constructor + * @param {Number/Object} [interval=10] The minimum precision in milliseconds supported by + * this TaskRunner instance. Alternatively, a config object to apply to the new instance. + */ +Ext.define('Ext.util.TaskRunner', { + // @require Ext.Function + /** + * @cfg {Boolean} fireIdleEvent + * This may be configured `false` to inhibit firing of the {@link + * Ext.GlobalEvents#idle idle event} after task invocation. By default the tasks + * run in a given tick determine whether `idle` events fire. + */ + fireIdleEvent: null, + /** + * @cfg {Number} interval + * How often to run the task in milliseconds. Defaults to every 10ms. + */ + interval: 10, + /** + * @property timerId + * The id of the current timer. + * @private + */ + timerId: null, + constructor: function(interval) { + var me = this; + if (typeof interval === 'number') { + me.interval = interval; + } else if (interval) { + Ext.apply(me, interval); + } + me.tasks = []; + me.timerFn = me.onTick.bind(me); + }, + /** + * Creates a new {@link Ext.util.TaskRunner.Task Task} instance. These instances can + * be easily started and stopped. + * @param {Object} config The config object. For details on the supported properties, + * see {@link #start}. + * + * @return {Ext.util.TaskRunner.Task} + * Ext.util.TaskRunner.Task instance, which can be useful for method chaining. + */ + newTask: function(config) { + var task = new Ext.util.TaskRunner.Task(config); + task.manager = this; + if (Ext.Timer.track) { + task.creator = new Error().stack; + } + return task; + }, + /** + * Starts a new task. + * + * Before each invocation, Ext injects the property `taskRunCount` into the task object + * so that calculations based on the repeat count can be performed. + * + * The returned task will contain a `destroy` method that can be used to destroy the + * task and cancel further calls. This is equivalent to the {@link #stop} method. + * + * @param {Object} task A config object that supports the following properties: + * @param {Function} task.run The function to execute each time the task is invoked. The + * function will be called at each interval and passed the `args` argument if specified, + * and the current invocation count if not. + * + * If a particular scope (`this` reference) is required, be sure to specify it using + * the `scope` argument. + * + * @param {Function} task.onError The function to execute in case of unhandled + * error on task.run. + * + * @param {Boolean} task.run.return `false` from this function to terminate the task. + * + * @param {Number} task.interval The frequency in milliseconds with which the task + * should be invoked. + * + * @param {Object[]} [task.args] An array of arguments to be passed to the function + * specified by `run`. If not specified, the current invocation count is passed. + * + * @param {Boolean} [task.addCountToArgs=false] True to add the current invocation count as + * one of the arguments of args. + * Note: This only takes effect when args is specified. + * + * @param {Object} [task.scope] The scope (`this` reference) in which to execute the + * `run` function. Defaults to the task config object. + * + * @param {Number} [task.duration] The length of time in milliseconds to invoke the task + * before stopping automatically (defaults to indefinite). + * + * @param {Number} [task.repeat] The number of times to invoke the task before stopping + * automatically (defaults to indefinite). + * + * @param {Number} [task.fireIdleEvent=true] If all tasks in a TaskRunner's execution + * sweep are configured with `fireIdleEvent: false`, then the + * {@link Ext.GlobalEvents#idle idle event} is not fired when the TaskRunner's execution + * sweep finishes. + * + * @param {Boolean} [task.fireOnStart=false] True to run the task immediately instead of + * waiting for the _interval's_ initial pass to call the _run_ function. + */ + start: function(task) { + var me = this, + now = Ext.Date.now(); + if (!task.pending) { + me.tasks.push(task); + task.pending = true; + } + // don't allow the task to be added to me.tasks again + task.stopped = false; + // might have been previously stopped... + task.taskStartTime = now; + task.taskRunTime = task.fireOnStart !== false ? 0 : task.taskStartTime; + task.taskRunCount = 0; + if (!me.firing) { + if (task.fireOnStart !== false) { + me.startTimer(0, now); + } else { + me.startTimer(task.interval, now); + } + } + return task; + }, + /** + * Stops an existing running task. + * @param {Object} task The task to stop. + * @param {Boolean} andRemove Pass `true` to also remove the task from the queue. + * @return {Object} The task + */ + stop: function(task, andRemove) { + var me = this, + tasks = me.tasks, + pendingCount = 0, + i; + // NOTE: we don't attempt to remove the task from me.tasks at this point because + // this could be called from inside a task which would then corrupt the state of + // the loop in onTick + if (!task.stopped) { + task.stopped = true; + task.pending = false; + if (task.onStop) { + task.onStop.call(task.scope || task, task); + } + } + if (andRemove) { + Ext.Array.remove(tasks, task); + } + // If there are now no pending tasks + // we shhuld stop the timer. + for (i = 0; !pendingCount && i < tasks.length; i++) { + if (!tasks[i].stopped) { + pendingCount++; + } + } + if (!pendingCount) { + Ext.undefer(me.timerId); + me.timerId = null; + } + return task; + }, + /** + * Stops all tasks that are currently running. + * @param {Boolean} andRemove Pass `true` to also remove the tasks from the queue. + */ + stopAll: function(andRemove) { + var me = this; + // onTick will take care of cleaning up the mess after this point... + // must use reverse in case a task is removed. + Ext.each(this.tasks, function(task) { + me.stop(task, andRemove); + }, null, true); + }, + //------------------------------------------------------------------------- + firing: false, + nextExpires: 1.0E99, + /** + * @private + */ + onTick: function() { + var me = this, + tasks = me.tasks, + fireIdleEvent = me.fireIdleEvent, + // null by default + now = Ext.Date.now(), + nextExpires = 1.0E99, + len = tasks.length, + expires, newTasks, i, task, rt, remove, args; + var timer = Ext.Timer.get(me.timerId); + if (timer) { + timer.tasks = []; + } + me.timerId = null; + me.firing = true; + // ensure we don't startTimer during this loop... + // tasks.length can be > len if start is called during a task.run call... so we + // first check len to avoid tasks.length reference but eventually we need to also + // check tasks.length. we avoid repeating use of tasks.length by setting len at + // that time (to help the next loop) + for (i = 0; i < len || i < (len = tasks.length); ++i) { + task = tasks[i]; + if (!(remove = task.stopped)) { + expires = task.taskRunTime + task.interval; + if (expires <= now) { + rt = 1; + // otherwise we have a stale "rt" + // If all tasks left specify fireIdleEvent as false, then don't do it + if (fireIdleEvent === null && task.fireIdleEvent !== false) { + fireIdleEvent = true; + } + task.taskRunCount++; + if (task.args) { + args = task.addCountToArgs ? task.args.concat([ + task.taskRunCount + ]) : task.args; + } else { + args = [ + task.taskRunCount + ]; + } + // We want the exceptions not to get caught while unit testing + if (timer) { + timer.tasks.push(task); + } + if (me.disableTryCatch) { + rt = task.run.apply(task.scope || task, args); + } else { + try { + rt = task.run.apply(task.scope || task, args); + } catch (taskError) { + try { + Ext.log({ + fn: task.run, + prefix: 'Error while running task', + stack: taskError.stack, + msg: taskError, + level: 'error' + }); + if (task.onError) { + rt = task.onError.call(task.scope || task, task, taskError); + } + } catch (ignore) {} + } + } + task.taskRunTime = now; + if (rt === false || task.taskRunCount === task.repeat) { + me.stop(task); + remove = true; + } else { + remove = task.stopped; + // in case stop was called by run + expires = now + task.interval; + } + } + if (!remove && task.duration && task.duration <= (now - task.taskStartTime)) { + me.stop(task); + remove = true; + } + } + if (remove) { + task.pending = false; + // allow the task to be added to me.tasks again + // once we detect that a task needs to be removed, we copy the tasks that + // will carry forward into newTasks... this way we avoid O(N*N) to remove + // each task from the tasks array (and ripple the array down) and also the + // potentially wasted effort of making a new tasks[] even if all tasks are + // going into the next wave. + if (!newTasks) { + newTasks = tasks.slice(0, i); + } + } else // we don't set me.tasks here because callbacks can also start tasks, + // which get added to me.tasks... so we will visit them in this loop + // and account for their expirations in nextExpires... + { + if (newTasks) { + newTasks.push(task); + } + // we've cloned the tasks[], so keep this one... + if (nextExpires > expires) { + nextExpires = expires; + } + } + } + // track the nearest expiration time + if (newTasks) { + // only now can we copy the newTasks to me.tasks since no user callbacks can + // take place + me.tasks = newTasks; + } + me.firing = false; + // we're done, so allow startTimer afterwards + if (me.tasks.length) { + // we create a new Date here because all the callbacks could have taken a long + // time... we want to base the next timeout on the current time (after the + // callback storm): + me.startTimer(nextExpires - now, Ext.Date.now()); + } + // If all tasks fired and had fireIdleEvent=false then our fireIdleEvent var + // will still be null. This is to allow any task that does not suppress idle + // to override those that do. The only other reason our var will be null is if + // no tasks fired. In which case, no need for idle either. + if (fireIdleEvent === null) { + fireIdleEvent = false; + } + Ext._suppressIdle = !fireIdleEvent; + }, + /** + * @private + */ + startTimer: function(timeout, now) { + var me = this, + expires = now + timeout, + timerId = me.timerId; + // Check to see if this request is enough in advance of the current timer. If so, + // we reschedule the timer based on this new expiration. + if (timerId && me.nextExpires - expires > me.interval) { + timerId = Ext.undefer(timerId); + } + if (!timerId) { + if (timeout < me.interval) { + timeout = me.interval; + } + me.timerId = Ext.defer(me.timerFn, timeout); + me.nextExpires = expires; + var timer = Ext.Timer.get(me.timerId); + if (timer) { + timer.runner = me; + } + } + } +}, function() { + var me = this, + proto = me.prototype; + /** + * Destroys this instance, stopping all tasks that are currently running. + * @method destroy + */ + proto.destroy = proto.stopAll; + /** + * Instances of this class are created by {@link Ext.util.TaskRunner#newTask} method. + * + * For details on config properties, see {@link Ext.util.TaskRunner#start}. + * @class Ext.util.TaskRunner.Task + */ + me.Task = new Ext.Class({ + isTask: true, + /** + * This flag is set to `true` by {@link #stop}. + * @private + */ + stopped: true, + // this avoids the odd combination of !stopped && !pending + fireOnStart: false, + constructor: function(config) { + Ext.apply(this, config); + }, + /** + * Restarts this task, clearing it duration, expiration and run count. + * @param {Number} [interval] Optionally reset this task's interval. + */ + restart: function(interval) { + if (interval !== undefined) { + this.interval = interval; + } + this.manager.start(this); + }, + /** + * Starts this task if it is not already started. + * @param {Number} [interval] Optionally reset this task's interval. + */ + start: function(interval) { + if (this.stopped) { + this.restart(interval); + } + }, + /** + * Stops this task. + */ + stop: function(andRemove) { + this.manager.stop(this, andRemove); + }, + destroy: function() { + this.stop(true); + } + }); + proto = me.Task.prototype; + /** + * Destroys this instance, stopping this task's execution. + * @method destroy + * @member Ext.util.TaskRunner.Task + */ + proto.destroy = proto.stop; +}); + +/** + * @class Ext.fx.target.Target + +This class specifies a generic target for an animation. It provides a wrapper around a +series of different types of objects to allow for a generic animation API. +A target can be a single object or a Composite object containing other objects that are +to be animated. This class and it's subclasses are generally not created directly, the +underlying animation will create the appropriate Ext.fx.target.Target object by passing +the instance to be animated. + +The following types of objects can be animated: + +- {@link Ext.fx.target.Component Components} +- {@link Ext.fx.target.Element Elements} +- {@link Ext.fx.target.Sprite Sprites} + + * @abstract + */ +Ext.define('Ext.fx.target.Target', { + isAnimTarget: true, + /** + * Creates new Target. + * @param {Ext.Component/Ext.dom.Element/Ext.draw.sprite.Sprite} target The object to be animated + */ + constructor: function(target) { + this.target = target; + this.id = this.getId(); + }, + getId: function() { + return this.target.id; + }, + remove: function() { + Ext.destroy(this.target); + } +}); + +/** + * @class Ext.fx.target.Element + * + * This class represents a animation target for an {@link Ext.dom.Element}. In general this class will not be + * created directly, the {@link Ext.dom.Element} will be passed to the animation and + * and the appropriate target will be created. + */ +Ext.define('Ext.fx.target.Element', { + /* Begin Definitions */ + extend: 'Ext.fx.target.Target', + /* End Definitions */ + type: 'element', + constructor: function(target) { + this.callParent([ + target + ]); + // Allow simple local left/top style setting for top level absolute positioned elements. + this.isAbsoluteOnPage = this.target.dom.parentNode === document.body && this.target.isStyle('position', 'absolute'); + }, + getElVal: function(el, attr, val) { + if (val === undefined) { + if (attr === 'x') { + val = el.getX(); + } else if (attr === 'y') { + val = el.getY(); + } else if (attr === 'scrollTop') { + val = el.getScroll().top; + } else if (attr === 'scrollLeft') { + val = el.getScroll().left; + } else if (attr === 'height') { + val = el.getHeight(); + } else if (attr === 'width') { + val = el.getWidth(); + } else { + val = el.getStyle(attr); + } + } + return val; + }, + getAttr: function(attr, val) { + var el = this.target; + return [ + [ + el, + this.getElVal(el, attr, val) + ] + ]; + }, + setAttr: function(targetData) { + var ln = targetData.length, + attrs, attr, o, i, j, ln2; + for (i = 0; i < ln; i++) { + attrs = targetData[i].attrs; + for (attr in attrs) { + if (attrs.hasOwnProperty(attr)) { + ln2 = attrs[attr].length; + for (j = 0; j < ln2; j++) { + o = attrs[attr][j]; + this.setElVal(o[0], attr, o[1]); + } + } + } + } + }, + setElVal: function(element, attr, value) { + if (attr === 'x') { + if (this.isAbsoluteOnPage) { + element.setLocalX(value); + } else { + element.setXY([ + value, + null + ]); + } + } else if (attr === 'y') { + if (this.isAbsoluteOnPage) { + element.setLocalY(value); + } else { + element.setXY([ + null, + value + ]); + } + } else if (attr === 'scrollTop') { + element.scrollTo('top', value); + } else if (attr === 'scrollLeft') { + element.scrollTo('left', value); + } else if (attr === 'width') { + element.setWidth(value); + } else if (attr === 'height') { + element.setHeight(value); + } else { + element.setStyle(attr, value); + } + } +}); + +/** + * @class Ext.fx.target.ElementCSS + * + * This class represents a animation target for an {@link Ext.dom.Element} that supports CSS + * based animation. In general this class will not be created directly, the {@link Ext.dom.Element} + * will be passed to the animation and the appropriate target will be created. + */ +Ext.define('Ext.fx.target.ElementCSS', { + /* Begin Definitions */ + extend: 'Ext.fx.target.Element', + /* End Definitions */ + setAttr: function(targetData, isFirstFrame) { + var cssArr = { + attrs: [], + duration: [], + easing: [] + }, + ln = targetData.length, + cleanerFn = function() { + this.setStyle(Ext.supports.CSS3Prefix + 'TransitionProperty', null); + this.setStyle(Ext.supports.CSS3Prefix + 'TransitionDuration', null); + this.setStyle(Ext.supports.CSS3Prefix + 'TransitionTimingFunction', null); + }, + single = { + single: true + }, + attributes, attrs, attr, easing, duration, o, i, j, ln2; + for (i = 0; i < ln; i++) { + attrs = targetData[i]; + duration = attrs.duration; + easing = attrs.easing; + attrs = attrs.attrs; + for (attr in attrs) { + if (Ext.Array.indexOf(cssArr.attrs, attr) == -1) { + cssArr.attrs.push(attr.replace(/[A-Z]/g, function(v) { + return '-' + v.toLowerCase(); + })); + cssArr.duration.push(duration + 'ms'); + cssArr.easing.push(easing); + } + } + } + attributes = cssArr.attrs.join(','); + duration = cssArr.duration.join(','); + easing = cssArr.easing.join(', '); + for (i = 0; i < ln; i++) { + attrs = targetData[i].attrs; + for (attr in attrs) { + ln2 = attrs[attr].length; + for (j = 0; j < ln2; j++) { + o = attrs[attr][j]; + o[0].setStyle(Ext.supports.CSS3Prefix + 'TransitionProperty', isFirstFrame ? '' : attributes); + o[0].setStyle(Ext.supports.CSS3Prefix + 'TransitionDuration', isFirstFrame ? '' : duration); + o[0].setStyle(Ext.supports.CSS3Prefix + 'TransitionTimingFunction', isFirstFrame ? '' : easing); + o[0].setStyle(attr, o[1]); + // Must trigger reflow to make this get used as the start point for the transition that follows + if (isFirstFrame) { + o = o[0].dom.offsetWidth; + } else { + // Remove transition properties when completed. + o[0].on(Ext.supports.CSS3TransitionEnd, cleanerFn, o[0], single); + } + } + } + } + } +}); + +/** + * @class Ext.fx.target.CompositeElement + * + * This class represents a animation target for a {@link Ext.CompositeElement}. It allows + * each {@link Ext.dom.Element} in the group to be animated as a whole. In general this class will not be + * created directly, the {@link Ext.CompositeElement} will be passed to the animation and + * and the appropriate target will be created. + */ +Ext.define('Ext.fx.target.CompositeElement', { + /* Begin Definitions */ + extend: 'Ext.fx.target.Element', + /* End Definitions */ + /** + * @property {Boolean} isComposite + * `true` in this class to identify an object as an instantiated CompositeElement, or subclass thereof. + */ + isComposite: true, + constructor: function(target) { + target.id = target.id || Ext.id(null, 'ext-composite-'); + this.callParent([ + target + ]); + }, + getAttr: function(attr, val) { + var out = [], + target = this.target, + elements = target.elements, + length = elements.length, + i, el; + for (i = 0; i < length; i++) { + el = elements[i]; + if (el) { + el = target.getElement(el); + out.push([ + el, + this.getElVal(el, attr, val) + ]); + } + } + return out; + }, + setAttr: function(targetData) { + var target = this.target, + ln = targetData.length, + elements = target.elements, + ln3 = elements.length, + value, k, attrs, attr, el, i, j, ln2; + for (i = 0; i < ln; i++) { + attrs = targetData[i].attrs; + for (attr in attrs) { + if (attrs.hasOwnProperty(attr)) { + ln2 = attrs[attr].length; + for (j = 0; j < ln2; j++) { + value = attrs[attr][j][1]; + for (k = 0; k < ln3; ++k) { + el = elements[k]; + if (el) { + el = target.getElement(el); + this.setElVal(el, attr, value); + } + } + } + } + } + } + }, + remove: function() { + this.target.destroy(); + } +}); + +/** + * @class Ext.fx.target.CompositeElementCSS + * + * This class represents a animation target for a {@link Ext.CompositeElement}, where the + * constituent elements support CSS based animation. It allows each {@link Ext.dom.Element} in + * the group to be animated as a whole. In general this class will not be created directly, + * the {@link Ext.CompositeElement} will be passed to the animation and the appropriate target + * will be created. + */ +Ext.define('Ext.fx.target.CompositeElementCSS', { + /* Begin Definitions */ + extend: 'Ext.fx.target.CompositeElement', + requires: [ + 'Ext.fx.target.ElementCSS' + ], + /* End Definitions */ + setAttr: function() { + return Ext.fx.target.ElementCSS.prototype.setAttr.apply(this, arguments); + } +}); + +/** + * @class Ext.fx.target.Sprite + * This class represents an animation target for a {@link Ext.draw.sprite.Sprite}. In general this class will not be + * created directly, the {@link Ext.draw.sprite.Sprite} will be passed to the animation and + * and the appropriate target will be created. + */ +Ext.define('Ext.fx.target.Sprite', { + /* Begin Definitions */ + extend: 'Ext.fx.target.Target', + /* End Definitions */ + type: 'draw', + getFromPrim: function(sprite, attr) { + var obj; + switch (attr) { + case 'rotate': + case 'rotation': + obj = sprite.attr.rotation; + return { + x: obj.x || 0, + y: obj.y || 0, + degrees: obj.degrees || 0 + }; + case 'scale': + case 'scaling': + obj = sprite.attr.scaling; + return { + x: obj.x || 1, + y: obj.y || 1, + cx: obj.cx || 0, + cy: obj.cy || 0 + }; + case 'translate': + case 'translation': + obj = sprite.attr.translation; + return { + x: obj.x || 0, + y: obj.y || 0 + }; + default: + return sprite.attr[attr]; + } + }, + getAttr: function(attr, val) { + return [ + [ + this.target, + val !== undefined ? val : this.getFromPrim(this.target, attr) + ] + ]; + }, + setAttr: function(targetData) { + var ln = targetData.length, + spriteArr = [], + attrsConf, attr, attrArr, attrs, sprite, idx, value, i, j, x, y, ln2; + for (i = 0; i < ln; i++) { + attrsConf = targetData[i].attrs; + for (attr in attrsConf) { + attrArr = attrsConf[attr]; + ln2 = attrArr.length; + for (j = 0; j < ln2; j++) { + sprite = attrArr[j][0]; + attrs = attrArr[j][1]; + if (attr === 'translate' || attr === 'translation') { + value = { + x: attrs.x, + y: attrs.y + }; + } else if (attr === 'rotate' || attr === 'rotation') { + x = attrs.x; + if (isNaN(x)) { + x = null; + } + y = attrs.y; + if (isNaN(y)) { + y = null; + } + value = { + degrees: attrs.degrees, + x: x, + y: y + }; + } else if (attr === 'scale' || attr === 'scaling') { + x = attrs.x; + if (isNaN(x)) { + x = null; + } + y = attrs.y; + if (isNaN(y)) { + y = null; + } + value = { + x: x, + y: y, + cx: attrs.cx, + cy: attrs.cy + }; + } else if (attr === 'width' || attr === 'height' || attr === 'x' || attr === 'y') { + value = parseFloat(attrs); + } else { + value = attrs; + } + idx = Ext.Array.indexOf(spriteArr, sprite); + if (idx === -1) { + spriteArr.push([ + sprite, + {} + ]); + idx = spriteArr.length - 1; + } + spriteArr[idx][1][attr] = value; + } + } + } + ln = spriteArr.length; + for (i = 0; i < ln; i++) { + spriteArr[i][0].setAttributes(spriteArr[i][1]); + } + this.target.redraw(); + } +}); + +/** + * @class Ext.fx.target.CompositeSprite + * + * This class represents a animation target for a {@link Ext.draw.sprite.Composite}. It allows + * each {@link Ext.draw.sprite.Sprite} in the group to be animated as a whole. In general this class will not be + * created directly, the {@link Ext.draw.sprite.Composite} will be passed to the animation and + * and the appropriate target will be created. + */ +Ext.define('Ext.fx.target.CompositeSprite', { + /* Begin Definitions */ + extend: 'Ext.fx.target.Sprite', + /* End Definitions */ + getAttr: function(attr, val) { + var out = [], + sprites = [].concat(this.target.items), + length = sprites.length, + i, sprite; + for (i = 0; i < length; i++) { + sprite = sprites[i]; + out.push([ + sprite, + val !== undefined ? val : this.getFromPrim(sprite, attr) + ]); + } + return out; + } +}); + +/** + * @class Ext.fx.target.Component + * + * This class represents a animation target for a {@link Ext.Component}. In general this class will not be + * created directly, the {@link Ext.Component} will be passed to the animation and + * and the appropriate target will be created. + */ +Ext.define('Ext.fx.target.Component', { + /* Begin Definitions */ + extend: 'Ext.fx.target.Target', + /* End Definitions */ + type: 'component', + // Methods to call to retrieve unspecified "from" values from a target Component + getPropMethod: { + top: function() { + return this.getPosition(true)[1]; + }, + left: function() { + return this.getPosition(true)[0]; + }, + x: function() { + return this.getPosition()[0]; + }, + y: function() { + return this.getPosition()[1]; + }, + height: function() { + return this.getHeight(); + }, + width: function() { + return this.getWidth(); + }, + opacity: function() { + return this.el.getStyle('opacity'); + } + }, + setMethods: { + top: 'setPosition', + left: 'setPosition', + x: 'setPagePosition', + y: 'setPagePosition', + height: 'setSize', + width: 'setSize', + opacity: 'setOpacity' + }, + // Read the named attribute from the target Component. Use the defined getter for the attribute + getAttr: function(attr, val) { + return [ + [ + this.target, + val !== undefined ? val : this.getPropMethod[attr].call(this.target) + ] + ]; + }, + setAttr: function(targetData, isFirstFrame, isLastFrame) { + var me = this, + ln = targetData.length, + attrs, attr, o, i, j, targets, left, top, w, h, + methodsToCall = {}, + methodProps; + for (i = 0; i < ln; i++) { + attrs = targetData[i].attrs; + for (attr in attrs) { + targets = attrs[attr].length; + for (j = 0; j < targets; j++) { + o = attrs[attr][j]; + methodProps = methodsToCall[me.setMethods[attr]] || (methodsToCall[me.setMethods[attr]] = {}); + methodProps.target = o[0]; + methodProps[attr] = o[1]; + } + } + // debugging code: Ext.log('Setting ' + o[0].id + "'s " + attr + ' to ' + o[1]); + if (methodsToCall.setPosition) { + o = methodsToCall.setPosition; + left = (o.left === undefined) ? undefined : parseFloat(o.left); + top = (o.top === undefined) ? undefined : parseFloat(o.top); + o.target.setPosition(left, top); + } + if (methodsToCall.setPagePosition) { + o = methodsToCall.setPagePosition; + o.target.setPagePosition(o.x, o.y); + } + if (methodsToCall.setSize) { + o = methodsToCall.setSize; + // Dimensions not being animated MUST NOT be autosized. They must remain at current value. + w = (o.width === undefined) ? o.target.getWidth() : parseFloat(o.width); + h = (o.height === undefined) ? o.target.getHeight() : parseFloat(o.height); + // Only set the size of the Component on the last frame, or if the animation was + // configured with dynamic: true. + // In other cases, we just set the target element size. + // This will result in either clipping if animating a reduction in size, or the revealing of + // the inner elements of the Component if animating an increase in size. + // Component's animate function initially resizes to the larger size before resizing the + // outer element to clip the contents. + o.target.el.setSize(w, h); + if (isLastFrame || me.dynamic) { + // Defer the final sizing & layout until we are outside of this frame. + // In case anything in the resulting layout calls animation. + // If it does, *this* frame will fire again... recursively + Ext.GlobalEvents.on({ + idle: Ext.Function.bind(o.target.setSize, o.target, [ + w, + h + ]), + single: true + }); + } + } + if (methodsToCall.setOpacity) { + o = methodsToCall.setOpacity; + o.target.el.setStyle('opacity', o.opacity); + } + } + } +}); + +/** + * @class Ext.fx.Queue + * Animation Queue mixin to handle chaining and queueing by target. + * @private + */ +Ext.define('Ext.fx.Queue', { + requires: [ + 'Ext.util.HashMap' + ], + constructor: function() { + this.targets = new Ext.util.HashMap(); + this.fxQueue = {}; + }, + /** + * @private + */ + getFxDefaults: function(targetId) { + var target = this.targets.get(targetId); + if (target) { + return target.fxDefaults; + } + return {}; + }, + /** + * @private + */ + setFxDefaults: function(targetId, obj) { + var target = this.targets.get(targetId); + if (target) { + target.fxDefaults = Ext.apply(target.fxDefaults || {}, obj); + } + }, + /** + * @private + */ + stopAnimation: function(targetId, suppressEvent) { + var me = this, + queue = me.getFxQueue(targetId), + ln = queue.length, + item; + while (ln) { + item = queue[ln - 1]; + if (item) { + item.end(suppressEvent); + } + ln--; + } + }, + /** + * @private + * Returns current animation object if the element has any effects actively running or queued, else returns false. + */ + getActiveAnimation: function(targetId) { + var queue = this.getFxQueue(targetId); + return (queue && !!queue.length) ? queue[0] : false; + }, + /** + * @private + */ + hasFxBlock: function(targetId) { + var queue = this.getFxQueue(targetId); + return queue && queue[0] && queue[0].block; + }, + /** + * @private + * Get fx queue for passed target, create if needed. + */ + getFxQueue: function(targetId) { + if (!targetId) { + return false; + } + var me = this, + fxQueue = me.fxQueue, + queue = fxQueue[targetId], + target = me.targets.get(targetId); + if (!target) { + return false; + } + if (!queue) { + me.fxQueue[targetId] = fxQueue[targetId] = []; + // GarbageCollector will need to clean up Elements since they aren't currently observable + if (target.type !== 'element') { + target.target.on('destroy', function() { + fxQueue[targetId] = null; + delete fxQueue[targetId]; + }); + } + } + return me.fxQueue[targetId]; + }, + /** + * @private + * Clears the fx queue of any pending animations + */ + clearFxQueue: function() { + Ext.Object.clear(this.fxQueue); + }, + /** + * @private + */ + queueFx: function(anim) { + var me = this, + target = anim.target, + targetId = target.getId(), + queue, ln; + if (!target) { + return; + } + queue = me.getFxQueue(targetId); + ln = queue.length; + if (ln) { + if (anim.concurrent) { + anim.paused = false; + } else { + queue[ln - 1].on('afteranimate', function() { + anim.paused = false; + }); + } + } else { + anim.paused = false; + } + anim.on('afteranimate', function() { + Ext.Array.remove(queue, anim); + if (queue.length === 0) { + me.targets.remove(anim.target); + me.fxQueue[targetId] = null; + delete me.fxQueue[targetId]; + } + if (anim.remove) { + if (target.type === 'element') { + var el = Ext.get(targetId); + if (el) { + el.destroy(); + } + } + } + }, me, { + single: true + }); + queue.push(anim); + } +}); + +/** + * @class Ext.fx.Manager + * Animation Manager which keeps track of all current animations and manages them on a frame by frame basis. + * @private + * @singleton + */ +Ext.define('Ext.fx.Manager', { + /* Begin Definitions */ + singleton: true, + requires: [ + 'Ext.util.MixedCollection', + 'Ext.util.TaskRunner', + 'Ext.fx.target.Element', + 'Ext.fx.target.ElementCSS', + 'Ext.fx.target.CompositeElement', + 'Ext.fx.target.CompositeElementCSS', + 'Ext.fx.target.Sprite', + 'Ext.fx.target.CompositeSprite', + 'Ext.fx.target.Component' + ], + mixins: { + queue: 'Ext.fx.Queue' + }, + /* End Definitions */ + /** + * @private + */ + constructor: function() { + var me = this; + me.items = new Ext.util.MixedCollection(); + me.targetArr = {}; + me.mixins.queue.constructor.call(me); + // Do not use fireIdleEvent: false. Each tick of the TaskRunner needs to fire the idleEvent + // in case an animation callback/listener adds a listener. + me.taskRunner = new Ext.util.TaskRunner(); + }, + /** + * @cfg {Number} interval Default interval in miliseconds to calculate each frame. Defaults to 16ms (~60fps) + */ + interval: 16, + /** + * @cfg {Boolean} forceJS Force the use of JavaScript-based animation instead of CSS3 animation, even when CSS3 + * animation is supported by the browser. This defaults to true currently, as CSS3 animation support is still + * considered experimental at this time, and if used should be thouroughly tested across all targeted browsers. + * @protected + */ + forceJS: true, + /** + * @private + * Target Factory + */ + createTarget: function(target) { + var me = this, + useCSS3 = !me.forceJS && Ext.supports.Transitions, + targetObj; + me.useCSS3 = useCSS3; + if (target) { + // dom element, string or fly + if (target.tagName || Ext.isString(target) || target.isFly) { + target = Ext.get(target); + targetObj = new Ext.fx.target['Element' + (useCSS3 ? 'CSS' : '')](target); + } + // Element + else if (target.dom) { + targetObj = new Ext.fx.target['Element' + (useCSS3 ? 'CSS' : '')](target); + } + // Element Composite + else if (target.isComposite) { + targetObj = new Ext.fx.target['CompositeElement' + (useCSS3 ? 'CSS' : '')](target); + } + // Draw Sprite + else if (target.isSprite) { + targetObj = new Ext.fx.target.Sprite(target); + } + // Draw Sprite Composite + else if (target.isCompositeSprite) { + targetObj = new Ext.fx.target.CompositeSprite(target); + } + // Component + else if (target.isComponent) { + targetObj = new Ext.fx.target.Component(target); + } else if (target.isAnimTarget) { + return target; + } else { + return null; + } + me.targets.add(targetObj); + return targetObj; + } else { + return null; + } + }, + /** + * Add an Anim to the manager. This is done automatically when an Anim instance is created. + * @param {Ext.fx.Anim} anim + */ + addAnim: function(anim) { + var me = this, + items = me.items, + task = me.task; + // Make sure we use the anim's id, not the anim target's id here. The anim id will be unique on + // each call to addAnim. `anim.target` is the DOM element being targeted, and since multiple animations + // can target a single DOM node concurrently, the target id cannot be assumned to be unique. + items.add(anim.id, anim); + //Ext.log('+ added anim ', anim.id, ', target: ', anim.target.getId(), ', duration: ', anim.duration); + // Start the timer if not already running + if (!task && items.length) { + task = me.task = { + run: me.runner, + interval: me.interval, + scope: me + }; + //Ext.log('--->> Starting task'); + me.taskRunner.start(task); + } + }, + /** + * Remove an Anim from the manager. This is done automatically when an Anim ends. + * @param {Ext.fx.Anim} anim + */ + removeAnim: function(anim) { + var me = this, + items = me.items, + task = me.task; + items.removeAtKey(anim.id); + //Ext.log(' X removed anim ', anim.id, ', target: ', anim.target.getId(), ', frames: ', anim.frameCount, ', item count: ', items.length); + // Stop the timer if there are no more managed Anims + if (task && !items.length) { + //Ext.log('[]--- Stopping task'); + me.taskRunner.stop(task); + delete me.task; + } + }, + /** + * @private + * Runner function being called each frame + */ + runner: function() { + var me = this, + items = me.items.getRange(), + i = 0, + len = items.length, + anim; + //Ext.log(' executing anim runner task with ', len, ' items'); + me.targetArr = {}; + // Single timestamp for all animations this interval + me.timestamp = new Date(); + // Loop to start any new animations first before looping to + // execute running animations (which will also include all animations + // started in this loop). This is a subtle difference from simply + // iterating in one loop and starting then running each animation, + // but separating the loops is necessary to ensure that all new animations + // actually kick off prior to existing ones regardless of array order. + // Otherwise in edge cases when there is excess latency in overall + // performance, allowing existing animations to run before new ones can + // lead to dropped frames and subtle race conditions when they are + // interdependent, which is often the case with certain Element fx. + for (; i < len; i++) { + anim = items[i]; + if (anim.isReady()) { + //Ext.log(' starting anim ', anim.id, ', target: ', anim.target.id); + me.startAnim(anim); + } + } + for (i = 0; i < len; i++) { + anim = items[i]; + if (anim.isRunning()) { + //Ext.log(' running anim ', anim.target.id); + me.runAnim(anim); + } + } + //else if (!me.useCSS3) { + // When using CSS3 transitions the animations get paused since they are not + // needed once the transition is handed over to the browser, so we can + // ignore this case. However if we are doing JS animations and something is + // paused here it's possibly unintentional. + //Ext.log(' (i) anim ', anim.id, ' is active but not running...'); + //} + // Apply all the pending changes to their targets + me.applyPendingAttrs(); + // Avoid retaining target references after we are finished with anims + me.targetArr = null; + }, + /** + * @private + * Start the individual animation (initialization) + */ + startAnim: function(anim) { + anim.start(this.timestamp); + }, + /** + * @private + * Run the individual animation for this frame + */ + runAnim: function(anim, forceEnd) { + if (!anim) { + return; + } + var me = this, + useCSS3 = me.useCSS3 && anim.target.type === 'element', + elapsedTime = me.timestamp - anim.startTime, + lastFrame = (elapsedTime >= anim.duration), + target, o; + if (forceEnd) { + elapsedTime = anim.duration; + lastFrame = true; + } + target = me.collectTargetData(anim, elapsedTime, useCSS3, lastFrame); + // For CSS3 animation, we need to immediately set the first frame's attributes without any transition + // to get a good initial state, then add the transition properties and set the final attributes. + if (useCSS3) { + //Ext.log(' (i) using CSS3 transitions'); + // Flush the collected attributes, without transition + anim.target.setAttr(target.anims[anim.id].attributes, true); + // Add the end frame data + me.collectTargetData(anim, anim.duration, useCSS3, lastFrame); + // Pause the animation so runAnim doesn't keep getting called + anim.paused = true; + target = anim.target.target; + // We only want to attach an event on the last element in a composite + if (anim.target.isComposite) { + target = anim.target.target.last(); + } + // Listen for the transitionend event + o = {}; + o[Ext.supports.CSS3TransitionEnd] = anim.lastFrame; + o.scope = anim; + o.single = true; + target.on(o); + } + return target; + }, + jumpToEnd: function(anim) { + var me = this, + target, clear; + // We may not be in the middle of a tick, where targetAttr is cleared, + // so if we don't have it, poke it in here while we jump to the end state + if (!me.targetArr) { + me.targetArr = {}; + clear = true; + } + target = me.runAnim(anim, true); + me.applyAnimAttrs(target, target.anims[anim.id]); + if (clear) { + me.targetArr = null; + } + }, + /** + * @private + * Collect target attributes for the given Anim object at the given timestamp + * @param {Ext.fx.Anim} anim The Anim instance + * @param {Number} elapsedTime Time after the anim's start time + * @param {Boolean} [useCSS3=false] True if using CSS3-based animation, else false + * @param {Boolean} [isLastFrame=false] True if this is the last frame of animation to be run, else false + * @return {Object} The animation target wrapper object containing the passed animation along with the + * new attributes to set on the target's element in the next animation frame. + */ + collectTargetData: function(anim, elapsedTime, useCSS3, isLastFrame) { + var targetId = anim.target.getId(), + target = this.targetArr[targetId]; + if (!target) { + // Create a thin wrapper around the target so that we can create a link between the + // target element and its associated animations. This is important later when applying + // attributes to the target so that each animation can be independently run with its own + // duration and stopped at any point without affecting other animations for the same target. + target = this.targetArr[targetId] = { + id: targetId, + el: anim.target, + anims: {} + }; + } + // This is a wrapper for the animation so that we can also save state along with it, + // including the current elapsed time and lastFrame status. Even though this method only + // adds a single anim object per call, each target element could have multiple animations + // associated with it, which is why the anim is added to the target's `anims` hash by id. + target.anims[anim.id] = { + id: anim.id, + anim: anim, + elapsed: elapsedTime, + isLastFrame: isLastFrame, + // This is the object that gets applied to the target element below in applyPendingAttrs(): + attributes: [ + { + duration: anim.duration, + easing: (useCSS3 && anim.reverse) ? anim.easingFn.reverse().toCSS3() : anim.easing, + // This is where the magic happens. The anim calculates what its new attributes should + // be based on the current frame and returns those as a hash of values. + attrs: anim.runAnim(elapsedTime) + } + ] + }; + return target; + }, + // Duplicating this code for performance reasons. We only want to apply the anims + // to a single animation because we're hitting the end. It may be out of sequence from + // the runner timer. + applyAnimAttrs: function(target, animWrap) { + var anim = animWrap.anim; + if (animWrap.attributes && anim.isRunning()) { + target.el.setAttr(animWrap.attributes, false, animWrap.isLastFrame); + // If this particular anim is at the last frame end it + if (animWrap.isLastFrame) { + anim.lastFrame(); + } + } + }, + /** + * @private + * Apply all pending attribute changes to their targets + */ + applyPendingAttrs: function() { + var targetArr = this.targetArr, + target, targetId, animWrap, anim, animId; + // Loop through each target + for (targetId in targetArr) { + if (targetArr.hasOwnProperty(targetId)) { + target = targetArr[targetId]; + // Each target could have multiple associated animations, so iterate those + for (animId in target.anims) { + if (target.anims.hasOwnProperty(animId)) { + animWrap = target.anims[animId]; + anim = animWrap.anim; + // If the animation has valid attributes, set them on the target + if (animWrap.attributes && anim.isRunning()) { + //Ext.log(' > applying attributes for anim ', animWrap.id, ', target: ', target.id, ', elapsed: ', animWrap.elapsed); + target.el.setAttr(animWrap.attributes, false, animWrap.isLastFrame); + // If this particular anim is at the last frame end it + if (animWrap.isLastFrame) { + //Ext.log(' running last frame for ', animWrap.id, ', target: ', targetId); + anim.lastFrame(); + } + } + } + } + } + } + }, + clear: function() { + var me = this; + if (me.taskRunner) { + me.taskRunner.stopAll(true); + } + me.targetArr = {}; + me.items.clear(); + me.targets.clear(); + me.clearFxQueue(); + } +}); + +/** + * @class Ext.fx.Animator + * + * This class is used to run keyframe based animations, which follows the CSS3 based animation structure. + * Keyframe animations differ from typical from/to animations in that they offer the ability to specify values + * at various points throughout the animation. + * + * ## Using Keyframes + * + * The {@link #keyframes} option is the most important part of specifying an animation when using this + * class. A key frame is a point in a particular animation. We represent this as a percentage of the + * total animation duration. At each key frame, we can specify the target values at that time. Note that + * you *must* specify the values at 0% and 100%, the start and ending values. There is also a {@link #keyframe} + * event that fires after each key frame is reached. + * + * ## Example + * + * In the example below, we modify the values of the element at each fifth throughout the animation. + * + * @example + * Ext.create('Ext.fx.Animator', { + * target: Ext.getBody().createChild({ + * style: { + * width: '100px', + * height: '100px', + * 'background-color': 'red' + * } + * }), + * duration: 10000, // 10 seconds + * keyframes: { + * 0: { + * opacity: 1, + * backgroundColor: 'FF0000' + * }, + * 20: { + * x: 30, + * opacity: 0.5 + * }, + * 40: { + * x: 130, + * backgroundColor: '0000FF' + * }, + * 60: { + * y: 80, + * opacity: 0.3 + * }, + * 80: { + * width: 200, + * y: 200 + * }, + * 100: { + * opacity: 1, + * backgroundColor: '00FF00' + * } + * } + * }); + */ +Ext.define('Ext.fx.Animator', { + /* Begin Definitions */ + mixins: { + observable: 'Ext.util.Observable' + }, + requires: [ + 'Ext.fx.Manager' + ], + /* End Definitions */ + /** + * @property {Boolean} isAnimator + * `true` in this class to identify an object as an instantiated Animator, or subclass thereof. + */ + isAnimator: true, + /** + * @cfg {Number} duration + * Time in milliseconds for the animation to last. Defaults to 250. + */ + duration: 250, + /** + * @cfg {Number} delay + * Time to delay before starting the animation. Defaults to 0. + */ + delay: 0, + // private used to track a delayed starting time + delayStart: 0, + /** + * @cfg {Boolean} dynamic + * Currently only for Component Animation: Only set a component's outer element size bypassing layouts. Set to true to do full layouts for every frame of the animation. Defaults to false. + */ + dynamic: false, + /** + * @cfg {String} easing + * + * This describes how the intermediate values used during a transition will be calculated. It allows for a transition to change + * speed over its duration. + * + * - backIn + * - backOut + * - bounceIn + * - bounceOut + * - ease + * - easeIn + * - easeOut + * - easeInOut + * - elasticIn + * - elasticOut + * - cubic-bezier(x1, y1, x2, y2) + * + * Note that cubic-bezier will create a custom easing curve following the CSS3 [transition-timing-function][0] + * specification. The four values specify points P1 and P2 of the curve as (x1, y1, x2, y2). All values must + * be in the range [0, 1] or the definition is invalid. + * + * [0]: http://www.w3.org/TR/css3-transitions/#transition-timing-function_tag + */ + easing: 'ease', + /** + * Flag to determine if the animation has started + * @property running + * @type Boolean + */ + running: false, + /** + * Flag to determine if the animation is paused. Only set this to true if you need to + * keep the Anim instance around to be unpaused later; otherwise call {@link #end}. + * @property paused + * @type Boolean + */ + paused: false, + /** + * @private + */ + damper: 1, + /** + * @cfg {Number} iterations + * Number of times to execute the animation. Defaults to 1. + */ + iterations: 1, + /** + * Current iteration the animation is running. + * @property currentIteration + * @type Number + */ + currentIteration: 0, + /** + * Current keyframe step of the animation. + * @property keyframeStep + * @type Number + */ + keyframeStep: 0, + /** + * @private + */ + animKeyFramesRE: /^(from|to|\d+%?)$/, + /** + * @cfg {Ext.fx.target.Target} target + * The Ext.fx.target to apply the animation to. If not specified during initialization, this can be passed to the applyAnimator + * method to apply the same animation to many targets. + */ + /** + * @event beforeanimate + * Fires before the animation starts. A handler can return false to cancel the animation. + * @param {Ext.fx.Animator} this + */ + /** + * @event keyframe + * Fires at each keyframe. + * @param {Ext.fx.Animator} this + * @param {Number} keyframe step number + */ + /** + * @event afteranimate + * Fires when the animation is complete. + * @param {Ext.fx.Animator} this + * @param {Date} startTime + */ + /** + * @cfg {Object} keyframes + * Animation keyframes follow the CSS3 Animation configuration pattern. 'from' is always considered '0%' and 'to' + * is considered '100%'.Every keyframe declaration must have a keyframe rule for 0% and 100%, possibly defined using + * "from" or "to". A keyframe declaration without these keyframe selectors is invalid and will not be available for + * animation. The keyframe declaration for a keyframe rule consists of properties and values. Properties that are unable to + * be animated are ignored in these rules, with the exception of 'easing' which can be changed at each keyframe. For example: +

+keyframes : {
+    '0%': {
+        left: 100
+    },
+    '40%': {
+        left: 150
+    },
+    '60%': {
+        left: 75
+    },
+    '100%': {
+        left: 100
+    }
+}
+ 
+ */ + constructor: function(config) { + var me = this; + config = Ext.apply(me, config || {}); + me.config = config; + me.id = Ext.id(null, 'ext-animator-'); + me.mixins.observable.constructor.call(me, config); + me.timeline = []; + me.createTimeline(me.keyframes); + if (me.target) { + me.applyAnimator(me.target); + Ext.fx.Manager.addAnim(me); + } + }, + /** + * @private + */ + sorter: function(a, b) { + return a.pct - b.pct; + }, + /** + * @private + * Takes the given keyframe configuration object and converts it into an ordered array with the passed attributes per keyframe + * or applying the 'to' configuration to all keyframes. Also calculates the proper animation duration per keyframe. + */ + createTimeline: function(keyframes) { + var me = this, + attrs = [], + to = me.to || {}, + duration = me.duration, + prevMs, ms, i, ln, pct, attr; + for (pct in keyframes) { + if (keyframes.hasOwnProperty(pct) && me.animKeyFramesRE.test(pct)) { + attr = { + attrs: Ext.apply(keyframes[pct], to) + }; + // CSS3 spec allow for from/to to be specified. + if (pct === "from") { + pct = 0; + } else if (pct === "to") { + pct = 100; + } + // convert % values into integers + attr.pct = parseInt(pct, 10); + attrs.push(attr); + } + } + // Sort by pct property + Ext.Array.sort(attrs, me.sorter); + // Only an end + //if (attrs[0].pct) { + // attrs.unshift({pct: 0, attrs: element.attrs}); + //} + ln = attrs.length; + for (i = 0; i < ln; i++) { + prevMs = (attrs[i - 1]) ? duration * (attrs[i - 1].pct / 100) : 0; + ms = duration * (attrs[i].pct / 100); + me.timeline.push({ + duration: ms - prevMs, + attrs: attrs[i].attrs + }); + } + }, + /** + * Applies animation to the Ext.fx.target + * @param {String/Object} target + * @private + */ + applyAnimator: function(target) { + var me = this, + anims = [], + timeline = me.timeline, + ln = timeline.length, + anim, easing, damper, attrs, i; + if (me.fireEvent('beforeanimate', me) !== false) { + for (i = 0; i < ln; i++) { + anim = timeline[i]; + attrs = anim.attrs; + easing = attrs.easing || me.easing; + damper = attrs.damper || me.damper; + delete attrs.easing; + delete attrs.damper; + anim = new Ext.fx.Anim({ + target: target, + easing: easing, + damper: damper, + duration: anim.duration, + paused: true, + to: attrs + }); + anims.push(anim); + } + me.animations = anims; + me.target = anim.target; + for (i = 0; i < ln - 1; i++) { + anim = anims[i]; + anim.nextAnim = anims[i + 1]; + anim.on('afteranimate', function() { + this.nextAnim.paused = false; + }); + anim.on('afteranimate', function() { + this.fireEvent('keyframe', this, ++this.keyframeStep); + }, me); + } + anims[ln - 1].on('afteranimate', function() { + this.lastFrame(); + }, me); + } + }, + /** + * @private + * Fires beforeanimate and sets the running flag. + */ + start: function(startTime) { + var me = this, + delay = me.delay, + delayStart = me.delayStart, + delayDelta; + if (delay) { + if (!delayStart) { + me.delayStart = startTime; + return; + } else { + delayDelta = startTime - delayStart; + if (delayDelta < delay) { + return; + } else { + // Compensate for frame delay; + startTime = new Date(delayStart.getTime() + delay); + } + } + } + if (me.fireEvent('beforeanimate', me) !== false) { + me.startTime = startTime; + me.running = true; + me.animations[me.keyframeStep].paused = false; + } + }, + /** + * @private + * Perform lastFrame cleanup and handle iterations + * @return a hash of the new attributes. + */ + lastFrame: function() { + var me = this, + iter = me.iterations, + iterCount = me.currentIteration; + iterCount++; + if (iterCount < iter) { + me.startTime = new Date(); + me.currentIteration = iterCount; + me.keyframeStep = 0; + me.applyAnimator(me.target); + me.animations[me.keyframeStep].paused = false; + } else { + me.currentIteration = 0; + me.end(); + } + }, + /** + * Fire afteranimate event and end the animation. Usually called automatically when the + * animation reaches its final frame, but can also be called manually to pre-emptively + * stop and destroy the running animation. + */ + end: function() { + var me = this; + me.fireEvent('afteranimate', me, me.startTime, new Date() - me.startTime); + }, + isReady: function() { + return this.paused === false && this.running === false && this.iterations > 0; + }, + isRunning: function() { + // Explicitly return false, we don't want to be run continuously by the manager + return false; + } +}); + +/** + * @private + */ +Ext.define('Ext.fx.CubicBezier', { + /* Begin Definitions */ + singleton: true, + /* End Definitions */ + cubicBezierAtTime: function(t, p1x, p1y, p2x, p2y, duration) { + var cx = 3 * p1x, + bx = 3 * (p2x - p1x) - cx, + ax = 1 - cx - bx, + cy = 3 * p1y, + by = 3 * (p2y - p1y) - cy, + ay = 1 - cy - by; + function sampleCurveX(t) { + return ((ax * t + bx) * t + cx) * t; + } + function solve(x, epsilon) { + var t = solveCurveX(x, epsilon); + return ((ay * t + by) * t + cy) * t; + } + function solveCurveX(x, epsilon) { + var t0, t1, t2, x2, d2, i; + for (t2 = x , i = 0; i < 8; i++) { + x2 = sampleCurveX(t2) - x; + if (Math.abs(x2) < epsilon) { + return t2; + } + d2 = (3 * ax * t2 + 2 * bx) * t2 + cx; + if (Math.abs(d2) < 1.0E-6) { + break; + } + t2 = t2 - x2 / d2; + } + t0 = 0; + t1 = 1; + t2 = x; + if (t2 < t0) { + return t0; + } + if (t2 > t1) { + return t1; + } + while (t0 < t1) { + x2 = sampleCurveX(t2); + if (Math.abs(x2 - x) < epsilon) { + return t2; + } + if (x > x2) { + t0 = t2; + } else { + t1 = t2; + } + t2 = (t1 - t0) / 2 + t0; + } + return t2; + } + return solve(t, 1 / (200 * duration)); + }, + cubicBezier: function(x1, y1, x2, y2) { + var fn = function(pos) { + return Ext.fx.CubicBezier.cubicBezierAtTime(pos, x1, y1, x2, y2, 1); + }; + fn.toCSS3 = function() { + return 'cubic-bezier(' + [ + x1, + y1, + x2, + y2 + ].join(',') + ')'; + }; + fn.reverse = function() { + return Ext.fx.CubicBezier.cubicBezier(1 - x2, 1 - y2, 1 - x1, 1 - y1); + }; + return fn; + } +}); + +/** + * This class contains a series of function definitions used to modify values during an animation. + * They describe how the intermediate values used during a transition will be calculated. It allows for a transition to change + * speed over its duration. The following options are available: + * + * - linear The default easing type + * - backIn + * - backOut + * - bounceIn + * - bounceOut + * - ease + * - easeIn + * - easeOut + * - easeInOut + * - elasticIn + * - elasticOut + * - cubic-bezier(x1, y1, x2, y2) + * + * Note that cubic-bezier will create a custom easing curve following the CSS3 [transition-timing-function][0] + * specification. The four values specify points P1 and P2 of the curve as (x1, y1, x2, y2). All values must + * be in the range [0, 1] or the definition is invalid. + * + * [0]: http://www.w3.org/TR/css3-transitions/#transition-timing-function_tag + * + * @singleton + */ +Ext.define('Ext.fx.Easing', function() { + var math = Math, + pi = math.PI, + pow = math.pow, + sin = math.sin, + sqrt = math.sqrt, + abs = math.abs, + backInSeed = 1.70158; + return { + requires: [ + 'Ext.fx.CubicBezier' + ], + singleton: true, + linear: Ext.identityFn, + ease: function(n) { + var q = 0.07813 - n / 2, + Q = sqrt(0.0066 + q * q), + x = Q - q, + X = pow(abs(x), 1 / 3) * (x < 0 ? -1 : 1), + y = -Q - q, + Y = pow(abs(y), 1 / 3) * (y < 0 ? -1 : 1), + t = X + Y + 0.25; + return pow(1 - t, 2) * 3 * t * 0.1 + (1 - t) * 3 * t * t + t * t * t; + }, + easeIn: function(n) { + return pow(n, 1.7); + }, + easeOut: function(n) { + return pow(n, 0.48); + }, + easeInOut: function(n) { + var q = 0.48 - n / 1.04, + Q = sqrt(0.1734 + q * q), + x = Q - q, + X = pow(abs(x), 1 / 3) * (x < 0 ? -1 : 1), + y = -Q - q, + Y = pow(abs(y), 1 / 3) * (y < 0 ? -1 : 1), + t = X + Y + 0.5; + return (1 - t) * 3 * t * t + t * t * t; + }, + backIn: function(n) { + return n * n * ((backInSeed + 1) * n - backInSeed); + }, + backOut: function(n) { + n = n - 1; + return n * n * ((backInSeed + 1) * n + backInSeed) + 1; + }, + elasticIn: function(n) { + if (n === 0 || n === 1) { + return n; + } + var p = 0.3, + s = p / 4; + return pow(2, -10 * n) * sin((n - s) * (2 * pi) / p) + 1; + }, + elasticOut: function(n) { + return 1 - Ext.fx.Easing.elasticIn(1 - n); + }, + bounceIn: function(n) { + return 1 - Ext.fx.Easing.bounceOut(1 - n); + }, + bounceOut: function(n) { + var s = 7.5625, + p = 2.75, + l; + if (n < (1 / p)) { + l = s * n * n; + } else { + if (n < (2 / p)) { + n -= (1.5 / p); + l = s * n * n + 0.75; + } else { + if (n < (2.5 / p)) { + n -= (2.25 / p); + l = s * n * n + 0.9375; + } else { + n -= (2.625 / p); + l = s * n * n + 0.984375; + } + } + } + return l; + } + }; +}, function(me) { + // since we are a singleton, we are passed the instance (not the class) + var Easing = me.self, + proto = Easing.prototype; + Easing.addMembers({ + 'back-in': proto.backIn, + 'back-out': proto.backOut, + 'ease-in': proto.easeIn, + 'ease-out': proto.easeOut, + 'elastic-in': proto.elasticIn, + 'elastic-out': proto.elasticOut, + 'bounce-in': proto.bounceIn, + 'bounce-out': proto.bounceOut, + 'ease-in-out': proto.easeInOut + }); +}); + +/** + * @class Ext.fx.DrawPath + * Provides SVG Paths handling functions. Copied from Ext.draw.Draw in ExtJs 4.2 in order + * to break the dependencies on parsePathString() and interpolatePaths() in PropertyHandler.js + * @private + */ +Ext.define('Ext.fx.DrawPath', { + /* Begin Definitions */ + singleton: true, + /* End Definitions */ + pathToStringRE: /,?([achlmqrstvxz]),?/gi, + pathCommandRE: /([achlmqstvz])[\s,]*((-?\d*\.?\d*(?:e[-+]?\d+)?\s*,?\s*)+)/ig, + pathValuesRE: /(-?\d*\.?\d*(?:e[-+]?\d+)?)\s*,?\s*/ig, + stopsRE: /^(\d+%?)$/, + radian: Math.PI / 180, + is: function(o, type) { + type = String(type).toLowerCase(); + return (type == "object" && o === Object(o)) || (type == "undefined" && typeof o == type) || (type == "null" && o === null) || (type == "array" && Array.isArray && Array.isArray(o)) || (Object.prototype.toString.call(o).toLowerCase().slice(8, -1)) == type; + }, + // To be deprecated, converts itself (an arrayPath) to a proper SVG path string + path2string: function() { + return this.join(",").replace(Ext.fx.DrawPath.pathToStringRE, "$1"); + }, + // Convert the passed arrayPath to a proper SVG path string (d attribute) + pathToString: function(arrayPath) { + return arrayPath.join(",").replace(Ext.fx.DrawPath.pathToStringRE, "$1"); + }, + parsePathString: function(pathString) { + if (!pathString) { + return null; + } + var paramCounts = { + a: 7, + c: 6, + h: 1, + l: 2, + m: 2, + q: 4, + s: 4, + t: 2, + v: 1, + z: 0 + }, + data = [], + me = this; + if (me.is(pathString, "array") && me.is(pathString[0], "array")) { + // rough assumption + data = me.pathClone(pathString); + } + if (!data.length) { + String(pathString).replace(me.pathCommandRE, function(a, b, c) { + var params = [], + name = b.toLowerCase(); + c.replace(me.pathValuesRE, function(a, b) { + if (b) { + params.push(+b); + } + }); + if (name == "m" && params.length > 2) { + data.push([ + b + ].concat(Ext.Array.splice(params, 0, 2))); + name = "l"; + b = (b == "m") ? "l" : "L"; + } + while (params.length >= paramCounts[name]) { + data.push([ + b + ].concat(Ext.Array.splice(params, 0, paramCounts[name]))); + if (!paramCounts[name]) { + break; + } + } + }); + } + data.toString = me.path2string; + return data; + }, + pathClone: function(pathArray) { + var res = [], + j, jj, i, ii; + if (!this.is(pathArray, "array") || !this.is(pathArray && pathArray[0], "array")) { + // rough assumption + pathArray = this.parsePathString(pathArray); + } + for (i = 0 , ii = pathArray.length; i < ii; i++) { + res[i] = []; + for (j = 0 , jj = pathArray[i].length; j < jj; j++) { + res[i][j] = pathArray[i][j]; + } + } + res.toString = this.path2string; + return res; + }, + pathToAbsolute: function(pathArray) { + if (!this.is(pathArray, "array") || !this.is(pathArray && pathArray[0], "array")) { + // rough assumption + pathArray = this.parsePathString(pathArray); + } + var res = [], + x = 0, + y = 0, + mx = 0, + my = 0, + i = 0, + ln = pathArray.length, + r, pathSegment, j, ln2; + // MoveTo initial x/y position + if (ln && pathArray[0][0] == "M") { + x = +pathArray[0][1]; + y = +pathArray[0][2]; + mx = x; + my = y; + i++; + res[0] = [ + "M", + x, + y + ]; + } + for (; i < ln; i++) { + r = res[i] = []; + pathSegment = pathArray[i]; + if (pathSegment[0] != pathSegment[0].toUpperCase()) { + r[0] = pathSegment[0].toUpperCase(); + switch (r[0]) { + // Elliptical Arc + case "A": + r[1] = pathSegment[1]; + r[2] = pathSegment[2]; + r[3] = pathSegment[3]; + r[4] = pathSegment[4]; + r[5] = pathSegment[5]; + r[6] = +(pathSegment[6] + x); + r[7] = +(pathSegment[7] + y); + break; + // Vertical LineTo + case "V": + r[1] = +pathSegment[1] + y; + break; + // Horizontal LineTo + case "H": + r[1] = +pathSegment[1] + x; + break; + case "M": + // MoveTo + mx = +pathSegment[1] + x; + my = +pathSegment[2] + y; + // fall; + default: + j = 1; + ln2 = pathSegment.length; + for (; j < ln2; j++) { + r[j] = +pathSegment[j] + ((j % 2) ? x : y); + }; + } + } else { + j = 0; + ln2 = pathSegment.length; + for (; j < ln2; j++) { + res[i][j] = pathSegment[j]; + } + } + switch (r[0]) { + // ClosePath + case "Z": + x = mx; + y = my; + break; + // Horizontal LineTo + case "H": + x = r[1]; + break; + // Vertical LineTo + case "V": + y = r[1]; + break; + // MoveTo + case "M": + pathSegment = res[i]; + ln2 = pathSegment.length; + mx = pathSegment[ln2 - 2]; + my = pathSegment[ln2 - 1]; + // fall; + default: + pathSegment = res[i]; + ln2 = pathSegment.length; + x = pathSegment[ln2 - 2]; + y = pathSegment[ln2 - 1]; + } + } + res.toString = this.path2string; + return res; + }, + interpolatePaths: function(path, path2) { + var me = this, + p = me.pathToAbsolute(path), + p2 = me.pathToAbsolute(path2), + attrs = { + x: 0, + y: 0, + bx: 0, + by: 0, + X: 0, + Y: 0, + qx: null, + qy: null + }, + attrs2 = { + x: 0, + y: 0, + bx: 0, + by: 0, + X: 0, + Y: 0, + qx: null, + qy: null + }, + fixArc = function(pp, i) { + if (pp[i].length > 7) { + pp[i].shift(); + var pi = pp[i]; + while (pi.length) { + Ext.Array.splice(pp, i++, 0, [ + "C" + ].concat(Ext.Array.splice(pi, 0, 6))); + } + Ext.Array.erase(pp, i, 1); + ii = Math.max(p.length, p2.length || 0); + } + }, + fixM = function(path1, path2, a1, a2, i) { + if (path1 && path2 && path1[i][0] == "M" && path2[i][0] != "M") { + Ext.Array.splice(path2, i, 0, [ + "M", + a2.x, + a2.y + ]); + a1.bx = 0; + a1.by = 0; + a1.x = path1[i][1]; + a1.y = path1[i][2]; + ii = Math.max(p.length, p2.length || 0); + } + }, + i, ii, seg, seg2, seglen, seg2len; + for (i = 0 , ii = Math.max(p.length, p2.length || 0); i < ii; i++) { + p[i] = me.command2curve(p[i], attrs); + fixArc(p, i); + (p2[i] = me.command2curve(p2[i], attrs2)); + fixArc(p2, i); + fixM(p, p2, attrs, attrs2, i); + fixM(p2, p, attrs2, attrs, i); + seg = p[i]; + seg2 = p2[i]; + seglen = seg.length; + seg2len = seg2.length; + attrs.x = seg[seglen - 2]; + attrs.y = seg[seglen - 1]; + attrs.bx = parseFloat(seg[seglen - 4]) || attrs.x; + attrs.by = parseFloat(seg[seglen - 3]) || attrs.y; + attrs2.bx = (parseFloat(seg2[seg2len - 4]) || attrs2.x); + attrs2.by = (parseFloat(seg2[seg2len - 3]) || attrs2.y); + attrs2.x = seg2[seg2len - 2]; + attrs2.y = seg2[seg2len - 1]; + } + return [ + p, + p2 + ]; + }, + //Returns any path command as a curveto command based on the attrs passed + command2curve: function(pathCommand, d) { + var me = this; + if (!pathCommand) { + return [ + "C", + d.x, + d.y, + d.x, + d.y, + d.x, + d.y + ]; + } + if (pathCommand[0] != "T" && pathCommand[0] != "Q") { + d.qx = d.qy = null; + } + switch (pathCommand[0]) { + case "M": + d.X = pathCommand[1]; + d.Y = pathCommand[2]; + break; + case "A": + pathCommand = [ + "C" + ].concat(me.arc2curve.apply(me, [ + d.x, + d.y + ].concat(pathCommand.slice(1)))); + break; + case "S": + pathCommand = [ + "C", + d.x + (d.x - (d.bx || d.x)), + d.y + (d.y - (d.by || d.y)) + ].concat(pathCommand.slice(1)); + break; + case "T": + d.qx = d.x + (d.x - (d.qx || d.x)); + d.qy = d.y + (d.y - (d.qy || d.y)); + pathCommand = [ + "C" + ].concat(me.quadratic2curve(d.x, d.y, d.qx, d.qy, pathCommand[1], pathCommand[2])); + break; + case "Q": + d.qx = pathCommand[1]; + d.qy = pathCommand[2]; + pathCommand = [ + "C" + ].concat(me.quadratic2curve(d.x, d.y, pathCommand[1], pathCommand[2], pathCommand[3], pathCommand[4])); + break; + case "L": + pathCommand = [ + "C" + ].concat(d.x, d.y, pathCommand[1], pathCommand[2], pathCommand[1], pathCommand[2]); + break; + case "H": + pathCommand = [ + "C" + ].concat(d.x, d.y, pathCommand[1], d.y, pathCommand[1], d.y); + break; + case "V": + pathCommand = [ + "C" + ].concat(d.x, d.y, d.x, pathCommand[1], d.x, pathCommand[1]); + break; + case "Z": + pathCommand = [ + "C" + ].concat(d.x, d.y, d.X, d.Y, d.X, d.Y); + break; + } + return pathCommand; + }, + quadratic2curve: function(x1, y1, ax, ay, x2, y2) { + var _13 = 1 / 3, + _23 = 2 / 3; + return [ + _13 * x1 + _23 * ax, + _13 * y1 + _23 * ay, + _13 * x2 + _23 * ax, + _13 * y2 + _23 * ay, + x2, + y2 + ]; + }, + rotate: function(x, y, rad) { + var cos = Math.cos(rad), + sin = Math.sin(rad), + X = x * cos - y * sin, + Y = x * sin + y * cos; + return { + x: X, + y: Y + }; + }, + arc2curve: function(x1, y1, rx, ry, angle, large_arc_flag, sweep_flag, x2, y2, recursive) { + // for more information of where this Math came from visit: + // http://www.w3.org/TR/SVG11/implnote.html#ArcImplementationNotes + var me = this, + PI = Math.PI, + radian = me.radian, + _120 = PI * 120 / 180, + rad = radian * (+angle || 0), + res = [], + math = Math, + mcos = math.cos, + msin = math.sin, + msqrt = math.sqrt, + mabs = math.abs, + masin = math.asin, + xy, x, y, h, rx2, ry2, k, cx, cy, f1, f2, df, c1, s1, c2, s2, t, hx, hy, m1, m2, m3, m4, newres, i, ln, f2old, x2old, y2old; + if (!recursive) { + xy = me.rotate(x1, y1, -rad); + x1 = xy.x; + y1 = xy.y; + xy = me.rotate(x2, y2, -rad); + x2 = xy.x; + y2 = xy.y; + x = (x1 - x2) / 2; + y = (y1 - y2) / 2; + h = (x * x) / (rx * rx) + (y * y) / (ry * ry); + if (h > 1) { + h = msqrt(h); + rx = h * rx; + ry = h * ry; + } + rx2 = rx * rx; + ry2 = ry * ry; + k = (large_arc_flag == sweep_flag ? -1 : 1) * msqrt(mabs((rx2 * ry2 - rx2 * y * y - ry2 * x * x) / (rx2 * y * y + ry2 * x * x))); + cx = k * rx * y / ry + (x1 + x2) / 2; + cy = k * -ry * x / rx + (y1 + y2) / 2; + f1 = masin(((y1 - cy) / ry).toFixed(7)); + f2 = masin(((y2 - cy) / ry).toFixed(7)); + f1 = x1 < cx ? PI - f1 : f1; + f2 = x2 < cx ? PI - f2 : f2; + if (f1 < 0) { + f1 = PI * 2 + f1; + } + if (f2 < 0) { + f2 = PI * 2 + f2; + } + if (sweep_flag && f1 > f2) { + f1 = f1 - PI * 2; + } + if (!sweep_flag && f2 > f1) { + f2 = f2 - PI * 2; + } + } else { + f1 = recursive[0]; + f2 = recursive[1]; + cx = recursive[2]; + cy = recursive[3]; + } + df = f2 - f1; + if (mabs(df) > _120) { + f2old = f2; + x2old = x2; + y2old = y2; + f2 = f1 + _120 * (sweep_flag && f2 > f1 ? 1 : -1); + x2 = cx + rx * mcos(f2); + y2 = cy + ry * msin(f2); + res = me.arc2curve(x2, y2, rx, ry, angle, 0, sweep_flag, x2old, y2old, [ + f2, + f2old, + cx, + cy + ]); + } + df = f2 - f1; + c1 = mcos(f1); + s1 = msin(f1); + c2 = mcos(f2); + s2 = msin(f2); + t = math.tan(df / 4); + hx = 4 / 3 * rx * t; + hy = 4 / 3 * ry * t; + m1 = [ + x1, + y1 + ]; + m2 = [ + x1 + hx * s1, + y1 - hy * c1 + ]; + m3 = [ + x2 + hx * s2, + y2 - hy * c2 + ]; + m4 = [ + x2, + y2 + ]; + m2[0] = 2 * m1[0] - m2[0]; + m2[1] = 2 * m1[1] - m2[1]; + if (recursive) { + return [ + m2, + m3, + m4 + ].concat(res); + } else { + res = [ + m2, + m3, + m4 + ].concat(res).join().split(","); + newres = []; + ln = res.length; + for (i = 0; i < ln; i++) { + newres[i] = i % 2 ? me.rotate(res[i - 1], res[i], rad).y : me.rotate(res[i], res[i + 1], rad).x; + } + return newres; + } + } +}); + +/** + * @private + */ +Ext.define('Ext.fx.PropertyHandler', { + /* Begin Definitions */ + requires: [ + 'Ext.fx.DrawPath' + ], + statics: { + defaultHandler: { + pixelDefaultsRE: /width|height|top$|bottom$|left$|right$/i, + unitRE: /^(-?\d*\.?\d*){1}(em|ex|px|in|cm|mm|pt|pc|%)*$/, + scrollRE: /^scroll/i, + computeDelta: function(from, end, damper, initial, attr) { + damper = (typeof damper == 'number') ? damper : 1; + var unitRE = this.unitRE, + match = unitRE.exec(from), + start, units; + if (match) { + from = match[1]; + units = match[2]; + if (!this.scrollRE.test(attr) && !units && this.pixelDefaultsRE.test(attr)) { + units = 'px'; + } + } + from = +from || 0; + match = unitRE.exec(end); + if (match) { + end = match[1]; + units = match[2] || units; + } + end = +end || 0; + start = (initial != null) ? initial : from; + return { + from: from, + delta: (end - start) * damper, + units: units + }; + }, + get: function(from, end, damper, initialFrom, attr) { + var ln = from.length, + out = [], + i, initial, res, j, len; + for (i = 0; i < ln; i++) { + if (initialFrom) { + initial = initialFrom[i][1].from; + } + if (Ext.isArray(from[i][1]) && Ext.isArray(end)) { + res = []; + j = 0; + len = from[i][1].length; + for (; j < len; j++) { + res.push(this.computeDelta(from[i][1][j], end[j], damper, initial, attr)); + } + out.push([ + from[i][0], + res + ]); + } else { + out.push([ + from[i][0], + this.computeDelta(from[i][1], end, damper, initial, attr) + ]); + } + } + return out; + }, + set: function(values, easing) { + var ln = values.length, + out = [], + i, val, res, len, j; + for (i = 0; i < ln; i++) { + val = values[i][1]; + if (Ext.isArray(val)) { + res = []; + j = 0; + len = val.length; + for (; j < len; j++) { + res.push(val[j].from + val[j].delta * easing + (val[j].units || 0)); + } + out.push([ + values[i][0], + res + ]); + } else { + out.push([ + values[i][0], + val.from + val.delta * easing + (val.units || 0) + ]); + } + } + return out; + } + }, + stringHandler: { + computeDelta: function(from, end, damper, initial, attr) { + return { + from: from, + delta: end + }; + }, + get: function(from, end, damper, initialFrom, attr) { + var ln = from.length, + out = [], + i, initial; + for (i = 0; i < ln; i++) { + out.push([ + from[i][0], + this.computeDelta(from[i][1], end, damper, initial, attr) + ]); + } + return out; + }, + set: function(values, easing) { + var ln = values.length, + out = [], + i, val; + for (i = 0; i < ln; i++) { + val = values[i][1]; + out.push([ + values[i][0], + val.delta + ]); + } + return out; + } + }, + color: { + rgbRE: /^rgb\(([0-9]+)\s*,\s*([0-9]+)\s*,\s*([0-9]+)\)$/i, + hexRE: /^#?([0-9A-F]{2})([0-9A-F]{2})([0-9A-F]{2})$/i, + hex3RE: /^#?([0-9A-F]{1})([0-9A-F]{1})([0-9A-F]{1})$/i, + parseColor: function(color, damper) { + damper = (typeof damper == 'number') ? damper : 1; + var out = false, + reList = [ + this.hexRE, + this.rgbRE, + this.hex3RE + ], + length = reList.length, + match, base, re, i; + for (i = 0; i < length; i++) { + re = reList[i]; + base = (i % 2 === 0) ? 16 : 10; + match = re.exec(color); + if (match && match.length === 4) { + if (i === 2) { + match[1] += match[1]; + match[2] += match[2]; + match[3] += match[3]; + } + out = { + red: parseInt(match[1], base), + green: parseInt(match[2], base), + blue: parseInt(match[3], base) + }; + break; + } + } + return out || color; + }, + computeDelta: function(from, end, damper, initial) { + from = this.parseColor(from); + end = this.parseColor(end, damper); + var start = initial ? initial : from, + tfrom = typeof start, + tend = typeof end; + //Extra check for when the color string is not recognized. + if (tfrom === 'string' || tfrom === 'undefined' || tend === 'string' || tend === 'undefined') { + return end || start; + } + return { + from: from, + delta: { + red: Math.round((end.red - start.red) * damper), + green: Math.round((end.green - start.green) * damper), + blue: Math.round((end.blue - start.blue) * damper) + } + }; + }, + get: function(start, end, damper, initialFrom) { + var ln = start.length, + out = [], + i, initial; + for (i = 0; i < ln; i++) { + if (initialFrom) { + initial = initialFrom[i][1].from; + } + out.push([ + start[i][0], + this.computeDelta(start[i][1], end, damper, initial) + ]); + } + return out; + }, + set: function(values, easing) { + var ln = values.length, + out = [], + i, val, parsedString, from, delta; + for (i = 0; i < ln; i++) { + val = values[i][1]; + if (val) { + from = val.from; + delta = val.delta; + //multiple checks to reformat the color if it can't recognized by computeDelta. + val = (typeof val === 'object' && 'red' in val) ? 'rgb(' + val.red + ', ' + val.green + ', ' + val.blue + ')' : val; + val = (typeof val === 'object' && val.length) ? val[0] : val; + if (typeof val === 'undefined') { + return []; + } + parsedString = typeof val === 'string' ? val : 'rgb(' + [ + (from.red + Math.round(delta.red * easing)) % 256, + (from.green + Math.round(delta.green * easing)) % 256, + (from.blue + Math.round(delta.blue * easing)) % 256 + ].join(',') + ')'; + out.push([ + values[i][0], + parsedString + ]); + } + } + return out; + } + }, + object: { + interpolate: function(prop, damper) { + damper = (typeof damper === 'number') ? damper : 1; + var out = {}, + p; + for (p in prop) { + out[p] = parseFloat(prop[p]) * damper; + } + return out; + }, + computeDelta: function(from, end, damper, initial) { + from = this.interpolate(from); + end = this.interpolate(end, damper); + var start = initial ? initial : from, + delta = {}, + p; + for (p in end) { + delta[p] = end[p] - start[p]; + } + return { + from: from, + delta: delta + }; + }, + get: function(start, end, damper, initialFrom) { + var ln = start.length, + out = [], + i, initial; + for (i = 0; i < ln; i++) { + if (initialFrom) { + initial = initialFrom[i][1].from; + } + out.push([ + start[i][0], + this.computeDelta(start[i][1], end, damper, initial) + ]); + } + return out; + }, + set: function(values, easing) { + var ln = values.length, + out = [], + outObject = {}, + i, from, delta, val, p; + for (i = 0; i < ln; i++) { + val = values[i][1]; + from = val.from; + delta = val.delta; + for (p in from) { + outObject[p] = from[p] + delta[p] * easing; + } + out.push([ + values[i][0], + outObject + ]); + } + return out; + } + }, + path: { + computeDelta: function(from, end, damper, initial) { + damper = (typeof damper === 'number') ? damper : 1; + var start; + from = +from || 0; + end = +end || 0; + start = (initial != null) ? initial : from; + return { + from: from, + delta: (end - start) * damper + }; + }, + forcePath: function(path) { + if (!Ext.isArray(path) && !Ext.isArray(path[0])) { + path = Ext.fx.DrawPath.parsePathString(path); + } + return path; + }, + get: function(start, end, damper, initialFrom) { + var endPath = this.forcePath(end), + out = [], + startLn = start.length, + startPathLn, pointsLn, i, deltaPath, initial, j, k, path, startPath; + for (i = 0; i < startLn; i++) { + startPath = this.forcePath(start[i][1]); + deltaPath = Ext.fx.DrawPath.interpolatePaths(startPath, endPath); + startPath = deltaPath[0]; + endPath = deltaPath[1]; + startPathLn = startPath.length; + path = []; + for (j = 0; j < startPathLn; j++) { + deltaPath = [ + startPath[j][0] + ]; + pointsLn = startPath[j].length; + for (k = 1; k < pointsLn; k++) { + initial = initialFrom && initialFrom[0][1][j][k].from; + deltaPath.push(this.computeDelta(startPath[j][k], endPath[j][k], damper, initial)); + } + path.push(deltaPath); + } + out.push([ + start[i][0], + path + ]); + } + return out; + }, + set: function(values, easing) { + var ln = values.length, + out = [], + i, j, k, newPath, calcPath, deltaPath, deltaPathLn, pointsLn; + for (i = 0; i < ln; i++) { + deltaPath = values[i][1]; + newPath = []; + deltaPathLn = deltaPath.length; + for (j = 0; j < deltaPathLn; j++) { + calcPath = [ + deltaPath[j][0] + ]; + pointsLn = deltaPath[j].length; + for (k = 1; k < pointsLn; k++) { + calcPath.push(deltaPath[j][k].from + deltaPath[j][k].delta * easing); + } + newPath.push(calcPath.join(',')); + } + out.push([ + values[i][0], + newPath.join(',') + ]); + } + return out; + } + } + } +}, /* End Definitions */ +function() { + //set color properties to color interpolator + var props = [ + 'outlineColor', + 'backgroundColor', + 'borderColor', + 'borderTopColor', + 'borderRightColor', + 'borderBottomColor', + 'borderLeftColor', + 'fill', + 'stroke' + ], + length = props.length, + i = 0, + prop; + for (; i < length; i++) { + prop = props[i]; + this[prop] = this.color; + } + //set string properties to string + props = [ + 'cursor' + ]; + length = props.length; + i = 0; + for (; i < length; i++) { + prop = props[i]; + this[prop] = this.stringHandler; + } +}); + +/** + * This class manages animation for a specific {@link #target}. The animation allows + * animation of various properties on the target, such as size, position, color and others. + * + * ## Starting Conditions + * + * The starting conditions for the animation are provided by the {@link #from} configuration. + * Any/all of the properties in the {@link #from} configuration can be specified. If a particular + * property is not defined, the starting value for that property will be read directly from the target. + * + * ## End Conditions + * + * The ending conditions for the animation are provided by the {@link #to} configuration. These mark + * the final values once the animations has finished. The values in the {@link #from} can mirror + * those in the {@link #to} configuration to provide a starting point. + * + * ## Other Options + * + * - {@link #duration}: Specifies the time period of the animation. + * - {@link #easing}: Specifies the easing of the animation. + * - {@link #iterations}: Allows the animation to repeat a number of times. + * - {@link #alternate}: Used in conjunction with {@link #iterations}, reverses the direction every second iteration. + * + * ## Example Code + * + * @example + * var myComponent = Ext.create('Ext.Component', { + * renderTo: document.body, + * width: 200, + * height: 200, + * style: 'border: 1px solid red;' + * }); + * + * Ext.create('Ext.fx.Anim', { + * target: myComponent, + * duration: 1000, + * from: { + * width: 400 //starting width 400 + * }, + * to: { + * width: 300, //end width 300 + * height: 300 // end height 300 + * } + * }); + */ +Ext.define('Ext.fx.Anim', { + /* Begin Definitions */ + mixins: { + observable: 'Ext.util.Observable' + }, + requires: [ + 'Ext.fx.Manager', + 'Ext.fx.Animator', + 'Ext.fx.Easing', + 'Ext.fx.CubicBezier', + 'Ext.fx.PropertyHandler' + ], + /* End Definitions */ + /** + * @property {Boolean} isAnimation + * `true` in this class to identify an object as an instantiated Anim, or subclass thereof. + */ + isAnimation: true, + /** + * @cfg {Function/String} callback + * A function to be run after the animation has completed. + * @controllable + */ + /** + * @cfg {Object} scope + * The scope that the {@link #callback} function will be called with + */ + /** + * @cfg {Boolean} remove + * `true` to remove the target when the animation is complete, using the appropriate removal + * method for the target. For example, a component will be destroyed, elements will be removed. + */ + /** + * @cfg {Number} duration + * Time in milliseconds for a single animation to last. If the {@link #iterations} property is + * specified, then each animate will take the same duration for each iteration. + */ + duration: 250, + /** + * @cfg {Number} delay + * Time to delay before starting the animation. + */ + delay: 0, + /** + * @private + * Tracks a delayed starting time + */ + delayStart: 0, + /** + * @cfg {Boolean} dynamic + * Currently only for Component Animation: Only set a component's outer element size bypassing layouts. + * Set to true to do full layouts for every frame of the animation. + */ + dynamic: false, + /** + * @cfg {String} easing + * This describes how the intermediate values used during a transition will be calculated. + * It allows for a transition to change speed over its duration. + * + * - backIn + * - backOut + * - bounceIn + * - bounceOut + * - ease + * - easeIn + * - easeOut + * - easeInOut + * - elasticIn + * - elasticOut + * - cubic-bezier(x1, y1, x2, y2) + * + * Note that cubic-bezier will create a custom easing curve following the CSS3 [transition-timing-function][0] + * specification. The four values specify points P1 and P2 of the curve as (x1, y1, x2, y2). All values must + * be in the range [0, 1] or the definition is invalid. + * + * [0]: http://www.w3.org/TR/css3-transitions/#transition-timing-function_tag + */ + easing: 'ease', + /** + * @cfg {Object} keyframes + * Animation keyframes follow the CSS3 Animation configuration pattern. 'from' is always considered '0%' and 'to' + * is considered '100%'. **Every keyframe declaration must have a keyframe rule for 0% and 100%, possibly defined using + * "from" or "to".** A keyframe declaration without these keyframe selectors is invalid and will not be available for + * animation. The keyframe declaration for a keyframe rule consists of properties and values. Properties that are unable to + * be animated are ignored in these rules, with the exception of 'easing' which can be changed at each keyframe. For example: + * + * keyframes : { + * '0%': { + * left: 100 + * }, + * '40%': { + * left: 150 + * }, + * '60%': { + * left: 75 + * }, + * '100%': { + * left: 100 + * } + * } + */ + /** + * @private + */ + damper: 1, + /** + * @private + */ + bezierRE: /^(?:cubic-)?bezier\(([^,]+),([^,]+),([^,]+),([^\)]+)\)/, + /** + * Run the animation from the end to the beginning + * Defaults to false. + * @cfg {Boolean} reverse + */ + reverse: false, + /** + * Flag to determine if the animation has started + * @property running + * @type Boolean + */ + running: false, + /** + * Flag to determine if the animation is paused. Only set this to true if you need to + * keep the Anim instance around to be un-paused later; otherwise call {@link #end}. + * @property paused + * @type Boolean + */ + paused: false, + /** + * @cfg {Number} iterations + * Number of times to execute the animation. + */ + iterations: 1, + /** + * @cfg {Boolean} autoEnd + * `true` to immediately force this animation to its final state. This can be useful + * in cases where you want the final effect of an animation, but need to the actual + * animation dynamically. Also see the {@link #jumpToEnd} method. + */ + autoEnd: false, + /** + * @cfg {Boolean} alternate + * Used in conjunction with iterations to reverse the animation each time an iteration completes. + */ + alternate: false, + /** + * Current iteration the animation is running. + * @property currentIteration + * @type Number + */ + currentIteration: 0, + /** + * Starting time of the animation. + * @property startTime + * @type Date + */ + startTime: 0, + /** + * Contains a cache of the interpolators to be used. + * @private + * @property propHandlers + * @type Object + */ + /** + * @cfg {String/Object} target + * The {@link Ext.fx.target.Target} to apply the animation to. This should only be specified when creating an Ext.fx.Anim directly. + * The target does not need to be a {@link Ext.fx.target.Target} instance, it can be the underlying object. For example, you can + * pass a Component, Element or Sprite as the target and the Anim will create the appropriate {@link Ext.fx.target.Target} object + * automatically. + */ + /** + * @cfg {Object} from + * An object containing property/value pairs for the beginning of the animation. If not specified, the current state of the + * Ext.fx.target will be used. For example: + * + * from: { + * opacity: 0, // Transparent + * color: '#ffffff', // White + * left: 0 + * } + * + */ + /** + * @cfg {Object} to (required) + * An object containing property/value pairs for the end of the animation. For example: + * + * to: { + * opacity: 1, // Opaque + * color: '#00ff00', // Green + * left: 500 + * } + * + */ + /** + * @private + */ + frameCount: 0, + /** + * @event beforeanimate + * Fires before the animation starts. A handler can return false to cancel the animation. + * @param {Ext.fx.Anim} this + */ + /** + * @event afteranimate + * Fires when the animation is complete. + * @param {Ext.fx.Anim} this + * @param {Date} startTime + */ + /** + * @event lastframe + * Fires when the animation's last frame has been set. + * @param {Ext.fx.Anim} this + * @param {Date} startTime + */ + /** + * @private + */ + constructor: function(config) { + var me = this, + curve; + config = config || {}; + // If keyframes are passed, they really want an Animator instead. + if (config.keyframes) { + return new Ext.fx.Animator(config); + } + Ext.apply(me, config); + if (me.from === undefined) { + me.from = {}; + } + me.propHandlers = {}; + me.config = config; + me.target = Ext.fx.Manager.createTarget(me.target); + me.easingFn = Ext.fx.Easing[me.easing]; + me.target.dynamic = me.dynamic; + // If not a pre-defined curve, try a cubic-bezier + if (!me.easingFn) { + me.easingFn = String(me.easing).match(me.bezierRE); + if (me.easingFn && me.easingFn.length === 5) { + curve = me.easingFn; + me.easingFn = Ext.fx.CubicBezier.cubicBezier(+curve[1], +curve[2], +curve[3], +curve[4]); + } + } + me.id = Ext.id(null, 'ext-anim-'); + me.mixins.observable.constructor.call(me); + Ext.fx.Manager.addAnim(me); + if (config.autoEnd) { + me.running = true; + me.jumpToEnd(); + } + }, + /** + * @private + * Helper to the target + */ + setAttr: function(attr, value) { + return Ext.fx.Manager.items.get(this.id).setAttr(this.target, attr, value); + }, + /** + * @private + * Set up the initial currentAttrs hash. + */ + initAttrs: function() { + var me = this, + from = me.from, + to = me.to, + initialFrom = me.initialFrom || {}, + out = {}, + start, end, propHandler, attr; + for (attr in to) { + if (to.hasOwnProperty(attr)) { + start = me.target.getAttr(attr, from[attr]); + end = to[attr]; + // Use default (numeric) property handler + if (!Ext.fx.PropertyHandler[attr]) { + if (Ext.isObject(end)) { + propHandler = me.propHandlers[attr] = Ext.fx.PropertyHandler.object; + } else { + propHandler = me.propHandlers[attr] = Ext.fx.PropertyHandler.defaultHandler; + } + } else // Use custom handler + { + propHandler = me.propHandlers[attr] = Ext.fx.PropertyHandler[attr]; + } + out[attr] = propHandler.get(start, end, me.damper, initialFrom[attr], attr); + } + } + me.currentAttrs = out; + }, + /** + * @private + * Fires beforeanimate and sets the running flag. + */ + start: function(startTime) { + var me = this, + delay = me.delay, + delayStart = me.delayStart, + delayDelta; + if (delay) { + if (!delayStart) { + me.delayStart = startTime; + return; + } else { + delayDelta = startTime - delayStart; + if (delayDelta < delay) { + return; + } else { + // Compensate for frame delay; + startTime = new Date(delayStart.getTime() + delay); + } + } + } + if (me.fireEvent('beforeanimate', me) !== false) { + me.startTime = startTime; + if (!me.paused && !me.currentAttrs) { + me.initAttrs(); + } + me.running = true; + me.frameCount = 0; + } + }, + /** + * Immediately force this animation to its final state. + */ + jumpToEnd: function(suppressEvent) { + var me = this; + if (!me.endWasCalled) { + if (!me.currentAttrs) { + me.initAttrs(); + } + Ext.fx.Manager.jumpToEnd(me); + me.end(suppressEvent); + } + }, + /** + * @private + * Calculate attribute value at the passed timestamp. + * @return a hash of the new attributes. + */ + runAnim: function(elapsedTime) { + var me = this, + attrs = me.currentAttrs, + duration = me.duration, + easingFn = me.easingFn, + propHandlers = me.propHandlers, + ret = {}, + easing, values, attr, lastFrame; + if (elapsedTime >= duration) { + elapsedTime = duration; + lastFrame = true; + } + if (me.reverse) { + elapsedTime = duration - elapsedTime; + } + for (attr in attrs) { + if (attrs.hasOwnProperty(attr)) { + values = attrs[attr]; + easing = lastFrame ? 1 : easingFn(elapsedTime / duration); + ret[attr] = propHandlers[attr].set(values, easing); + } + } + me.frameCount++; + return ret; + }, + /** + * @private + * Perform lastFrame cleanup and handle iterations + * @return a hash of the new attributes. + */ + lastFrame: function() { + var me = this, + iter = me.iterations, + iterCount = me.currentIteration; + iterCount++; + if (iterCount < iter) { + if (me.alternate) { + me.reverse = !me.reverse; + } + me.startTime = new Date(); + me.currentIteration = iterCount; + // Turn off paused for CSS3 Transitions + me.paused = false; + } else { + me.currentIteration = 0; + me.end(); + me.fireEvent('lastframe', me, me.startTime); + } + }, + endWasCalled: 0, + /** + * Fire afteranimate event and end the animation. Usually called automatically when the + * animation reaches its final frame, but can also be called manually to preemptively + * stop and destroy the running animation. + */ + end: function(suppressEvent) { + var me = this; + if (me.endWasCalled++) { + return; + } + me.startTime = 0; + me.paused = false; + me.running = false; + Ext.fx.Manager.removeAnim(me); + if (!suppressEvent) { + me.fireEvent('afteranimate', me, me.startTime); + Ext.callback(me.callback, me.scope, [ + me, + me.startTime + ]); + } + if (me.remove) { + me.target.destroy(); + } + }, + isReady: function() { + return this.paused === false && this.running === false && this.iterations > 0; + }, + isRunning: function() { + return this.paused === false && this.running === true && this.isAnimator !== true; + } +}); +/** + * @member Ext + * @property {Boolean} enableFx + * True if the {@link Ext.fx.Anim} Class is available. + */ +Ext.enableFx = true; +// Indicate that Fx is available. Class might not be available immediately. + +/** + * This animation class is a mixin. + * + * Ext.util.Animate provides an API for the creation of animated transitions of properties and styles. + * This class is used as a mixin and currently applied to {@link Ext.dom.Element}, {@link Ext.CompositeElement}, + * {@link Ext.draw.sprite.Sprite}, {@link Ext.draw.sprite.Composite}, and {@link Ext.Component}. Note that Components + * have a limited subset of what attributes can be animated such as top, left, x, y, height, width, and + * opacity (color, paddings, and margins can not be animated). + * + * ## Animation Basics + * + * All animations require three things - `easing`, `duration`, and `to` (the final end value for each property) + * you wish to animate. Easing and duration are defaulted values specified below. + * Easing describes how the intermediate values used during a transition will be calculated. + * {@link Ext.fx.Anim#easing Easing} allows for a transition to change speed over its duration. + * You may use the defaults for easing and duration, but you must always set a + * {@link Ext.fx.Anim#to to} property which is the end value for all animations. + * + * Popular element 'to' configurations are: + * + * - opacity + * - x + * - y + * - color + * - height + * - width + * + * Popular sprite 'to' configurations are: + * + * - translation + * - path + * - scale + * - stroke + * - rotation + * + * The default duration for animations is 250 (which is a 1/4 of a second). Duration is denoted in + * milliseconds. Therefore 1 second is 1000, 1 minute would be 60000, and so on. The default easing curve + * used for all animations is 'ease'. Popular easing functions are included and can be found in {@link Ext.fx.Anim#easing Easing}. + * + * For example, a simple animation to fade out an element with a default easing and duration: + * + * var p1 = Ext.get('myElementId'); + * + * p1.animate({ + * to: { + * opacity: 0 + * } + * }); + * + * To make this animation fade out in a tenth of a second: + * + * var p1 = Ext.get('myElementId'); + * + * p1.animate({ + * duration: 100, + * to: { + * opacity: 0 + * } + * }); + * + * ## Animation Queues + * + * By default all animations are added to a queue which allows for animation via a chain-style API. + * For example, the following code will queue 4 animations which occur sequentially (one right after the other): + * + * p1.animate({ + * to: { + * x: 500 + * } + * }).animate({ + * to: { + * y: 150 + * } + * }).animate({ + * to: { + * backgroundColor: '#f00' //red + * } + * }).animate({ + * to: { + * opacity: 0 + * } + * }); + * + * You can change this behavior by calling the {@link Ext.util.Animate#syncFx syncFx} method and all + * subsequent animations for the specified target will be run concurrently (at the same time). + * + * p1.syncFx(); //this will make all animations run at the same time + * + * p1.animate({ + * to: { + * x: 500 + * } + * }).animate({ + * to: { + * y: 150 + * } + * }).animate({ + * to: { + * backgroundColor: '#f00' //red + * } + * }).animate({ + * to: { + * opacity: 0 + * } + * }); + * + * This works the same as: + * + * p1.animate({ + * to: { + * x: 500, + * y: 150, + * backgroundColor: '#f00' //red + * opacity: 0 + * } + * }); + * + * The {@link Ext.util.Animate#stopAnimation stopAnimation} method can be used to stop any + * currently running animations and clear any queued animations. + * + * ## Animation Keyframes + * + * You can also set up complex animations with {@link Ext.fx.Anim#keyframes keyframes} which follow the + * CSS3 Animation configuration pattern. Note rotation, translation, and scaling can only be done for sprites. + * The previous example can be written with the following syntax: + * + * p1.animate({ + * duration: 1000, //one second total + * keyframes: { + * 25: { //from 0 to 250ms (25%) + * x: 0 + * }, + * 50: { //from 250ms to 500ms (50%) + * y: 0 + * }, + * 75: { //from 500ms to 750ms (75%) + * backgroundColor: '#f00' //red + * }, + * 100: { //from 750ms to 1sec + * opacity: 0 + * } + * } + * }); + * + * ## Animation Events + * + * Each animation you create has events for {@link Ext.fx.Anim#beforeanimate beforeanimate}, + * {@link Ext.fx.Anim#afteranimate afteranimate}, and {@link Ext.fx.Anim#lastframe lastframe}. + * Keyframed animations adds an additional {@link Ext.fx.Animator#keyframe keyframe} event which + * fires for each keyframe in your animation. + * + * All animations support the {@link Ext.util.Observable#listeners listeners} configuration to attact functions to these events. + * + * startAnimate: function() { + * var p1 = Ext.get('myElementId'); + * p1.animate({ + * duration: 100, + * to: { + * opacity: 0 + * }, + * listeners: { + * beforeanimate: function() { + * // Execute my custom method before the animation + * this.myBeforeAnimateFn(); + * }, + * afteranimate: function() { + * // Execute my custom method after the animation + * this.myAfterAnimateFn(); + * }, + * scope: this + * }); + * }, + * myBeforeAnimateFn: function() { + * // My custom logic + * }, + * myAfterAnimateFn: function() { + * // My custom logic + * } + * + * Due to the fact that animations run asynchronously, you can determine if an animation is currently + * running on any target by using the {@link Ext.util.Animate#getActiveAnimation getActiveAnimation} + * method. This method will return false if there are no active animations or return the currently + * running {@link Ext.fx.Anim} instance. + * + * In this example, we're going to wait for the current animation to finish, then stop any other + * queued animations before we fade our element's opacity to 0: + * + * var curAnim = p1.getActiveAnimation(); + * if (curAnim) { + * curAnim.on('afteranimate', function() { + * p1.stopAnimation(); + * p1.animate({ + * to: { + * opacity: 0 + * } + * }); + * }); + * } + */ +Ext.define('Ext.util.Animate', { + mixinId: 'animate', + requires: [ + 'Ext.fx.Manager', + 'Ext.fx.Anim' + ], + isAnimate: true, + /** + * Performs custom animation on this object. + * + * This method is applicable to both the {@link Ext.Component Component} class and the {@link Ext.draw.sprite.Sprite Sprite} + * class. It performs animated transitions of certain properties of this object over a specified timeline. + * + * ### Animating a {@link Ext.Component Component} + * + * When animating a Component, the following properties may be specified in `from`, `to`, and `keyframe` objects: + * + * - `x` - The Component's page X position in pixels. + * + * - `y` - The Component's page Y position in pixels + * + * - `left` - The Component's `left` value in pixels. + * + * - `top` - The Component's `top` value in pixels. + * + * - `width` - The Component's `width` value in pixels. + * + * - `height` - The Component's `height` value in pixels. + * + * The following property may be set on the animation config root: + * + * - `dynamic` - Specify as true to update the Component's layout (if it is a Container) at every frame of the animation. + * *Use sparingly as laying out on every intermediate size change is an expensive operation.* + * + * For example, to animate a Window to a new size, ensuring that its internal layout and any shadow is correct: + * + * myWindow = Ext.create('Ext.window.Window', { + * title: 'Test Component animation', + * width: 500, + * height: 300, + * layout: { + * type: 'hbox', + * align: 'stretch' + * }, + * items: [{ + * title: 'Left: 33%', + * margin: '5 0 5 5', + * flex: 1 + * }, { + * title: 'Left: 66%', + * margin: '5 5 5 5', + * flex: 2 + * }] + * }); + * myWindow.show(); + * myWindow.header.el.on('click', function() { + * myWindow.animate({ + * to: { + * width: (myWindow.getWidth() == 500) ? 700 : 500, + * height: (myWindow.getHeight() == 300) ? 400 : 300 + * } + * }); + * }); + * + * For performance reasons, by default, the internal layout is only updated when the Window reaches its final `"to"` + * size. If dynamic updating of the Window's child Components is required, then configure the animation with + * `dynamic: true` and the two child items will maintain their proportions during the animation. + * + * @param {Object} animObj Configuration for {@link Ext.fx.Anim}. + * Note that the {@link Ext.fx.Anim#to to} config is required. + * @return {Object} this + */ + animate: function(animObj) { + var me = this; + if (Ext.fx.Manager.hasFxBlock(me.id)) { + return me; + } + Ext.fx.Manager.queueFx(new Ext.fx.Anim(me.anim(animObj))); + return this; + }, + /** + * @private + * Process the passed fx configuration. + */ + anim: function(config) { + if (!Ext.isObject(config)) { + return (config) ? {} : false; + } + var me = this; + if (config.stopAnimation) { + me.stopAnimation(); + } + Ext.applyIf(config, Ext.fx.Manager.getFxDefaults(me.id)); + return Ext.apply({ + target: me, + paused: true + }, config); + }, + /** + * @private + * Get animation properties + */ + getAnimationProps: function() { + var me = this, + layout = me.layout; + return layout && layout.animate ? layout.animate : {}; + }, + /** + * Stops any running effects and clears this object's internal effects queue if it contains any additional effects + * that haven't started yet. + * @deprecated 4.0 Replaced by {@link #stopAnimation} + * @return {Ext.dom.Element} The Element + * @method + */ + stopFx: Ext.Function.alias(Ext.util.Animate, 'stopAnimation'), + /** + * Stops any running effects and clears this object's internal effects queue if it contains any additional effects + * that haven't started yet. + * @param {Boolean} suppressEvent (private) + * @return {Ext.dom.Element} The Element + */ + stopAnimation: function(suppressEvent) { + Ext.fx.Manager.stopAnimation(this.id, suppressEvent); + return this; + }, + /** + * Ensures that all effects queued after syncFx is called on this object are run concurrently. This is the opposite + * of {@link #sequenceFx}. + * @return {Object} this + */ + syncFx: function() { + Ext.fx.Manager.setFxDefaults(this.id, { + concurrent: true + }); + return this; + }, + /** + * Ensures that all effects queued after sequenceFx is called on this object are run in sequence. This is the + * opposite of {@link #syncFx}. + * @return {Object} this + */ + sequenceFx: function() { + Ext.fx.Manager.setFxDefaults(this.id, { + concurrent: false + }); + return this; + }, + /** + * @method hasActiveFx + * @deprecated 4.0 Replaced by {@link #getActiveAnimation} + * @inheritdoc Ext.util.Animate#method-getActiveAnimation + */ + hasActiveFx: Ext.Function.alias(Ext.util.Animate, 'getActiveAnimation'), + /** + * Returns the current animation if this object has any effects actively running or queued, else returns false. + * @return {Ext.fx.Anim/Boolean} Anim if element has active effects, else false + */ + getActiveAnimation: function() { + return Ext.fx.Manager.getActiveAnimation(this.id); + } +}); + +/** + * A flyweight Ext.dom.Element that can be dynamically attached to a DOM node. + * In general this class should not be instantiated directly. Use {@link Ext#fly} + * to create and retrieve Fly instances. + */ +Ext.define('Ext.dom.Fly', { + extend: 'Ext.dom.Element', + alternateClassName: 'Ext.dom.Element.Fly', + // This adds the ability to wrap DOCUMENT_FRAGMENT_NODE + // Document Fragments cannot have event listeners and therefore do not + // need the caching mechanism provided by Ext.get. + // However the many Element APIs are useful such as Traversal, child appending/removing. + validNodeTypes: { + 1: 1, + // ELEMENT_NODE + 9: 1, + // DOCUMENT_NODE + 11: 1 + }, + // DOCUMENT_FRAGMENT_NODE + /** + * @property {Boolean} isFly + * This is `true` to identify Element flyweights + */ + isFly: true, + constructor: function(dom) { + this.dom = dom; + // set an "el" property that references "this". This allows + // Ext.util.Positionable methods to operate on this.el.dom since it + // gets mixed into both Element and Component + this.el = this; + }, + attach: function(dom) { + var me = this, + data; + if (!dom) { + return me.detach(); + } + // Sometimes we want to attach to the DOM of Ext.Element instance + me.dom = Ext.getDom(dom); + // If the element is not being managed by an Ext.Element instance, + // we have to assume that the classList/classMap in the data object are out of sync with reality. + if (!Ext.cache[dom.id]) { + data = me.peekData(); + if (data) { + data.isSynchronized = false; + } + } + return me; + }, + detach: function() { + return (this.dom = null); + }, + addListener: function() { + Ext.raise("Cannot use addListener() on Ext.dom.Fly instances. " + "Please use Ext.get() to retrieve an Ext.dom.Element instance instead."); + } || null, + removeListener: function() { + Ext.raise("Cannot use removeListener() on Ext.dom.Fly instances. " + "Please use Ext.get() to retrieve an Ext.dom.Element instance instead."); + } || null +}, function(Fly) { + var flyweights = {}, + detachedBodyEl; + /** + * @member Ext + * @property {Object} cache + * Stores `Fly` instances keyed by their assigned or generated name. + * @readonly + * @private + * @since 5.0.0 + */ + Fly.cache = flyweights; + /** + * @member Ext + * @method fly + * Gets the globally shared flyweight Element, with the passed node as the active + * element. Do not store a reference to this element - the dom node can be overwritten + * by other code. {@link Ext#fly} is alias for {@link Ext.dom.Element#fly}. + * + * Use this to make one-time references to DOM elements which are not going to be + * accessed again either by application code, or by Ext's classes. If accessing an + * element which will be processed regularly, then {@link Ext#get Ext.get} will be + * more appropriate to take advantage of the caching provided by the + * {@link Ext.dom.Element} class. + * + * If this method is called with and id or element that has already been cached by + * a previous call to Ext.get() it will return the cached Element instead of the + * flyweight instance. + * + * @param {String/HTMLElement} dom The DOM node or `id`. + * @param {String} [named] Allows for creation of named reusable flyweights to prevent + * conflicts (e.g. internally Ext uses "_global"). + * @return {Ext.dom.Element} The shared Element object (or `null` if no matching + * element was found). + */ + Ext.fly = function(dom, named) { + var fly = null, + fn = Ext.fly, + nodeType, data; + // name the flyweight after the calling method name if possible. + named = named || (fn.caller && (fn.caller.$name || fn.caller.name)) || '_global'; + dom = Ext.getDom(dom); + if (dom) { + nodeType = dom.nodeType; + // check if we have a valid node type or if the el is a window object before + // proceeding. This allows elements, document fragments, and document/window + // objects (even those inside iframes) to be wrapped. + // Note: a window object can be detected by comparing it's window property to + // itself, but we must use == for the comparison because === will return false + // in IE8 even though the 2 window objects are the same + if (Fly.prototype.validNodeTypes[nodeType] || (!nodeType && (dom.window == dom))) { + fly = Ext.cache[dom.id]; + // If there's no Element cached, or the element cached is for another DOM node, return a Fly + if (!fly || fly.dom !== dom) { + fly = flyweights[named] || (flyweights[named] = new Fly()); + fly.dom = dom; + data = fly.peekData(); + if (data) { + data.isSynchronized = false; + } + } + } + } + return fly; + }; + /** + * Returns an HTML div element into which {@link Ext.container.Container#method-remove removed} components + * are placed so that their DOM elements are not garbage collected as detached Dom trees. + * @return {Ext.dom.Element} + * @method getDetachedBody + * @member Ext + * @private + */ + Ext.getDetachedBody = function() { + if (!detachedBodyEl) { + Ext.detachedBodyEl = detachedBodyEl = new Fly(document.createElement('div')); + detachedBodyEl.isDetachedBody = true; + } + return detachedBodyEl; + }; +}); + +/** + * This class encapsulates a *collection* of DOM elements, providing methods to filter members, or to perform collective + * actions upon the whole set. + * + * Although they are not listed, this class supports all of the methods of {@link Ext.dom.Element}. The + * methods from these classes will be performed on all the elements in this collection. + * + * Example: + * + * var els = Ext.select("#some-el div.some-class"); + * // or select directly from an existing element + * var el = Ext.get('some-el'); + * el.select('div.some-class'); + * + * els.setWidth(100); // all elements become 100 width + * els.hide(true); // all elements fade out and hide + * // or + * els.setWidth(100).hide(true); + * + * @mixins Ext.dom.Element + */ +Ext.define('Ext.dom.CompositeElementLite', { + alternateClassName: [ + 'Ext.CompositeElementLite' + ], + requires: [ + 'Ext.dom.Fly' + ], + /** + * @property {Boolean} isComposite + * `true` in this class to identify an object as an instantiated CompositeElement, or subclass thereof. + */ + isComposite: true, + /** + * @private + */ + isLite: true, + // We use the @mixins tag above to document that CompositeElement has + // all the same methods as Element, but the @mixins tag also pulls in + // configs and properties which we don't want, so hide them explicitly: + /** + * @cfg bubbleEvents + * @hide + */ + /** + * @cfg listeners + * @hide + */ + /** + * @property dom + * @hide + */ + /** + * @property id + * @hide + */ + statics: { + // this method is called once in the class creation callback to import all methods + // from Ext.dom.Element into CompositeElementLite. It is important to remember + // that any subsequent overrides of Ext.dom.Element need to call this method again + // to ensure any additional methods get added. + importElementMethods: function() { + var Element = Ext.dom.Element, + prototype = this.prototype; + Ext.Object.each(Element.prototype, function(name, member) { + if (typeof member === 'function' && !prototype[name]) { + prototype[name] = function() { + return this.invoke(name, arguments); + }; + } + }); + } + }, + constructor: function(elements, skipValidation) { + /** + * @property {HTMLElement[]} elements + * @param skipValidation (private) + * @readonly + * The Array of DOM elements which this CompositeElement encapsulates. + * + * This will not *usually* be accessed in developers' code, but developers wishing to augment the capabilities + * of the CompositeElementLite class may use it when adding methods to the class. + * + * For example to add the `nextAll` method to the class to **add** all following siblings of selected elements, + * the code would be + * + * Ext.override(Ext.dom.CompositeElementLite, { + * nextAll: function() { + * var elements = this.elements, i, l = elements.length, n, r = [], ri = -1; + * + * // Loop through all elements in this Composite, accumulating + * // an Array of all siblings. + * for (i = 0; i < l; i++) { + * for (n = elements[i].nextSibling; n; n = n.nextSibling) { + * r[++ri] = n; + * } + * } + * + * // Add all found siblings to this Composite + * return this.add(r); + * } + * }); + */ + if (skipValidation) { + // if the caller told us that they are passing a valid elements array + // let's take their word for it. This is the fast path for performance- + // critical pieces such as Ext.dom.Element.select(), this allows us to + // skip all the transformElement() and getDom()/Ext.get() calls. + this.elements = elements || []; + } else { + this.elements = []; + this.add(elements); + } + }, + /** + * @private + */ + getElement: function(el) { + // Set the shared flyweight dom property to the current element + var fly = this._fly || (this._fly = new Ext.dom.Fly()); + return fly.attach(el); + }, + /** + * @private + */ + transformElement: function(el) { + return Ext.getDom(el); + }, + /** + * Returns the number of elements in this Composite. + * @return {Number} + */ + getCount: function() { + return this.elements.length; + }, + /** + * Adds elements to this Composite object. + * @param {HTMLElement[]/Ext.dom.CompositeElementLite} els Either an Array of DOM elements to add, or another Composite + * object who's elements should be added. + * @param {HTMLElement/String} [root] The root element of the query or id of the root. + * @return {Ext.dom.CompositeElementLite} This Composite object. + */ + add: function(els, root) { + var elements = this.elements, + i, ln; + if (!els) { + return this; + } + if (typeof els == "string") { + els = Ext.fly(root || document).query(els); + } else if (els.isComposite) { + els = els.elements; + } else if (!Ext.isIterable(els)) { + els = [ + els + ]; + } + for (i = 0 , ln = els.length; i < ln; ++i) { + elements.push(this.transformElement(els[i])); + } + return this; + }, + invoke: function(fn, args) { + var me = this, + elements = me.elements, + ln = elements.length, + prototype, element, i; + if (i !== 0) { + // make sure we are using the correct prototype, since Fly overrides a + // couple of Element methods + prototype = (me.isLite ? Ext.dom.Fly : Ext.dom.Element).prototype; + for (i = 0; i < ln; i++) { + element = elements[i]; + if (element) { + prototype[fn].apply(me.getElement(element), args); + } + } + } + return me; + }, + /** + * Returns a flyweight Element of the dom element object at the specified index. + * @param {Number} index + * @return {Ext.dom.Element} + */ + item: function(index) { + var el = this.elements[index], + out = null; + if (el) { + out = this.getElement(el); + } + return out; + }, + /** + * Gets a range nodes. + * @param {Number} start (optional) The index of the first node in the range + * @param {Number} end (optional) The index of the last node in the range + * @return {HTMLElement[]} An array of nodes + */ + slice: function(start, end) { + return Ext.Array.slice(this.elements, start, end); + }, + /** + * Calls the passed function for each element in this composite. + * @param {Function} fn The function to call. + * @param {Ext.dom.Element} fn.el The current Element in the iteration. **This is the flyweight + * (shared) Ext.dom.Element instance, so if you require a a reference to the dom node, use el.dom.** + * @param {Ext.dom.CompositeElementLite} fn.c This Composite object. + * @param {Number} fn.index The zero-based index in the iteration. + * @param {Object} [scope] The scope (this reference) in which the function is executed. + * Defaults to the Element. + * @return {Ext.dom.CompositeElementLite} this + */ + each: function(fn, scope) { + var me = this, + els = me.elements, + len = els.length, + i, e; + for (i = 0; i < len; i++) { + e = els[i]; + if (e) { + e = this.getElement(e); + if (fn.call(scope || e, e, me, i) === false) { + break; + } + } + } + return me; + }, + /** + * Clears this Composite and adds the elements passed. + * @param {HTMLElement[]/Ext.dom.CompositeElementLite} els Either an array of DOM elements, or another Composite from which + * to fill this Composite. + * @return {Ext.dom.CompositeElementLite} this + */ + fill: function(els) { + var me = this; + me.elements = []; + me.add(els); + return me; + }, + insert: function(index, nodes) { + Ext.Array.insert(this.elements, index, nodes); + }, + /** + * Filters this composite to only elements that match the passed selector. + * @param {String/Function} selector A string CSS selector or a comparison function. The comparison function will be + * called with the following arguments: + * @param {Ext.dom.Element} selector.el The current DOM element. + * @param {Number} selector.index The current index within the collection. + * @return {Ext.dom.CompositeElementLite} this + */ + filter: function(selector) { + var me = this, + els = me.elements, + len = els.length, + out = [], + i = 0, + isFunc = typeof selector == 'function', + add, el; + for (; i < len; i++) { + el = els[i]; + add = false; + if (el) { + el = me.getElement(el); + if (isFunc) { + add = selector.call(el, el, me, i) !== false; + } else { + add = el.is(selector); + } + if (add) { + out.push(me.transformElement(el)); + } + } + } + me.elements = out; + return me; + }, + /** + * Find the index of the passed element within the composite collection. + * @param {String/HTMLElement/Ext.dom.Element/Number} el The id of an element, or an Ext.dom.Element, or an HtmlElement + * to find within the composite collection. + * @return {Number} The index of the passed Ext.dom.Element in the composite collection, or -1 if not found. + */ + indexOf: function(el) { + return Ext.Array.indexOf(this.elements, this.transformElement(el)); + }, + /** + * Replaces the specified element with the passed element. + * @param {String/HTMLElement/Ext.dom.Element/Number} el The id of an element, the Element itself, the index of the + * element in this composite to replace. + * @param {String/Ext.dom.Element} replacement The id of an element or the Element itself. + * @param {Boolean} [domReplace] `true` to remove and replace the element in the document too. + * @return {Ext.dom.CompositeElementLite} this + */ + replaceElement: function(el, replacement, domReplace) { + var index = !isNaN(el) ? el : this.indexOf(el), + d; + if (index > -1) { + replacement = Ext.getDom(replacement); + if (domReplace) { + d = this.elements[index]; + d.parentNode.insertBefore(replacement, d); + Ext.removeNode(d); + } + Ext.Array.splice(this.elements, index, 1, replacement); + } + return this; + }, + /** + * Removes all elements from this Composite. + * @param {Boolean} [removeDom] True to also remove the elements from the document. + */ + clear: function(removeDom) { + var me = this, + els = me.elements, + i = els.length - 1; + if (removeDom) { + for (; i >= 0; i--) { + Ext.removeNode(els[i]); + } + } + this.elements = []; + }, + addElements: function(els, root) { + if (!els) { + return this; + } + if (typeof els === "string") { + els = Ext.dom.Element.selectorFunction(els, root); + } + var yels = this.elements, + eLen = els.length, + e; + for (e = 0; e < eLen; e++) { + yels.push(Ext.get(els[e])); + } + return this; + }, + /** + * Returns the first Element + * @return {Ext.dom.Element} + */ + first: function() { + return this.item(0); + }, + /** + * Returns the last Element + * @return {Ext.dom.Element} + */ + last: function() { + return this.item(this.getCount() - 1); + }, + /** + * Returns `true` if this composite contains the passed element + * @param {String/HTMLElement/Ext.dom.Element/Number} el The id of an element, or an Ext.Element, or an HtmlElement to + * find within the composite collection. + * @return {Boolean} + */ + contains: function(el) { + return this.indexOf(el) != -1; + }, + /** + * Removes the specified element(s). + * @param {String/HTMLElement/Ext.dom.Element/Number} keys The id of an element, the Element itself, the index of the + * element in this composite or an array of any of those. + * @param {Boolean} [removeDom] `true` to also remove the element from the document + * @return {Ext.dom.CompositeElementLite} this + */ + removeElement: function(keys, removeDom) { + keys = [].concat(keys); + var me = this, + elements = me.elements, + kLen = keys.length, + val, el, k; + for (k = 0; k < kLen; k++) { + val = keys[k]; + if ((el = (elements[val] || elements[val = me.indexOf(val)]))) { + if (removeDom) { + if (el.dom) { + el.destroy(); + } else { + Ext.removeNode(el); + } + } + Ext.Array.erase(elements, val, 1); + } + } + return me; + }, + destroy: function() { + this.invoke('destroy', arguments); + this.callParent(); + } +}, function(CompositeElementLite) { + var prototype = CompositeElementLite.prototype; + CompositeElementLite.importElementMethods(); + prototype.on = prototype.addListener; +}); + +/** + * @class Ext.dom.Element + * @override Ext.dom.Element + */ +Ext.define('Ext.overrides.dom.Element', (function() { + var Element, + // we cannot do this yet "= Ext.dom.Element" + WIN = window, + DOC = document, + HIDDEN = 'hidden', + ISCLIPPED = 'isClipped', + OVERFLOW = 'overflow', + OVERFLOWX = 'overflow-x', + OVERFLOWY = 'overflow-y', + ORIGINALCLIP = 'originalClip', + HEIGHT = 'height', + WIDTH = 'width', + VISIBILITY = 'visibility', + DISPLAY = 'display', + NONE = 'none', + OFFSETS = 'offsets', + CLIP = 'clip', + ORIGINALDISPLAY = 'originalDisplay', + VISMODE = 'visibilityMode', + ISVISIBLE = 'isVisible', + OFFSETCLASS = Ext.baseCSSPrefix + 'hidden-offsets', + CLIPCLASS = Ext.baseCSSPrefix + 'hidden-clip', + boxMarkup = [ + '', + '', + '' + ].join(''), + scriptTagRe = /(?:]*)?>)((\n|\r|.)*?)(?:<\/script>)/ig, + replaceScriptTagRe = /(?:)((\n|\r|.)*?)(?:<\/script>)/ig, + srcRe = /\ssrc=([\'\"])(.*?)\1/i, + nonSpaceRe = /\S/, + typeRe = /\stype=([\'\"])(.*?)\1/i, + adjustDirect2DTableRe = /table-row|table-.*-group/, + msRe = /^-ms-/, + camelRe = /(-[a-z])/gi, + camelReplaceFn = function(m, a) { + return a.charAt(1).toUpperCase(); + }, + XMASKED = Ext.baseCSSPrefix + "masked", + XMASKEDRELATIVE = Ext.baseCSSPrefix + "masked-relative", + EXTELMASKMSG = Ext.baseCSSPrefix + "mask-msg", + bodyRe = /^body/i, + propertyCache = {}, + getVisMode = function(el) { + var data = el.getData(), + visMode = data[VISMODE]; + if (visMode === undefined) { + data[VISMODE] = visMode = Element.VISIBILITY; + } + return visMode; + }, + emptyRange = DOC.createRange ? DOC.createRange() : null, + syncContentFly; + if (Ext.isIE8) { + var garbageBin = DOC.createElement('div'), + destroyQueue = [], + // prevent memory leaks in IE8 + // see http://social.msdn.microsoft.com/Forums/ie/en-US/c76967f0-dcf8-47d0-8984-8fe1282a94f5/ie-appendchildremovechild-memory-problem?forum=iewebdevelopment + // This function is called to fully destroy an element on a timer so that code following the + // remove call can still access the element. + clearGarbage, + clearGarbageFn = function() { + var len = destroyQueue.length, + i; + for (i = 0; i < len; i++) { + garbageBin.appendChild(destroyQueue[i]); + } + garbageBin.innerHTML = ''; + destroyQueue.length = 0; + }; + clearGarbageFn.$skipTimerCheck = true; + clearGarbage = Ext.Function.createBuffered(clearGarbageFn, 10); + } + return { + override: 'Ext.dom.Element', + mixins: [ + 'Ext.util.Animate' + ], + uses: [ + 'Ext.dom.GarbageCollector', + 'Ext.dom.Fly', + 'Ext.event.publisher.MouseEnterLeave', + 'Ext.fx.Manager', + 'Ext.fx.Anim' + ], + skipGarbageCollection: false, + _init: function(E) { + Element = E; + // now we can poke this into closure scope + // We want to expose destroyQueue on the prototype for testing purposes + if (WIN.__UNIT_TESTING__) { + E.destroyQueue = destroyQueue; + } + }, + statics: { + normalize: function(prop) { + if (prop === 'float') { + prop = Ext.supports.Float ? 'cssFloat' : 'styleFloat'; + } + // For '-ms-foo' we need msFoo + return propertyCache[prop] || (propertyCache[prop] = prop.replace(msRe, 'ms-').replace(camelRe, camelReplaceFn)); + } + }, + /** + * Convenience method for constructing a KeyMap + * @param {String/Number/Number[]/Object} key Either a string with the keys to listen for, the numeric key code, + * array of key codes or an object with the following options: + * @param {Number/Array} key.key + * @param {Boolean} key.shift + * @param {Boolean} key.ctrl + * @param {Boolean} key.alt + * @param {Function} fn The function to call + * @param {Object} [scope] The scope (`this` reference) in which the specified function is executed. Defaults to this Element. + * @return {Ext.util.KeyMap} The KeyMap created + */ + addKeyListener: function(key, fn, scope) { + var config; + if (typeof key !== 'object' || Ext.isArray(key)) { + config = { + target: this, + key: key, + fn: fn, + scope: scope + }; + } else { + config = { + target: this, + key: key.key, + shift: key.shift, + ctrl: key.ctrl, + alt: key.alt, + fn: fn, + scope: scope + }; + } + return new Ext.util.KeyMap(config); + }, + /** + * Creates a KeyMap for this element + * @param {Object} config The KeyMap config. See {@link Ext.util.KeyMap} for more details + * @return {Ext.util.KeyMap} The KeyMap created + */ + addKeyMap: function(config) { + return new Ext.util.KeyMap(Ext.apply({ + target: this + }, config)); + }, + /** + * @private + * Returns the fractional portion of this element's measurement in the given dimension. + * (IE9+ only) + * @return {Number} + */ + adjustDirect2DDimension: function(dimension) { + var me = this, + dom = me.dom, + display = me.getStyle('display'), + inlineDisplay = dom.style.display, + inlinePosition = dom.style.position, + originIndex = dimension === WIDTH ? 0 : 1, + currentStyle = dom.currentStyle, + floating; + if (display === 'inline') { + dom.style.display = 'inline-block'; + } + dom.style.position = display.match(adjustDirect2DTableRe) ? 'absolute' : 'static'; + // floating will contain digits that appears after the decimal point + // if height or width are set to auto we fallback to msTransformOrigin calculation + // Use currentStyle here instead of getStyle. In some difficult to reproduce + // instances it resets the scrollWidth of the element + floating = (parseFloat(currentStyle[dimension]) || parseFloat(currentStyle.msTransformOrigin.split(' ')[originIndex]) * 2) % 1; + dom.style.position = inlinePosition; + if (display === 'inline') { + dom.style.display = inlineDisplay; + } + return floating; + }, + /** + * @private + */ + afterAnimate: function() { + var shadow = this.shadow; + if (shadow && !shadow.disabled && !shadow.animate) { + shadow.show(); + } + }, + /** + * @private + */ + anchorAnimX: function(anchor) { + var xName = (anchor === 'l') ? 'right' : 'left'; + this.dom.style[xName] = '0px'; + }, + /** + * @private + * process the passed fx configuration. + */ + anim: function(config) { + if (!Ext.isObject(config)) { + return (config) ? {} : false; + } + var me = this, + duration = config.duration || Ext.fx.Anim.prototype.duration, + easing = config.easing || 'ease', + animConfig; + if (config.stopAnimation) { + me.stopAnimation(); + } + Ext.applyIf(config, Ext.fx.Manager.getFxDefaults(me.id)); + // Clear any 'paused' defaults. + Ext.fx.Manager.setFxDefaults(me.id, { + delay: 0 + }); + animConfig = { + // Pass the DOM reference. That's tested first so will be converted to an Ext.fx.Target fastest. + target: me.dom, + remove: config.remove, + alternate: config.alternate || false, + duration: duration, + easing: easing, + callback: config.callback, + listeners: config.listeners, + iterations: config.iterations || 1, + scope: config.scope, + block: config.block, + concurrent: config.concurrent, + delay: config.delay || 0, + paused: true, + keyframes: config.keyframes, + from: config.from || {}, + to: Ext.apply({}, config), + userConfig: config + }; + Ext.apply(animConfig.to, config.to); + // Anim API properties - backward compat + delete animConfig.to.to; + delete animConfig.to.from; + delete animConfig.to.remove; + delete animConfig.to.alternate; + delete animConfig.to.keyframes; + delete animConfig.to.iterations; + delete animConfig.to.listeners; + delete animConfig.to.target; + delete animConfig.to.paused; + delete animConfig.to.callback; + delete animConfig.to.scope; + delete animConfig.to.duration; + delete animConfig.to.easing; + delete animConfig.to.concurrent; + delete animConfig.to.block; + delete animConfig.to.stopAnimation; + delete animConfig.to.delay; + return animConfig; + }, + /** + * Calls `{@link #addAnimation}` and returns this Element (for call chaining). For + * details, see `{@link #addAnimation}`. + * + * @param {Object} config Configuration for {@link Ext.fx.Anim}. + * Note that the {@link Ext.fx.Anim#to to} config is required. + * @return {Ext.dom.Element} this + */ + animate: function(config) { + this.addAnimation(config); + return this; + }, + /** + * Starts a custom animation on this Element. + * + * The following properties may be specified in `from`, `to`, and `keyframe` objects: + * + * - `x` - The page X position in pixels. + * - `y` - The page Y position in pixels + * - `left` - The element's CSS `left` value. Units must be supplied. + * - `top` - The element's CSS `top` value. Units must be supplied. + * - `width` - The element's CSS `width` value. Units must be supplied. + * - `height` - The element's CSS `height` value. Units must be supplied. + * - `scrollLeft` - The element's `scrollLeft` value. + * - `scrollTop` - The element's `scrollTop` value. + * - `opacity` - The element's `opacity` value (between `0` and `1`). + * + * **Be aware** that animating an Element which is being used by an Ext Component + * without in some way informing the Component about the changed element state will + * result in incorrect Component behaviour. This is because the Component will be + * using the old state of the element. To avoid this problem, it is now possible + * to directly animate certain properties of Components. + * + * @param {Object} config Configuration for {@link Ext.fx.Anim}. + * Note that the {@link Ext.fx.Anim#to to} config is required. + * @return {Ext.fx.Anim} The new animation. + */ + addAnimation: function(config) { + var me = this, + animId = me.dom.id || Ext.id(me.dom), + listeners, anim, end; + if (!Ext.fx.Manager.hasFxBlock(animId)) { + // Bit of gymnastics here to ensure our internal listeners get bound first + if (config.listeners) { + listeners = config.listeners; + delete config.listeners; + } + if (config.internalListeners) { + config.listeners = config.internalListeners; + delete config.internalListeners; + } + end = config.autoEnd; + delete config.autoEnd; + anim = new Ext.fx.Anim(me.anim(config)); + anim.on({ + afteranimate: 'afterAnimate', + beforeanimate: 'beforeAnimate', + scope: me, + single: true + }); + if (listeners) { + anim.on(listeners); + } + Ext.fx.Manager.queueFx(anim); + if (end) { + anim.jumpToEnd(); + } + } + return anim; + }, + /** + * @private + */ + beforeAnimate: function() { + var shadow = this.shadow; + if (shadow && !shadow.disabled && !shadow.animate) { + shadow.hide(); + } + }, + /** + * Wraps the specified element with a special 9 element markup/CSS block that renders by default as + * a gray container with a gradient background, rounded corners and a 4-way shadow. + * + * This special markup is used throughout Ext when box wrapping elements ({@link Ext.button.Button}, + * {@link Ext.panel.Panel} when {@link Ext.panel.Panel#frame frame=true}, {@link Ext.window.Window}). + * The markup is of this form: + * + *
+ *
+ *
+ * + * Example usage: + * + * // Basic box wrap + * Ext.get("foo").boxWrap(); + * + * // You can also add a custom class and use CSS inheritance rules to customize the box look. + * // 'x-box-blue' is a built-in alternative -- look at the related CSS definitions as an example + * // for how to create a custom box wrap style. + * Ext.get("foo").boxWrap().addCls("x-box-blue"); + * + * @param {String} [cls='x-box'] A base CSS class to apply to the containing wrapper element. + * Note that there are a number of CSS rules that are dependent on this name to make the overall effect work, + * so if you supply an alternate base class, make sure you also supply all of the necessary rules. + * @return {Ext.dom.Element} The outermost wrapping element of the created box structure. + */ + boxWrap: function(cls) { + cls = cls || Ext.baseCSSPrefix + 'box'; + var el = Ext.get(this.insertHtml("beforeBegin", "")); + el.selectNode('.' + cls + '-mc').appendChild(this.dom); + return el; + }, + /** + * Removes Empty, or whitespace filled text nodes. Combines adjacent text nodes. + * @param {Boolean} [forceReclean=false] By default the element keeps track if it has been cleaned already + * so you can call this over and over. However, if you update the element and need to force a re-clean, you + * can pass true. + */ + clean: function(forceReclean) { + var me = this, + dom = me.dom, + data = me.getData(), + n = dom.firstChild, + ni = -1, + nx; + if (data.isCleaned && forceReclean !== true) { + return me; + } + while (n) { + nx = n.nextSibling; + if (n.nodeType === 3) { + // Remove empty/whitespace text nodes + if (!(nonSpaceRe.test(n.nodeValue))) { + dom.removeChild(n); + } + // Combine adjacent text nodes + else if (nx && nx.nodeType === 3) { + n.appendData(Ext.String.trim(nx.data)); + dom.removeChild(nx); + nx = n.nextSibling; + n.nodeIndex = ++ni; + } + } else { + // Recursively clean + Ext.fly(n, '_clean').clean(); + n.nodeIndex = ++ni; + } + n = nx; + } + data.isCleaned = true; + return me; + }, + /** + * @method + * Empties this element. Removes all child nodes. + */ + empty: emptyRange ? function() { + var dom = this.dom; + if (dom.firstChild) { + emptyRange.setStartBefore(dom.firstChild); + emptyRange.setEndAfter(dom.lastChild); + emptyRange.deleteContents(); + } + } : function() { + var dom = this.dom; + while (dom.lastChild) { + dom.removeChild(dom.lastChild); + } + }, + clearListeners: function() { + this.removeAnchor(); + this.callParent(); + }, + /** + * Clears positioning back to the default when the document was loaded. + * @param {String} [value=''] The value to use for the left, right, top, bottom. + * You could use 'auto'. + * @return {Ext.dom.Element} this + */ + clearPositioning: function(value) { + value = value || ''; + return this.setStyle({ + left: value, + right: value, + top: value, + bottom: value, + 'z-index': '', + position: 'static' + }); + }, + /** + * Creates a proxy element of this element + * @param {String/Object} config The class name of the proxy element or a DomHelper config object + * @param {String/HTMLElement} [renderTo] The element or element id to render the proxy to. Defaults to: document.body. + * @param {Boolean} [matchBox=false] True to align and size the proxy to this element now. + * @return {Ext.dom.Element} The new proxy element + */ + createProxy: function(config, renderTo, matchBox) { + config = (typeof config === 'object') ? config : { + tag: "div", + role: 'presentation', + cls: config + }; + var me = this, + proxy = renderTo ? Ext.DomHelper.append(renderTo, config, true) : Ext.DomHelper.insertBefore(me.dom, config, true); + proxy.setVisibilityMode(Element.DISPLAY); + proxy.hide(); + if (matchBox && me.setBox && me.getBox) { + // check to make sure Element_position.js is loaded + proxy.setBox(me.getBox()); + } + return proxy; + }, + /** + * Clears any opacity settings from this element. Required in some cases for IE. + * @return {Ext.dom.Element} this + */ + clearOpacity: function() { + return this.setOpacity(''); + }, + /** + * Store the current overflow setting and clip overflow on the element - use {@link #unclip} to remove + * @return {Ext.dom.Element} this + */ + clip: function() { + var me = this, + data = me.getData(), + style; + if (!data[ISCLIPPED]) { + data[ISCLIPPED] = true; + style = me.getStyle([ + OVERFLOW, + OVERFLOWX, + OVERFLOWY + ]); + data[ORIGINALCLIP] = { + o: style[OVERFLOW], + x: style[OVERFLOWX], + y: style[OVERFLOWY] + }; + me.setStyle(OVERFLOW, HIDDEN); + me.setStyle(OVERFLOWX, HIDDEN); + me.setStyle(OVERFLOWY, HIDDEN); + } + return me; + }, + destroy: function() { + var me = this, + dom = me.dom, + data = me.peekData(), + maskEl, maskMsg; + if (dom) { + if (me.isAnimate) { + me.stopAnimation(true); + } + me.removeAnchor(); + } + if (me.deferredFocusTimer) { + Ext.undefer(me.deferredFocusTimer); + me.deferredFocusTimer = null; + } + me.callParent(); + // prevent memory leaks in IE8 + // see http://social.msdn.microsoft.com/Forums/ie/en-US/c76967f0-dcf8-47d0-8984-8fe1282a94f5/ie-appendchildremovechild-memory-problem?forum=iewebdevelopment + // must not be document, documentElement, body or window object + // Have to use != instead of !== for IE8 or it will not recognize that the window + // objects are equal + if (dom && Ext.isIE8 && (dom.window != dom) && (dom.nodeType !== 9) && (dom.tagName !== 'BODY') && (dom.tagName !== 'HTML')) { + destroyQueue[destroyQueue.length] = dom; + // Will perform extra IE8 cleanup in 10 milliseconds + // see http://social.msdn.microsoft.com/Forums/ie/en-US/c76967f0-dcf8-47d0-8984-8fe1282a94f5/ie-appendchildremovechild-memory-problem?forum=iewebdevelopment + clearGarbage(); + } + if (data) { + maskEl = data.maskEl; + maskMsg = data.maskMsg; + if (maskEl) { + maskEl.destroy(); + } + if (maskMsg) { + maskMsg.destroy(); + } + } + }, + /** + * Convenience method for setVisibilityMode(Element.DISPLAY). + * @param {String} [display] What to set display to when visible + * @return {Ext.dom.Element} this + */ + enableDisplayMode: function(display) { + var me = this; + me.setVisibilityMode(Element.DISPLAY); + if (display !== undefined) { + me.getData()[ORIGINALDISPLAY] = display; + } + return me; + }, + /** + * Fade an element in (from transparent to opaque). The ending opacity can be specified using the `opacity` + * config option. Usage: + * + * // default: fade in from opacity 0 to 100% + * el.fadeIn(); + * + * // custom: fade in from opacity 0 to 75% over 2 seconds + * el.fadeIn({ opacity: .75, duration: 2000}); + * + * // common config options shown with default values + * el.fadeIn({ + * opacity: 1, //can be any value between 0 and 1 (e.g. .5) + * easing: 'easeOut', + * duration: 500 + * }); + * + * @param {Object} options (optional) Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + fadeIn: function(options) { + var me = this, + dom = me.dom, + animFly = new Ext.dom.Fly(); + me.animate(Ext.apply({}, options, { + opacity: 1, + internalListeners: { + beforeanimate: function(anim) { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + // restore any visibility/display that may have + // been applied by a fadeout animation + if (animFly.isStyle('display', 'none')) { + animFly.setDisplayed(''); + } else { + animFly.show(); + } + } + } + })); + return this; + }, + /** + * Fade an element out (from opaque to transparent). The ending opacity can be specified using the `opacity` + * config option. Note that IE may require `useDisplay:true` in order to redisplay correctly. + * Usage: + * + * // default: fade out from the element's current opacity to 0 + * el.fadeOut(); + * + * // custom: fade out from the element's current opacity to 25% over 2 seconds + * el.fadeOut({ opacity: .25, duration: 2000}); + * + * // common config options shown with default values + * el.fadeOut({ + * opacity: 0, //can be any value between 0 and 1 (e.g. .5) + * easing: 'easeOut', + * duration: 500, + * remove: false, + * useDisplay: false + * }); + * + * @param {Object} options (optional) Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + fadeOut: function(options) { + var me = this, + dom = me.dom, + animFly = new Ext.dom.Fly(); + options = Ext.apply({ + opacity: 0, + internalListeners: { + afteranimate: function(anim) { + if (anim.to.opacity === 0) { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + if (options.useDisplay) { + animFly.setDisplayed(false); + } else { + animFly.hide(); + } + } + } + } + }, options); + me.animate(options); + return me; + }, + /** + * @private + */ + fixDisplay: function() { + var me = this; + if (me.isStyle(DISPLAY, NONE)) { + me.setStyle(VISIBILITY, HIDDEN); + me.setStyle(DISPLAY, me._getDisplay()); + // first try reverting to default + if (me.isStyle(DISPLAY, NONE)) { + // if that fails, default to block + me.setStyle(DISPLAY, "block"); + } + } + }, + /** + * Shows a ripple of exploding, attenuating borders to draw attention to an Element. Usage: + * + * // default: a single light blue ripple + * el.frame(); + * + * // custom: 3 red ripples lasting 3 seconds total + * el.frame("#ff0000", 3, { duration: 3000 }); + * + * // common config options shown with default values + * el.frame("#C3DAF9", 1, { + * duration: 1000 // duration of each individual ripple. + * // Note: Easing is not configurable and will be ignored if included + * }); + * + * @param {String} [color='#C3DAF9'] The hex color value for the border. + * @param {Number} [count=1] The number of ripples to display. + * @param {Object} [obj] Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + frame: function(color, count, obj) { + var me = this, + dom = me.dom, + animFly = new Ext.dom.Fly(), + beforeAnim; + color = color || '#C3DAF9'; + count = count || 1; + obj = obj || {}; + beforeAnim = function() { + var animScope = this, + box, proxy, proxyAnim; + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + animFly.show(); + box = animFly.getBox(); + proxy = Ext.getBody().createChild({ + role: 'presentation', + id: animFly.dom.id + '-anim-proxy', + style: { + position: 'absolute', + 'pointer-events': 'none', + 'z-index': 35000, + border: '0px solid ' + color + } + }); + proxyAnim = new Ext.fx.Anim({ + target: proxy, + duration: obj.duration || 1000, + iterations: count, + from: { + top: box.y, + left: box.x, + borderWidth: 0, + opacity: 1, + height: box.height, + width: box.width + }, + to: { + top: box.y - 20, + left: box.x - 20, + borderWidth: 10, + opacity: 0, + height: box.height + 40, + width: box.width + 40 + } + }); + proxyAnim.on('afteranimate', function() { + proxy.destroy(); + // kill the no-op element animation created below + animScope.end(); + }); + }; + me.animate({ + // See "A Note About Wrapped Animations" at the top of this class: + duration: (Math.max(obj.duration, 500) * 2) || 2000, + listeners: { + beforeanimate: { + fn: beforeAnim + } + }, + callback: obj.callback, + scope: obj.scope + }); + return me; + }, + /** + * Return the CSS color for the specified CSS attribute. rgb, 3 digit (like `#fff`) + * and valid values are convert to standard 6 digit hex color. + * @param {String} attr The css attribute + * @param {String} defaultValue The default value to use when a valid color isn't found + * @param {String} [prefix] defaults to #. Use an empty string when working with + * color anims. + * @private + */ + getColor: function(attr, defaultValue, prefix) { + var v = this.getStyle(attr), + color = prefix || prefix === '' ? prefix : '#', + h, len, + i = 0; + if (!v || (/transparent|inherit/.test(v))) { + return defaultValue; + } + if (/^r/.test(v)) { + v = v.slice(4, v.length - 1).split(','); + len = v.length; + for (; i < len; i++) { + h = parseInt(v[i], 10); + color += (h < 16 ? '0' : '') + h.toString(16); + } + } else { + v = v.replace('#', ''); + color += v.length === 3 ? v.replace(/^(\w)(\w)(\w)$/, '$1$1$2$2$3$3') : v; + } + return (color.length > 5 ? color.toLowerCase() : defaultValue); + }, + /** + * Gets this element's {@link Ext.ElementLoader ElementLoader} + * @return {Ext.ElementLoader} The loader + */ + getLoader: function() { + var me = this, + data = me.getData(), + loader = data.loader; + if (!loader) { + data.loader = loader = new Ext.ElementLoader({ + target: me + }); + } + return loader; + }, + /** + * Gets an object with all CSS positioning properties. Useful along with + * `setPositioning` to get snapshot before performing an update and then restoring + * the element. + * @param {Boolean} [autoPx=false] true to return pixel values for "auto" styles. + * @return {Object} + */ + getPositioning: function(autoPx) { + var styles = this.getStyle([ + 'left', + 'top', + 'position', + 'z-index' + ]), + dom = this.dom; + if (autoPx) { + if (styles.left === 'auto') { + styles.left = dom.offsetLeft + 'px'; + } + if (styles.top === 'auto') { + styles.top = dom.offsetTop + 'px'; + } + } + return styles; + }, + /** + * Slides the element while fading it out of view. An anchor point can be optionally passed to set the ending point + * of the effect. Usage: + * + * // default: slide the element downward while fading out + * el.ghost(); + * + * // custom: slide the element out to the right with a 2-second duration + * el.ghost('r', { duration: 2000 }); + * + * // common config options shown with default values + * el.ghost('b', { + * easing: 'easeOut', + * duration: 500 + * }); + * + * @param {String} [anchor] One of the valid {@link Ext.fx.Anim} anchor positions (defaults to bottom: 'b') + * @param {Object} [options] Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + ghost: function(anchor, options) { + var me = this, + dom = me.dom, + animFly = new Ext.dom.Fly(), + beforeAnim; + anchor = anchor || "b"; + beforeAnim = function() { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + var width = animFly.getWidth(), + height = animFly.getHeight(), + xy = animFly.getXY(), + position = animFly.getPositioning(), + to = { + opacity: 0 + }; + switch (anchor) { + case 't': + to.y = xy[1] - height; + break; + case 'l': + to.x = xy[0] - width; + break; + case 'r': + to.x = xy[0] + width; + break; + case 'b': + to.y = xy[1] + height; + break; + case 'tl': + to.x = xy[0] - width; + to.y = xy[1] - height; + break; + case 'bl': + to.x = xy[0] - width; + to.y = xy[1] + height; + break; + case 'br': + to.x = xy[0] + width; + to.y = xy[1] + height; + break; + case 'tr': + to.x = xy[0] + width; + to.y = xy[1] - height; + break; + } + this.to = to; + this.on('afteranimate', function() { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + if (animFly) { + animFly.hide(); + animFly.clearOpacity(); + animFly.setPositioning(position); + } + }); + }; + me.animate(Ext.applyIf(options || {}, { + duration: 500, + easing: 'ease-out', + listeners: { + beforeanimate: beforeAnim + } + })); + return me; + }, + getTextSelection: function() { + var ret = this.callParent(); + if (typeof ret[0] !== 'number') { + var dom = this.dom; + var doc = dom.ownerDocument; + var range = doc.selection.createRange(); + var textRange = dom.createTextRange(); + textRange.setEndPoint('EndToStart', range); + ret[0] = textRange.text.length; + ret[1] = ret[0] + range.text.length; + } + return ret; + }, + /** + * Hide this element - Uses display mode to determine whether to use "display", + * "visibility", "offsets", or "clip". See {@link #setVisible}. + * @param {Boolean/Object} [animate] true for the default animation or a standard + * Element animation config object + * @return {Ext.dom.Element} this + */ + hide: function(animate) { + // hideMode override + if (typeof animate === 'string') { + this.setVisible(false, animate); + return this; + } + this.setVisible(false, this.anim(animate)); + return this; + }, + /** + * Highlights the Element by setting a color (applies to the background-color by default, but can be changed using + * the "attr" config option) and then fading back to the original color. If no original color is available, you + * should provide the "endColor" config option which will be cleared after the animation. Usage: + * + * // default: highlight background to yellow + * el.highlight(); + * + * // custom: highlight foreground text to blue for 2 seconds + * el.highlight("0000ff", { attr: 'color', duration: 2000 }); + * + * // common config options shown with default values + * el.highlight("ffff9c", { + * attr: "backgroundColor", //can be any valid CSS property (attribute) that supports a color value + * endColor: (current color) or "ffffff", + * easing: 'easeIn', + * duration: 1000 + * }); + * + * @param {String} color (optional) The highlight color. Should be a 6 char hex color without the leading # + * (defaults to yellow: 'ffff9c') + * @param {Object} options (optional) Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + highlight: function(color, options) { + var me = this, + dom = me.dom, + from = {}, + animFly = new Ext.dom.Fly(), + restore, to, attr, lns, event, fn; + options = options || {}; + lns = options.listeners || {}; + attr = options.attr || 'backgroundColor'; + from[attr] = color || 'ffff9c'; + if (!options.to) { + to = {}; + to[attr] = options.endColor || me.getColor(attr, 'ffffff', ''); + } else { + to = options.to; + } + // Don't apply directly on lns, since we reference it in our own callbacks below + options.listeners = Ext.apply(Ext.apply({}, lns), { + beforeanimate: function() { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + restore = dom.style[attr]; + animFly.clearOpacity(); + animFly.show(); + event = lns.beforeanimate; + if (event) { + fn = event.fn || event; + return fn.apply(event.scope || lns.scope || WIN, arguments); + } + }, + afteranimate: function() { + if (dom) { + dom.style[attr] = restore; + } + event = lns.afteranimate; + if (event) { + fn = event.fn || event; + fn.apply(event.scope || lns.scope || WIN, arguments); + } + } + }); + me.animate(Ext.apply({}, options, { + duration: 1000, + easing: 'ease-in', + from: from, + to: to + })); + return me; + }, + /** + * Initializes a {@link Ext.dd.DD} drag drop object for this element. + * @param {String} group The group the DD object is member of + * @param {Object} config The DD config object + * @param {Object} overrides An object containing methods to override/implement on the DD object + * @return {Ext.dd.DD} The DD object + */ + initDD: function(group, config, overrides) { + var dd = new Ext.dd.DD(Ext.id(this.dom), group, config); + return Ext.apply(dd, overrides); + }, + /** + * Initializes a {@link Ext.dd.DDProxy} object for this element. + * @param {String} group The group the DDProxy object is member of + * @param {Object} config The DDProxy config object + * @param {Object} overrides An object containing methods to override/implement on the DDProxy object + * @return {Ext.dd.DDProxy} The DDProxy object + */ + initDDProxy: function(group, config, overrides) { + var dd = new Ext.dd.DDProxy(Ext.id(this.dom), group, config); + return Ext.apply(dd, overrides); + }, + /** + * Initializes a {@link Ext.dd.DDTarget} object for this element. + * @param {String} group The group the DDTarget object is member of + * @param {Object} config The DDTarget config object + * @param {Object} overrides An object containing methods to override/implement on the DDTarget object + * @return {Ext.dd.DDTarget} The DDTarget object + */ + initDDTarget: function(group, config, overrides) { + var dd = new Ext.dd.DDTarget(Ext.id(this.dom), group, config); + return Ext.apply(dd, overrides); + }, + /** + * Returns true if this element is masked. Also re-centers any displayed message + * within the mask. + * + * @param {Boolean} [deep] Go up the DOM hierarchy to determine if any parent + * element is masked. + * + * @return {Boolean} + */ + isMasked: function(deep) { + var me = this, + data = me.getData(), + maskEl = data.maskEl, + maskMsg = data.maskMsg, + hasMask = false, + parent; + if (maskEl && maskEl.isVisible()) { + if (maskMsg) { + maskMsg.center(me); + } + hasMask = true; + } else if (deep) { + parent = me.findParentNode(); + if (parent) { + return Ext.fly(parent).isMasked(deep); + } + } + return hasMask; + }, + /** + * Direct access to the Ext.ElementLoader {@link Ext.ElementLoader#method-load} method. + * The method takes the same object parameter as {@link Ext.ElementLoader#method-load} + * @param {Object} options a options object for Ext.ElementLoader {@link Ext.ElementLoader#method-load} + * @return {Ext.dom.Element} this + */ + load: function(options) { + this.getLoader().load(options); + return this; + }, + /** + * Puts a mask over this element to disable user interaction. + * This method can only be applied to elements which accept child nodes. Use + * {@link #unmask} to remove the mask. + * + * @param {String} [msg] A message to display in the mask + * @param {String} [msgCls] A css class to apply to the msg element + * @param {Number} elHeight (private) Passed by AbstractComponent.mask to avoid the need to interrogate the DOM to get the height + * @return {Ext.dom.Element} The mask element + */ + mask: function(msg, msgCls, elHeight) { + var me = this, + dom = me.dom, + data = me.getData(), + maskEl = data.maskEl, + maskMsg; + if (!(bodyRe.test(dom.tagName) && me.getStyle('position') === 'static')) { + me.addCls(XMASKEDRELATIVE); + } + // We always needs to recreate the mask since the DOM element may have been re-created + if (maskEl) { + maskEl.destroy(); + } + maskEl = Ext.DomHelper.append(dom, { + role: 'presentation', + cls: Ext.baseCSSPrefix + "mask " + Ext.baseCSSPrefix + "border-box", + children: { + role: 'presentation', + cls: msgCls ? EXTELMASKMSG + " " + msgCls : EXTELMASKMSG, + cn: { + tag: 'div', + role: 'presentation', + cls: Ext.baseCSSPrefix + 'mask-msg-inner', + cn: { + tag: 'div', + role: 'presentation', + cls: Ext.baseCSSPrefix + 'mask-msg-text', + html: msg || '' + } + } + } + }, true); + maskMsg = Ext.fly(maskEl.dom.firstChild); + data.maskEl = maskEl; + me.addCls(XMASKED); + maskEl.setDisplayed(true); + if (typeof msg === 'string') { + maskMsg.setDisplayed(true); + maskMsg.center(me); + } else { + maskMsg.setDisplayed(false); + } + if (dom === DOC.body) { + maskEl.addCls(Ext.baseCSSPrefix + 'mask-fixed'); + } + // When masking the body, don't touch its tabbable state + me.saveTabbableState({ + skipSelf: dom === DOC.body + }); + // ie will not expand full height automatically + if (Ext.isIE9m && dom !== DOC.body && me.isStyle('height', 'auto')) { + maskEl.setSize(undefined, elHeight || me.getHeight()); + } + return maskEl; + }, + /** + * Fades the element out while slowly expanding it in all directions. When the effect is completed, the element will + * be hidden (visibility = 'hidden') but block elements will still take up space in the document. Usage: + * + * // default + * el.puff(); + * + * // common config options shown with default values + * el.puff({ + * easing: 'easeOut', + * duration: 500, + * useDisplay: false + * }); + * + * @param {Object} obj (optional) Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + puff: function(obj) { + var me = this, + dom = me.dom, + animFly = new Ext.dom.Fly(), + beforeAnim, + box = me.getBox(), + originalStyles = me.getStyle([ + 'width', + 'height', + 'left', + 'right', + 'top', + 'bottom', + 'position', + 'z-index', + 'font-size', + 'opacity' + ], true); + obj = Ext.applyIf(obj || {}, { + easing: 'ease-out', + duration: 500, + useDisplay: false + }); + beforeAnim = function() { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + animFly.clearOpacity(); + animFly.show(); + this.to = { + width: box.width * 2, + height: box.height * 2, + x: box.x - (box.width / 2), + y: box.y - (box.height / 2), + opacity: 0, + fontSize: '200%' + }; + this.on('afteranimate', function() { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + if (obj.useDisplay) { + animFly.setDisplayed(false); + } else { + animFly.hide(); + } + animFly.setStyle(originalStyles); + Ext.callback(obj.callback, obj.scope); + }); + }; + me.animate({ + duration: obj.duration, + easing: obj.easing, + listeners: { + beforeanimate: { + fn: beforeAnim + } + } + }); + return me; + }, + // private + // used to ensure the mouseup event is captured if it occurs outside of the + // window in IE9m. The only reason this method exists, (vs just calling + // el.dom.setCapture() directly) is so that we can override it to emptyFn + // during testing because setCapture() can wreak havoc on emulated mouse events + // http://msdn.microsoft.com/en-us/library/windows/desktop/ms646262(v=vs.85).aspx + setCapture: function() { + var dom = this.dom; + if (Ext.isIE9m && dom.setCapture) { + dom.setCapture(); + } + }, + /** + * Set the height of this Element. + * + * // change the height to 200px and animate with default configuration + * Ext.fly('elementId').setHeight(200, true); + * + * // change the height to 150px and animate with a custom configuration + * Ext.fly('elId').setHeight(150, { + * duration : 500, // animation will have a duration of .5 seconds + * // will change the content to "finished" + * callback: function(){ this.setHtml("finished"); } + * }); + * + * @param {Number/String} height The new height. This may be one of: + * + * - A Number specifying the new height in pixels. + * - A String used to set the CSS height style. Animation may **not** be used. + * + * @param {Boolean/Object} [animate] a standard Element animation config object or `true` for + * the default animation (`{duration: 350, easing: 'ease-in'}`) + * @return {Ext.dom.Element} this + */ + setHeight: function(height, animate) { + var me = this; + if (!animate || !me.anim) { + me.callParent(arguments); + } else { + if (!Ext.isObject(animate)) { + animate = {}; + } + me.animate(Ext.applyIf({ + to: { + height: height + } + }, animate)); + } + return me; + }, + /** + * Removes "vertical" state from this element (reverses everything done + * by {@link #setVertical}). + * @private + */ + setHorizontal: function() { + var me = this, + cls = me.verticalCls; + delete me.vertical; + if (cls) { + delete me.verticalCls; + me.removeCls(cls); + } + // delete the inverted methods and revert to inheriting from the prototype + delete me.setWidth; + delete me.setHeight; + if (!Ext.isIE8) { + delete me.getWidth; + delete me.getHeight; + } + // revert to inheriting styleHooks from the prototype + delete me.styleHooks; + }, + /** + * Updates the *text* value of this element. + * Replaces the content of this element with a *single text node* containing the passed text. + * @param {String} text The text to display in this Element. + */ + updateText: function(text) { + var me = this, + dom, textNode; + if (dom) { + textNode = dom.firstChild; + if (!textNode || (textNode.nodeType !== 3 || textNode.nextSibling)) { + textNode = DOC.createTextNode(); + me.empty(); + dom.appendChild(textNode); + } + if (text) { + textNode.data = text; + } + } + }, + /** + * Updates the innerHTML of this element, optionally searching for and processing scripts. + * @param {String} html The new HTML + * @param {Boolean} [loadScripts] Pass `true` to look for and process scripts. + * @param {Function} [callback] For async script loading you can be notified when the update completes. + * @param {Object} [scope=`this`] The scope (`this` reference) in which to execute the callback. + * + * Also used as the scope for any *inline* script source if the `loadScripts` parameter is `true`. + * Scripts with a `src` attribute cannot be executed in this scope. + * + * Defaults to this Element. + * @return {Ext.dom.Element} this + */ + setHtml: function(html, loadScripts, callback, scope) { + var me = this, + id, dom, interval; + if (!me.dom) { + return me; + } + html = html || ''; + dom = me.dom; + if (loadScripts !== true) { + dom.innerHTML = html; + Ext.callback(callback, me); + return me; + } + id = Ext.id(); + html += ''; + interval = Ext.interval(function() { + var hd, match, attrs, srcMatch, typeMatch, el, s; + if (!(el = DOC.getElementById(id))) { + return false; + } + Ext.uninterval(interval); + Ext.removeNode(el); + hd = Ext.getHead().dom; + while ((match = scriptTagRe.exec(html))) { + attrs = match[1]; + srcMatch = attrs ? attrs.match(srcRe) : false; + if (srcMatch && srcMatch[2]) { + s = DOC.createElement("script"); + s.src = srcMatch[2]; + typeMatch = attrs.match(typeRe); + if (typeMatch && typeMatch[2]) { + s.type = typeMatch[2]; + } + hd.appendChild(s); + } else if (match[2] && match[2].length > 0) { + if (scope) { + Ext.functionFactory(match[2]).call(scope); + } else { + Ext.globalEval(match[2]); + } + } + } + Ext.callback(callback, scope || me); + }, 20); + dom.innerHTML = html.replace(replaceScriptTagRe, ''); + return me; + }, + /** + * Set the opacity of the element + * @param {Number} opacity The new opacity. 0 = transparent, .5 = 50% visible, 1 = fully visible, etc + * @param {Boolean/Object} [animate] a standard Element animation config object or `true` for + * the default animation (`{duration: 350, easing: 'ease-in'}`) + * @return {Ext.dom.Element} this + */ + setOpacity: function(opacity, animate) { + var me = this; + if (!me.dom) { + return me; + } + if (!animate || !me.anim) { + me.setStyle('opacity', opacity); + } else { + if (typeof animate != 'object') { + animate = { + duration: 350, + easing: 'ease-in' + }; + } + me.animate(Ext.applyIf({ + to: { + opacity: opacity + } + }, animate)); + } + return me; + }, + /** + * Set positioning with an object returned by `getPositioning`. + * @param {Object} pc + * @return {Ext.dom.Element} this + */ + setPositioning: function(pc) { + return this.setStyle(pc); + }, + /** + * Changes this Element's state to "vertical" (rotated 90 or 270 degrees). + * This involves inverting the getters and setters for height and width, + * and applying hooks for rotating getters and setters for border/margin/padding. + * (getWidth becomes getHeight and vice versa), setStyle and getStyle will + * also return the inverse when height or width are being operated on. + * + * @param {Number} angle the angle of rotation - either 90 or 270 + * @param {String} cls an optional css class that contains the required + * styles for switching the element to vertical orientation. Omit this if + * the element already contains vertical styling. If cls is provided, + * it will be removed from the element when {@link #setHorizontal} is called. + * @private + */ + setVertical: function(angle, cls) { + var me = this, + proto = Element.prototype; + me.vertical = true; + if (cls) { + me.addCls(me.verticalCls = cls); + } + me.setWidth = proto.setHeight; + me.setHeight = proto.setWidth; + if (!Ext.isIE8) { + // In browsers that use CSS3 transforms we must invert getHeight and + // get Width. In IE8 no adjustment is needed because we use + // a BasicImage filter to rotate the element and the element's + // offsetWidth and offsetHeight are automatically inverted. + me.getWidth = proto.getHeight; + me.getHeight = proto.getWidth; + } + // Switch to using the appropriate vertical style hooks + me.styleHooks = (angle === 270) ? proto.verticalStyleHooks270 : proto.verticalStyleHooks90; + }, + /** + * Set the size of this Element. If animation is true, both width and height will be animated concurrently. + * @param {Number/String} width The new width. This may be one of: + * + * - A Number specifying the new width in pixels. + * - A String used to set the CSS width style. Animation may **not** be used. + * - A size object in the format `{width: widthValue, height: heightValue}`. + * + * @param {Number/String} height The new height. This may be one of: + * + * - A Number specifying the new height in pixels. + * - A String used to set the CSS height style. Animation may **not** be used. + * + * @param {Boolean/Object} [animate] a standard Element animation config object or `true` for + * the default animation (`{duration: 350, easing: 'ease-in'}`) + * + * @return {Ext.dom.Element} this + */ + setSize: function(width, height, animate) { + var me = this; + if (Ext.isObject(width)) { + // in case of object from getSize() + animate = height; + height = width.height; + width = width.width; + } + if (!animate || !me.anim) { + me.dom.style.width = Element.addUnits(width); + me.dom.style.height = Element.addUnits(height); + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + } else { + if (animate === true) { + animate = {}; + } + me.animate(Ext.applyIf({ + to: { + width: width, + height: height + } + }, animate)); + } + return me; + }, + /** + * Sets the visibility of the element (see details). If the visibilityMode is set + * to Element.DISPLAY, it will use the display property to hide the element, + * otherwise it uses visibility. The default is to hide and show using the + * visibility property. + * + * @param {Boolean} visible Whether the element is visible + * @param {Boolean/Object} [animate] True for the default animation, + * or a standard Element animation config object. + * + * @return {Ext.dom.Element} this + */ + setVisible: function(visible, animate) { + var me = this, + dom = me.dom, + animFly, + visMode = getVisMode(me); + // hideMode string override + if (typeof animate === 'string') { + switch (animate) { + case DISPLAY: + visMode = Element.DISPLAY; + break; + case VISIBILITY: + visMode = Element.VISIBILITY; + break; + case OFFSETS: + visMode = Element.OFFSETS; + break; + case CLIP: + visMode = Element.CLIP; + break; + } + me.setVisibilityMode(visMode); + animate = false; + } + if (!animate || !me.anim) { + if (visMode === Element.DISPLAY) { + return me.setDisplayed(visible); + } else if (visMode === Element.OFFSETS) { + me[visible ? 'removeCls' : 'addCls'](OFFSETCLASS); + } else if (visMode === Element.CLIP) { + me[visible ? 'removeCls' : 'addCls'](CLIPCLASS); + } else if (visMode === Element.VISIBILITY) { + me.fixDisplay(); + // Show by clearing visibility style. Explicitly setting to "visible" overrides parent visibility setting + dom.style.visibility = visible ? '' : HIDDEN; + } + } else { + // closure for composites + if (visible) { + me.setOpacity(0.01); + me.setVisible(true); + } + if (!Ext.isObject(animate)) { + animate = { + duration: 350, + easing: 'ease-in' + }; + } + animFly = new Ext.dom.Fly() , me.animate(Ext.applyIf({ + callback: function() { + if (!visible) { + // Grab the dom again, since the reference may have changed if we use fly + animFly.attach(dom).setVisible(false).setOpacity(1); + } + }, + to: { + opacity: (visible) ? 1 : 0 + } + }, animate)); + } + me.getData()[ISVISIBLE] = visible; + if (me.shadow || me.shim) { + me.setUnderlaysVisible(visible); + } + return me; + }, + /** + * Set the width of this Element. + * + * // change the width to 200px and animate with default configuration + * Ext.fly('elementId').setWidth(200, true); + * + * // change the width to 150px and animate with a custom configuration + * Ext.fly('elId').setWidth(150, { + * duration : 500, // animation will have a duration of .5 seconds + * // will change the content to "finished" + * callback: function(){ this.setHtml("finished"); } + * }); + * + * @param {Number/String} width The new width. This may be one of: + * + * - A Number specifying the new width in pixels. + * - A String used to set the CSS width style. Animation may **not** be used. + * + * @param {Boolean/Object} [animate] a standard Element animation config object or `true` for + * the default animation (`{duration: 350, easing: 'ease-in'}`) + * @return {Ext.dom.Element} this + */ + setWidth: function(width, animate) { + var me = this; + if (!animate || !me.anim) { + me.callParent(arguments); + } else { + if (!Ext.isObject(animate)) { + animate = {}; + } + me.animate(Ext.applyIf({ + to: { + width: width + } + }, animate)); + } + return me; + }, + setX: function(x, animate) { + return this.setXY([ + x, + this.getY() + ], animate); + }, + setXY: function(xy, animate) { + var me = this; + if (!animate || !me.anim) { + me.callParent([ + xy + ]); + } else { + if (!Ext.isObject(animate)) { + animate = {}; + } + me.animate(Ext.applyIf({ + to: { + x: xy[0], + y: xy[1] + } + }, animate)); + } + return this; + }, + setY: function(y, animate) { + return this.setXY([ + this.getX(), + y + ], animate); + }, + /** + * Show this element - Uses display mode to determine whether to use "display", + * "visibility", "offsets", or "clip". See {@link #setVisible}. + * + * @param {Boolean/Object} [animate] true for the default animation or a standard + * Element animation config object. + * + * @return {Ext.dom.Element} this + */ + show: function(animate) { + // hideMode override + if (typeof animate === 'string') { + this.setVisible(true, animate); + return this; + } + this.setVisible(true, this.anim(animate)); + return this; + }, + /** + * Slides the element into view. An anchor point can be optionally passed to set the point of origin for the slide + * effect. This function automatically handles wrapping the element with a fixed-size container if needed. See the + * {@link Ext.fx.Anim} class overview for valid anchor point options. Usage: + * + * // default: slide the element in from the top + * el.slideIn(); + * + * // custom: slide the element in from the right with a 2-second duration + * el.slideIn('r', { duration: 2000 }); + * + * // common config options shown with default values + * el.slideIn('t', { + * easing: 'easeOut', + * duration: 500 + * }); + * + * @param {String} [anchor] One of the valid {@link Ext.fx.Anim} anchor positions (defaults to top: 't') + * @param {Object} [options] Object literal with any of the {@link Ext.fx.Anim} config options + * @param {Boolean} options.preserveScroll Set to true if preservation of any descendant elements' + * `scrollTop` values is required. By default the DOM wrapping operation performed by `slideIn` and + * `slideOut` causes the browser to lose all scroll positions. + * @param {Boolean} slideOut + * @return {Ext.dom.Element} The Element + */ + slideIn: function(anchor, options, slideOut) { + var me = this, + dom = me.dom, + elStyle = dom.style, + animFly = new Ext.dom.Fly(), + beforeAnim, wrapAnim, restoreScroll, wrapDomParentNode; + anchor = anchor || "t"; + options = options || {}; + beforeAnim = function() { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + var animScope = this, + listeners = options.listeners, + box, originalStyles, anim, wrap; + if (!slideOut) { + animFly.fixDisplay(); + } + box = animFly.getBox(); + if ((anchor === 't' || anchor === 'b') && box.height === 0) { + box.height = dom.scrollHeight; + } else if ((anchor === 'l' || anchor === 'r') && box.width === 0) { + box.width = dom.scrollWidth; + } + originalStyles = animFly.getStyle([ + 'width', + 'height', + 'left', + 'right', + 'top', + 'bottom', + 'position', + 'z-index' + ], true); + animFly.setSize(box.width, box.height); + // Cache all descendants' scrollTop & scrollLeft values if configured to preserve scroll. + if (options.preserveScroll) { + restoreScroll = animFly.cacheScrollValues(); + } + wrap = animFly.wrap({ + role: 'presentation', + id: Ext.id() + '-anim-wrap-for-' + dom.id, + style: { + visibility: slideOut ? 'visible' : 'hidden' + } + }); + wrapDomParentNode = wrap.dom.parentNode; + wrap.setPositioning(animFly.getPositioning()); + if (wrap.isStyle('position', 'static')) { + wrap.position('relative'); + } + animFly.clearPositioning('auto'); + wrap.clip(); + // The wrap will have reset all descendant scrollTops. Restore them if we cached them. + if (restoreScroll) { + restoreScroll(); + } + // This element is temporarily positioned absolute within its wrapper. + // Restore to its default, CSS-inherited visibility setting. + // We cannot explicitly poke visibility:visible into its style because that overrides the visibility of the wrap. + animFly.setStyle({ + visibility: '', + position: 'absolute' + }); + if (slideOut) { + wrap.setSize(box.width, box.height); + } + switch (anchor) { + case 't': + anim = { + from: { + width: box.width + 'px', + height: '0px' + }, + to: { + width: box.width + 'px', + height: box.height + 'px' + } + }; + elStyle.bottom = '0px'; + break; + case 'l': + anim = { + from: { + width: '0px', + height: box.height + 'px' + }, + to: { + width: box.width + 'px', + height: box.height + 'px' + } + }; + me.anchorAnimX(anchor); + break; + case 'r': + anim = { + from: { + x: box.x + box.width, + width: '0px', + height: box.height + 'px' + }, + to: { + x: box.x, + width: box.width + 'px', + height: box.height + 'px' + } + }; + me.anchorAnimX(anchor); + break; + case 'b': + anim = { + from: { + y: box.y + box.height, + width: box.width + 'px', + height: '0px' + }, + to: { + y: box.y, + width: box.width + 'px', + height: box.height + 'px' + } + }; + break; + case 'tl': + anim = { + from: { + x: box.x, + y: box.y, + width: '0px', + height: '0px' + }, + to: { + width: box.width + 'px', + height: box.height + 'px' + } + }; + elStyle.bottom = '0px'; + me.anchorAnimX('l'); + break; + case 'bl': + anim = { + from: { + y: box.y + box.height, + width: '0px', + height: '0px' + }, + to: { + y: box.y, + width: box.width + 'px', + height: box.height + 'px' + } + }; + me.anchorAnimX('l'); + break; + case 'br': + anim = { + from: { + x: box.x + box.width, + y: box.y + box.height, + width: '0px', + height: '0px' + }, + to: { + x: box.x, + y: box.y, + width: box.width + 'px', + height: box.height + 'px' + } + }; + me.anchorAnimX('r'); + break; + case 'tr': + anim = { + from: { + x: box.x + box.width, + width: '0px', + height: '0px' + }, + to: { + x: box.x, + width: box.width + 'px', + height: box.height + 'px' + } + }; + elStyle.bottom = '0px'; + me.anchorAnimX('r'); + break; + } + wrap.show(); + wrapAnim = Ext.apply({}, options); + delete wrapAnim.listeners; + wrapAnim = new Ext.fx.Anim(Ext.applyIf(wrapAnim, { + target: wrap, + duration: 500, + easing: 'ease-out', + from: slideOut ? anim.to : anim.from, + to: slideOut ? anim.from : anim.to + })); + // In the absence of a callback, this listener MUST be added first + wrapAnim.on('afteranimate', function() { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + animFly.setStyle(originalStyles); + if (slideOut) { + if (options.useDisplay) { + animFly.setDisplayed(false); + } else { + animFly.hide(); + } + } + if (wrap.dom) { + if (wrap.dom.parentNode) { + wrap.dom.parentNode.insertBefore(dom, wrap.dom); + } else { + wrapDomParentNode.appendChild(dom); + } + wrap.destroy(); + } + // The unwrap will have reset all descendant scrollTops. Restore them if we cached them. + if (restoreScroll) { + restoreScroll(); + } + // kill the no-op element animation created below + animScope.end(); + }); + // Add configured listeners after + if (listeners) { + wrapAnim.on(listeners); + } + }; + me.animate({ + // See "A Note About Wrapped Animations" at the top of this class: + duration: options.duration ? Math.max(options.duration, 500) * 2 : 1000, + listeners: { + beforeanimate: beforeAnim + } + }); + // kick off the wrap animation + return me; + }, + /** + * Slides the element out of view. An anchor point can be optionally passed to set the end point for the slide + * effect. When the effect is completed, the element will be hidden (visibility = 'hidden') but block elements will + * still take up space in the document. The element must be removed from the DOM using the 'remove' config option if + * desired. This function automatically handles wrapping the element with a fixed-size container if needed. See the + * {@link Ext.fx.Anim} class overview for valid anchor point options. Usage: + * + * // default: slide the element out to the top + * el.slideOut(); + * + * // custom: slide the element out to the right with a 2-second duration + * el.slideOut('r', { duration: 2000 }); + * + * // common config options shown with default values + * el.slideOut('t', { + * easing: 'easeOut', + * duration: 500, + * remove: false, + * useDisplay: false + * }); + * + * @param {String} anchor (optional) One of the valid {@link Ext.fx.Anim} anchor positions (defaults to top: 't') + * @param {Object} options (optional) Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + slideOut: function(anchor, options) { + return this.slideIn(anchor, options, true); + }, + /** + * Blinks the element as if it was clicked and then collapses on its center (similar to switching off a television). + * When the effect is completed, the element will be hidden (visibility = 'hidden') but block elements will still + * take up space in the document. The element must be removed from the DOM using the 'remove' config option if + * desired. Usage: + * + * // default + * el.switchOff(); + * + * // all config options shown with default values + * el.switchOff({ + * easing: 'easeIn', + * duration: .3, + * remove: false, + * useDisplay: false + * }); + * + * @param {Object} options (optional) Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + switchOff: function(options) { + var me = this, + dom = me.dom, + animFly = new Ext.dom.Fly(), + beforeAnim; + options = Ext.applyIf(options || {}, { + easing: 'ease-in', + duration: 500, + remove: false, + useDisplay: false + }); + beforeAnim = function() { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + var animScope = this, + size = animFly.getSize(), + xy = animFly.getXY(), + keyframe, position; + animFly.clearOpacity(); + animFly.clip(); + position = animFly.getPositioning(); + keyframe = new Ext.fx.Animator({ + target: dom, + duration: options.duration, + easing: options.easing, + keyframes: { + 33: { + opacity: 0.3 + }, + 66: { + height: 1, + y: xy[1] + size.height / 2 + }, + 100: { + width: 1, + x: xy[0] + size.width / 2 + } + } + }); + keyframe.on('afteranimate', function() { + // Reattach to the DOM in case the caller animated a Fly + // in which case the dom reference will have changed by now. + animFly.attach(dom); + if (options.useDisplay) { + animFly.setDisplayed(false); + } else { + animFly.hide(); + } + animFly.clearOpacity(); + animFly.setPositioning(position); + animFly.setSize(size); + // kill the no-op element animation created below + animScope.end(); + }); + }; + me.animate({ + // See "A Note About Wrapped Animations" at the top of this class: + duration: (Math.max(options.duration, 500) * 2), + listeners: { + beforeanimate: { + fn: beforeAnim + } + }, + callback: options.callback, + scope: options.scope + }); + return me; + }, + /** + * @private + * Currently used for updating grid cells without modifying DOM structure + * + * Synchronizes content of this Element with the content of the passed element. + * + * Style and CSS class are copied from source into this Element, and contents are synced + * recursively. If a child node is a text node, the textual data is copied. + */ + syncContent: function(source) { + source = Ext.getDom(source); + var sourceNodes = source.childNodes, + sourceLen = sourceNodes.length, + dest = this.dom, + destNodes = dest.childNodes, + destLen = destNodes.length, + i, destNode, sourceNode, sourceStyle, nodeType, newAttrs, attLen, attName, value, + elData = dest._extData; + if (!syncContentFly) { + syncContentFly = new Ext.dom.Fly(); + } + // Update any attributes who's values have changed.. + newAttrs = source.attributes; + attLen = newAttrs.length; + for (i = 0; i < attLen; i++) { + attName = newAttrs[i].name; + value = newAttrs[i].value; + if (attName !== 'id' && dest.getAttribute(attName) !== value) { + dest.setAttribute(attName, newAttrs[i].value); + } + } + // The element's data is no longer synchronized. We just overwrite it in the DOM + if (elData) { + elData.isSynchronized = false; + } + // If the number of child nodes does not match, fall back to replacing innerHTML + if (sourceLen !== destLen) { + dest.innerHTML = source.innerHTML; + return; + } + // Loop through source nodes. + // If there are fewer, we must remove excess + for (i = 0; i < sourceLen; i++) { + sourceNode = sourceNodes[i]; + destNode = destNodes[i]; + nodeType = sourceNode.nodeType; + sourceStyle = sourceNode.style; + // If node structure is out of sync, just drop innerHTML in and return + if (nodeType !== destNode.nodeType || (nodeType === 1 && sourceNode.tagName !== destNode.tagName)) { + dest.innerHTML = source.innerHTML; + return; + } + // Update non-Element node (text, comment) + if (!sourceStyle) { + destNode.data = sourceNode.data; + } else // Sync element content + { + if (sourceNode.id && destNode.id !== sourceNode.id) { + destNode.id = sourceNode.id; + } + destNode.style.cssText = sourceStyle.cssText; + destNode.className = sourceNode.className; + syncContentFly.attach(destNode).syncContent(sourceNode); + } + } + }, + /** + * Toggles the element's visibility, depending on visibility mode. + * @param {Boolean/Object} [animate] True for the default animation, or a standard Element animation config object + * @return {Ext.dom.Element} this + */ + toggle: function(animate) { + var me = this; + me.setVisible(!me.isVisible(), me.anim(animate)); + return me; + }, + /** + * Hides a previously applied mask. + */ + unmask: function() { + var me = this, + data = me.getData(), + maskEl = data.maskEl, + style; + if (maskEl) { + style = maskEl.dom.style; + // Remove resource-intensive CSS expressions as soon as they are not required. + if (style.clearExpression) { + style.clearExpression('width'); + style.clearExpression('height'); + } + if (maskEl) { + maskEl.destroy(); + delete data.maskEl; + } + me.removeCls([ + XMASKED, + XMASKEDRELATIVE + ]); + } + me.restoreTabbableState(me.dom === DOC.body); + }, + /** + * Return clipping (overflow) to original clipping before {@link #clip} was called + * @return {Ext.dom.Element} this + */ + unclip: function() { + var me = this, + data = me.getData(), + clip; + if (data[ISCLIPPED]) { + data[ISCLIPPED] = false; + clip = data[ORIGINALCLIP]; + if (clip.o) { + me.setStyle(OVERFLOW, clip.o); + } + if (clip.x) { + me.setStyle(OVERFLOWX, clip.x); + } + if (clip.y) { + me.setStyle(OVERFLOWY, clip.y); + } + } + return me; + }, + translate: function(x, y, z) { + if (Ext.supports.CssTransforms && !Ext.isIE9m) { + this.callParent(arguments); + } else { + if (x != null) { + this.dom.style.left = x + 'px'; + } + if (y != null) { + this.dom.style.top = y + 'px'; + } + } + }, + deprecated: { + '4.0': { + methods: { + /** + * @method pause + * Creates a pause before any subsequent queued effects begin. If there are no effects queued after the pause it will + * have no effect. Usage: + * + * el.pause(1); + * + * @deprecated 4.0 Use the `delay` config to {@link #animate} instead. + * @param {Number} ms The length of time to pause (in milliseconds) + * @return {Ext.dom.Element} The Element + */ + pause: function(ms) { + var me = this; + Ext.fx.Manager.setFxDefaults(me.id, { + delay: ms + }); + return me; + }, + /** + * @method scale + * Animates the transition of an element's dimensions from a starting height/width to an ending height/width. This + * method is a convenience implementation of {@link #shift}. Usage: + * + * // change height and width to 100x100 pixels + * el.scale(100, 100); + * + * // common config options shown with default values. The height and width will default to + * // the element's existing values if passed as null. + * el.scale( + * [element's width], + * [element's height], { + * easing: 'easeOut', + * duration: 350 + * } + * ); + * + * @deprecated 4.0 Just use {@link #animate} instead. + * @param {Number} width The new width (pass undefined to keep the original width) + * @param {Number} height The new height (pass undefined to keep the original height) + * @param {Object} options (optional) Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + scale: function(width, height, options) { + this.animate(Ext.apply({}, options, { + width: width, + height: height + })); + return this; + }, + /** + * @method shift + * Animates the transition of any combination of an element's dimensions, xy position and/or opacity. Any of these + * properties not specified in the config object will not be changed. This effect requires that at least one new + * dimension, position or opacity setting must be passed in on the config object in order for the function to have + * any effect. Usage: + * + * // slide the element horizontally to x position 200 while changing the height and opacity + * el.shift({ x: 200, height: 50, opacity: .8 }); + * + * // common config options shown with default values. + * el.shift({ + * width: [element's width], + * height: [element's height], + * x: [element's x position], + * y: [element's y position], + * opacity: [element's opacity], + * easing: 'easeOut', + * duration: 350 + * }); + * + * @deprecated 4.0 Just use {@link #animate} instead. + * @param {Object} options Object literal with any of the {@link Ext.fx.Anim} config options + * @return {Ext.dom.Element} The Element + */ + shift: function(options) { + this.animate(options); + return this; + } + } + }, + '4.2': { + methods: { + /** + * @method moveTo + * Sets the position of the element in page coordinates. + * @param {Number} x X value for new position (coordinates are page-based) + * @param {Number} y Y value for new position (coordinates are page-based) + * @param {Boolean/Object} [animate] True for the default animation, or a standard + * Element animation config object + * @return {Ext.dom.Element} this + * @deprecated 4.2.0 Use {@link Ext.dom.Element#setXY} instead. + */ + moveTo: function(x, y, animate) { + return this.setXY([ + x, + y + ], animate); + }, + /** + * @method setBounds + * Sets the element's position and size in one shot. If animation is true then + * width, height, x and y will be animated concurrently. + * + * @param {Number} x X value for new position (coordinates are page-based) + * @param {Number} y Y value for new position (coordinates are page-based) + * @param {Number/String} width The new width. This may be one of: + * + * - A Number specifying the new width in pixels + * - A String used to set the CSS width style. Animation may **not** be used. + * + * @param {Number/String} height The new height. This may be one of: + * + * - A Number specifying the new height in pixels + * - A String used to set the CSS height style. Animation may **not** be used. + * + * @param {Boolean/Object} [animate] true for the default animation or + * a standard Element animation config object + * + * @return {Ext.dom.Element} this + * @deprecated 4.2.0 Use {@link Ext.util.Positionable#setBox} instead. + */ + setBounds: function(x, y, width, height, animate) { + return this.setBox({ + x: x, + y: y, + width: width, + height: height + }, animate); + }, + /** + * @method setLeftTop + * Sets the element's left and top positions directly using CSS style + * @param {Number/String} left Number of pixels or CSS string value to + * set as the left CSS property value + * @param {Number/String} top Number of pixels or CSS string value to + * set as the top CSS property value + * @return {Ext.dom.Element} this + * @deprecated 4.2.0 Use {@link Ext.dom.Element#setLocalXY} instead + */ + setLeftTop: function(left, top) { + var me = this, + style = me.dom.style; + style.left = Element.addUnits(left); + style.top = Element.addUnits(top); + if (me.shadow || me.shim) { + me.syncUnderlays(); + } + return me; + }, + /** + * @method setLocation + * Sets the position of the element in page coordinates. + * @param {Number} x X value for new position + * @param {Number} y Y value for new position + * @param {Boolean/Object} [animate] True for the default animation, or a standard + * Element animation config object + * @return {Ext.dom.Element} this + * @deprecated 4.2.0 Use {@link Ext.dom.Element#setXY} instead. + */ + setLocation: function(x, y, animate) { + return this.setXY([ + x, + y + ], animate); + } + } + }, + '5.0': { + methods: { + /** + * @method getAttributeNS + * Returns the value of a namespaced attribute from the element's underlying DOM node. + * @param {String} namespace The namespace in which to look for the attribute + * @param {String} name The attribute name + * @return {String} The attribute value + * @deprecated 5.0.0 Please use {@link Ext.dom.Element#getAttribute} instead. + */ + getAttributeNS: function(namespace, name) { + return this.getAttribute(name, namespace); + }, + /** + * @method getCenterXY + * Calculates the x, y to center this element on the screen + * @return {Number[]} The x, y values [x, y] + * @deprecated 5.0.0 Use {@link Ext.dom.Element#getAlignToXY} instead. + * el.getAlignToXY(document, 'c-c'); + */ + getCenterXY: function() { + return this.getAlignToXY(DOC, 'c-c'); + }, + /** + * @method getComputedHeight + * Returns either the offsetHeight or the height of this element based on CSS height adjusted by padding or borders + * when needed to simulate offsetHeight when offsets aren't available. This may not work on display:none elements + * if a height has not been set using CSS. + * @return {Number} + * @deprecated 5.0.0 use {@link Ext.dom.Element#getHeight} instead + */ + getComputedHeight: function() { + return Math.max(this.dom.offsetHeight, this.dom.clientHeight) || parseFloat(this.getStyle(HEIGHT)) || 0; + }, + /** + * @method getComputedWidth + * Returns either the offsetWidth or the width of this element based on CSS width adjusted by padding or borders + * when needed to simulate offsetWidth when offsets aren't available. This may not work on display:none elements + * if a width has not been set using CSS. + * @return {Number} + * @deprecated 5.0.0 use {@link Ext.dom.Element#getWidth} instead. + */ + getComputedWidth: function() { + return Math.max(this.dom.offsetWidth, this.dom.clientWidth) || parseFloat(this.getStyle(WIDTH)) || 0; + }, + /** + * @method getStyleSize + * Returns the dimensions of the element available to lay content out in. + * + * getStyleSize utilizes prefers style sizing if present, otherwise it chooses the larger of offsetHeight/clientHeight and + * offsetWidth/clientWidth. To obtain the size excluding scrollbars, use getViewSize. + * + * Sizing of the document body is handled at the adapter level which handles special cases for IE and strict modes, etc. + * + * @return {Object} Object describing width and height. + * @return {Number} return.width + * @return {Number} return.height + * @deprecated 5.0.0 Use {@link Ext.dom.Element#getSize} instead. + */ + getStyleSize: function() { + var me = this, + d = this.dom, + isDoc = (d === DOC || d === DOC.body), + s, w, h; + // If the body, use static methods + if (isDoc) { + return { + width: Element.getViewportWidth(), + height: Element.getViewportHeight() + }; + } + s = me.getStyle([ + 'height', + 'width' + ], true); + //seek inline + // Use Styles if they are set + if (s.width && s.width !== 'auto') { + w = parseFloat(s.width); + } + // Use Styles if they are set + if (s.height && s.height !== 'auto') { + h = parseFloat(s.height); + } + // Use getWidth/getHeight if style not set. + return { + width: w || me.getWidth(true), + height: h || me.getHeight(true) + }; + }, + /** + * @method isBorderBox + * Returns true if this element uses the border-box-sizing model. This method is + * deprecated as of version 5.0 because border-box sizing is forced upon all elements + * via a style sheet rule, and the browsers that do not support border-box (IE6/7 strict + * mode) are no longer supported. + * @deprecated 5.0.0 This method is deprecated. Browsers that do not + * support border-box (IE6/7 strict mode) are no longer supported. + * @return {Boolean} + */ + isBorderBox: function() { + return true; + }, + /** + * @method isDisplayed + * Returns true if display is not "none" + * @return {Boolean} + * @deprecated 5.0.0 use element.isStyle('display', 'none'); + */ + isDisplayed: function() { + return !this.isStyle('display', 'none'); + }, + /** + * @method focusable + * Checks whether this element can be focused. + * @return {Boolean} True if the element is focusable + * @deprecated 5.0.0 use {@link #isFocusable} instead + */ + focusable: 'isFocusable' + } + } + } + }; +})(), function() { + var Element = Ext.dom.Element, + proto = Element.prototype, + useDocForId = !Ext.isIE8, + DOC = document, + view = DOC.defaultView, + opacityRe = /alpha\(opacity=(.*)\)/i, + trimRe = /^\s+|\s+$/g, + styleHooks = proto.styleHooks, + supports = Ext.supports, + verticalStyleHooks90, verticalStyleHooks270, edges, k, edge, borderWidth, getBorderWidth; + proto._init(Element); + delete proto._init; + Ext.plainTableCls = Ext.baseCSSPrefix + 'table-plain'; + Ext.plainListCls = Ext.baseCSSPrefix + 'list-plain'; + // ensure that any methods added by this override are also added to Ext.CompositeElementLite + if (Ext.CompositeElementLite) { + Ext.CompositeElementLite.importElementMethods(); + } + if (!supports.Opacity && Ext.isIE) { + Ext.apply(styleHooks.opacity, { + get: function(dom) { + var filter = dom.style.filter, + match, opacity; + if (filter.match) { + match = filter.match(opacityRe); + if (match) { + opacity = parseFloat(match[1]); + if (!isNaN(opacity)) { + return opacity ? opacity / 100 : 0; + } + } + } + return 1; + }, + set: function(dom, value) { + var style = dom.style, + val = style.filter.replace(opacityRe, '').replace(trimRe, ''); + style.zoom = 1; + // ensure dom.hasLayout + // value can be a number or '' or null... so treat falsey as no opacity + if (typeof (value) === 'number' && value >= 0 && value < 1) { + value *= 100; + style.filter = val + (val.length ? ' ' : '') + 'alpha(opacity=' + value + ')'; + } else { + style.filter = val; + } + } + }); + } + if (!supports.matchesSelector) { + // Match basic tagName.ClassName selector syntax for is implementation + var simpleSelectorRe = /^([a-z]+|\*)?(?:\.([a-z][a-z\-_0-9]*))?$/i, + dashRe = /\-/g, + fragment, + classMatcher = function(tag, cls) { + var classRe = new RegExp('(?:^|\\s+)' + cls.replace(dashRe, '\\-') + '(?:\\s+|$)'); + if (tag && tag !== '*') { + tag = tag.toUpperCase(); + return function(el) { + return el.tagName === tag && classRe.test(el.className); + }; + } + return function(el) { + return classRe.test(el.className); + }; + }, + tagMatcher = function(tag) { + tag = tag.toUpperCase(); + return function(el) { + return el.tagName === tag; + }; + }, + cache = {}; + proto.matcherCache = cache; + proto.is = function(selector) { + // Empty selector always matches + if (!selector) { + return true; + } + var dom = this.dom, + cls, match, testFn, root, isOrphan, is, tag; + // Only Element node types can be matched. + if (dom.nodeType !== 1) { + return false; + } + if (!(testFn = Ext.isFunction(selector) ? selector : cache[selector])) { + if (!(match = selector.match(simpleSelectorRe))) { + // Not a simple tagName.className selector, do it the hard way + root = dom.parentNode; + if (!root) { + isOrphan = true; + root = fragment || (fragment = DOC.createDocumentFragment()); + fragment.appendChild(dom); + } + is = Ext.Array.indexOf(Ext.fly(root, '_is').query(selector), dom) !== -1; + if (isOrphan) { + fragment.removeChild(dom); + } + return is; + } + tag = match[1]; + cls = match[2]; + cache[selector] = testFn = cls ? classMatcher(tag, cls) : tagMatcher(tag); + } + return testFn(dom); + }; + } + // IE8 needs its own implementation of getStyle because it doesn't support getComputedStyle + if (!view || !view.getComputedStyle) { + proto.getStyle = function(property, inline) { + var me = this, + dom = me.dom, + multiple = typeof property !== 'string', + prop = property, + props = prop, + len = 1, + isInline = inline, + styleHooks = me.styleHooks, + camel, domStyle, values, hook, out, style, i; + if (multiple) { + values = {}; + prop = props[0]; + i = 0; + if (!(len = props.length)) { + return values; + } + } + if (!dom || dom.documentElement) { + return values || ''; + } + domStyle = dom.style; + if (inline) { + style = domStyle; + } else { + style = dom.currentStyle; + // fallback to inline style if rendering context not available + if (!style) { + isInline = true; + style = domStyle; + } + } + do { + hook = styleHooks[prop]; + if (!hook) { + styleHooks[prop] = hook = { + name: Element.normalize(prop) + }; + } + if (hook.get) { + out = hook.get(dom, me, isInline, style); + } else { + camel = hook.name; + out = style[camel]; + } + if (!multiple) { + return out; + } + values[prop] = out; + prop = props[++i]; + } while (i < len); + return values; + }; + } + // override getStyle for border-*-width + if (Ext.isIE8) { + getBorderWidth = function(dom, el, inline, style) { + if (style[this.styleName] === 'none') { + return '0px'; + } + return style[this.name]; + }; + edges = [ + 'Top', + 'Right', + 'Bottom', + 'Left' + ]; + k = edges.length; + while (k--) { + edge = edges[k]; + borderWidth = 'border' + edge + 'Width'; + styleHooks['border-' + edge.toLowerCase() + '-width'] = styleHooks[borderWidth] = { + name: borderWidth, + styleName: 'border' + edge + 'Style', + get: getBorderWidth + }; + } + // IE8 has an odd bug with handling font icons in pseudo elements; + // it will render the icon once and not update it when something + // like text color is changed via style addition or removal. + // We have to force icon repaint by adding a style with forced empty + // pseudo element content, (x-sync-repaint) and removing it back to work + // around this issue. + // See this: https://github.com/FortAwesome/Font-Awesome/issues/954 + // and this: https://github.com/twbs/bootstrap/issues/13863 + var syncRepaintCls = Ext.baseCSSPrefix + 'sync-repaint'; + proto.syncRepaint = function() { + this.addCls(syncRepaintCls); + // Measuring element width will make the browser to repaint it + this.getWidth(); + // Removing empty content makes the icon to appear again and be redrawn + this.removeCls(syncRepaintCls); + }; + } + if (Ext.isIE10m) { + Ext.override(Element, { + focus: function(defer, dom) { + var me = this, + ex; + dom = dom || me.dom; + if (me.deferredFocusTimer) { + Ext.undefer(me.deferredFocusTimer); + } + me.deferredFocusTimer = null; + if (Number(defer)) { + me.deferredFocusTimer = Ext.defer(me.focus, defer, me, [ + null, + dom + ]); + } else { + Ext.GlobalEvents.fireEvent('beforefocus', dom); + // IE10m has an acute problem with focusing input elements; + // when the element was just shown and did not have enough + // time to initialize, focusing it might fail. The problem + // is somewhat random in nature; most of the time focusing + // an input element will succeed, failing only occasionally. + // When it fails, the focus will be thrown to the document + // body element, with subsequent focusout/focusin event pair + // on the body, which throws off our focusenter/focusleave + // processing. + // Fortunately for us, when this focus failure happens, the + // resulting focusout event will happen *synchronously* + // unlike the normal focusing events which IE will fire + // asynchronously. Also fortunately for us, in most cases + // trying to focus the given element the second time + // immediately after it failed to focus the first time + // seems to do the trick; however when second focus attempt + // succeeds, it will result in focusout on the body and + // focusin on the given element, which again wreaks havoc + // on our focusenter/focusleave handling. + // The only workable solution we have is to pretend that + // focus never went to the document body and ignore the + // focusout and focusin caused by failed first focus attempt. + // To this end, we fudge the event stream in Focus publisher + // override. + if (dom && (dom.tagName === 'INPUT' || dom.tagname === 'TEXTAREA')) { + Ext.synchronouslyFocusing = document.activeElement; + } + // Also note that trying to focus an unfocusable element + // might throw an exception in IE8. What a cute idea, MS. :( + try { + dom.focus(); + } catch (xcpt) { + ex = xcpt; + } + // Ok so now we have this situation when we tried to focus + // the first time but did not succeed. Let's try again but + // not if there was an exception the first time - when the + // "focus failure" happens it does so silently. :( + if (Ext.synchronouslyFocusing && document.activeElement !== dom && !ex) { + dom.focus(); + } + Ext.synchronouslyFocusing = null; + } + return me; + } + }); + } + Ext.apply(Ext, { + /** + * `true` to automatically uncache orphaned Ext.Elements periodically. If set to + * `false`, the application will be required to clean up orphaned Ext.Elements and + * it's listeners as to not cause memory leakage. + * @member Ext + */ + enableGarbageCollector: true, + // In sencha v5 isBorderBox is no longer needed since all supported browsers + // support border-box, but it is hard coded to true for backward compatibility + isBorderBox: true, + /** + * @property {Boolean} useShims + * @member Ext + * Set to `true` to use a {@link Ext.util.Floating#shim shim} on all floating Components + * and {@link Ext.LoadMask LoadMasks} + */ + useShims: false, + getElementById: function(id) { + var el = DOC.getElementById(id), + detachedBodyEl; + if (!el && (detachedBodyEl = Ext.detachedBodyEl)) { + el = detachedBodyEl.dom.querySelector(Ext.makeIdSelector(id)); + } + return el; + }, + /** + * Applies event listeners to elements by selectors when the document is ready. + * The event name is specified with an `@` suffix. + * + * Ext.addBehaviors({ + * // add a listener for click on all anchors in element with id foo + * '#foo a@click': function(e, t){ + * // do something + * }, + * + * // add the same listener to multiple selectors (separated by comma BEFORE the @) + * '#foo a, #bar span.some-class@mouseover': function(){ + * // do something + * } + * }); + * + * @param {Object} obj The list of behaviors to apply + * @member Ext + */ + addBehaviors: function(obj) { + if (!Ext.isReady) { + Ext.onInternalReady(function() { + Ext.addBehaviors(obj); + }); + } else { + var cache = {}, + // simple cache for applying multiple behaviors to same selector does query multiple times + parts, b, s; + for (b in obj) { + if ((parts = b.split('@'))[1]) { + // for Object prototype breakers + s = parts[0]; + if (!cache[s]) { + cache[s] = Ext.fly(document).select(s, true); + } + cache[s].on(parts[1], obj[b]); + } + } + cache = null; + } + } + }); + if (Ext.isIE9m) { + Ext.getElementById = function(id) { + var el = DOC.getElementById(id), + detachedBodyEl; + if (!el && (detachedBodyEl = Ext.detachedBodyEl)) { + el = detachedBodyEl.dom.all[id]; + } + return el; + }; + proto.getById = function(id, asDom) { + var dom = this.dom, + ret = null, + entry, el; + if (dom) { + // for normal elements getElementById is the best solution, but if the el is + // not part of the document.body, we need to use all[] + el = (useDocForId && DOC.getElementById(id)) || dom.all[id]; + if (el) { + if (asDom) { + ret = el; + } else { + // calling Element.get here is a real hit (2x slower) because it has to + // redetermine that we are giving it a dom el. + entry = Ext.cache[id]; + if (entry) { + if (entry.skipGarbageCollection || !Ext.isGarbage(entry.dom)) { + ret = entry; + } else { + Ext.raise("Stale Element with id '" + el.id + "' found in Element cache. " + "Make sure to clean up Element instances using destroy()"); + entry.destroy(); + } + } + ret = ret || new Ext.Element(el); + } + } + } + return ret; + }; + } else if (!DOC.querySelector) { + Ext.getDetachedBody = Ext.getBody; + Ext.getElementById = function(id) { + return DOC.getElementById(id); + }; + proto.getById = function(id, asDom) { + var dom = DOC.getElementById(id); + return asDom ? dom : (dom ? Ext.get(dom) : null); + }; + } + if (Ext.isIE && !(Ext.isIE9p && DOC.documentMode >= 9)) { + // Essentially all web browsers (Firefox, Internet Explorer, recent versions of Opera, Safari, Konqueror, and iCab, + // as a non-exhaustive list) return null when the specified attribute does not exist on the specified element. + // The DOM specification says that the correct return value in this case is actually the empty string, and some + // DOM implementations implement this behavior. The implementation of getAttribute in XUL (Gecko) actually follows + // the specification and returns an empty string. Consequently, you should use hasAttribute to check for an attribute's + // existence prior to calling getAttribute() if it is possible that the requested attribute does not exist on the specified element. + // + // https://developer.mozilla.org/en-US/docs/DOM/element.getAttribute + // http://www.w3.org/TR/DOM-Level-2-Core/core.html#ID-745549614 + proto.getAttribute = function(name, ns) { + var d = this.dom, + type; + if (ns) { + type = typeof d[ns + ":" + name]; + if (type !== 'undefined' && type !== 'unknown') { + return d[ns + ":" + name] || null; + } + return null; + } + if (name === "for") { + name = "htmlFor"; + } + return d[name] || null; + }; + } + Ext.onInternalReady(function() { + var transparentRe = /^(?:transparent|(?:rgba[(](?:\s*\d+\s*[,]){3}\s*0\s*[)]))$/i, + origSetWidth = proto.setWidth, + origSetHeight = proto.setHeight, + origSetSize = proto.setSize, + origUnselectable = proto.unselectable, + pxRe = /^\d+(?:\.\d*)?px$/i, + colorStyles, i, name, camel; + if (supports.FixedTableWidthBug) { + // EXTJSIV-12665 + // https://bugs.webkit.org/show_bug.cgi?id=130239 + // Webkit browsers fail to layout correctly when a form field's width is less + // than the min-width of the body element. The only way to fix it seems to be + // to toggle the display style of the field's element before and after setting + // the width. Note: once the bug has been corrected by toggling the element's + // display, successive calls to setWidth will work without the hack. It's only + // when going from naturally widthed to having an explicit width that the bug + // occurs. + styleHooks.width = { + name: 'width', + set: function(dom, value, el) { + var style = dom.style, + needsFix = el._needsTableWidthFix, + origDisplay = style.display; + if (needsFix) { + style.display = 'none'; + } + style.width = value; + if (needsFix) { + // repaint + dom.scrollWidth; + // jshint ignore:line + style.display = origDisplay; + } + } + }; + proto.setWidth = function(width, animate) { + var me = this, + dom = me.dom, + style = dom.style, + needsFix = me._needsTableWidthFix, + origDisplay = style.display; + if (needsFix && !animate) { + style.display = 'none'; + } + origSetWidth.call(me, width, animate); + if (needsFix && !animate) { + // repaint + dom.scrollWidth; + // jshint ignore:line + style.display = origDisplay; + } + return me; + }; + proto.setSize = function(width, height, animate) { + var me = this, + dom = me.dom, + style = dom.style, + needsFix = me._needsTableWidthFix, + origDisplay = style.display; + if (needsFix && !animate) { + style.display = 'none'; + } + origSetSize.call(me, width, height, animate); + if (needsFix && !animate) { + // repaint + dom.scrollWidth; + // jshint ignore:line + style.display = origDisplay; + } + return me; + }; + } + if (Ext.isIE8) { + styleHooks.height = { + name: 'height', + set: function(dom, value, el) { + var component = el.component, + frameInfo, frameBodyStyle; + if (component && component._syncFrameHeight && el === component.el) { + frameBodyStyle = component.frameBody.dom.style; + if (pxRe.test(value)) { + frameInfo = component.getFrameInfo(); + if (frameInfo) { + frameBodyStyle.height = (parseInt(value, 10) - frameInfo.height) + 'px'; + } + } else if (!value || value === 'auto') { + frameBodyStyle.height = ''; + } + } + dom.style.height = value; + } + }; + proto.setHeight = function(height, animate) { + var component = this.component, + frameInfo, frameBodyStyle; + if (component && component._syncFrameHeight && this === component.el) { + frameBodyStyle = component.frameBody.dom.style; + if (!height || height === 'auto') { + frameBodyStyle.height = ''; + } else { + frameInfo = component.getFrameInfo(); + if (frameInfo) { + frameBodyStyle.height = (height - frameInfo.height) + 'px'; + } + } + } + return origSetHeight.call(this, height, animate); + }; + proto.setSize = function(width, height, animate) { + var component = this.component, + frameInfo, frameBodyStyle; + if (component && component._syncFrameHeight && this === component.el) { + frameBodyStyle = component.frameBody.dom.style; + if (!height || height === 'auto') { + frameBodyStyle.height = ''; + } else { + frameInfo = component.getFrameInfo(); + if (frameInfo) { + frameBodyStyle.height = (height - frameInfo.height) + 'px'; + } + } + } + return origSetSize.call(this, width, height, animate); + }; + // Override for IE8 which throws an error setting innerHTML when inside + // an event handler invoked from that element. + proto.setText = function(text) { + var dom = this.dom; + // Remove all child nodes, leave only a single textNode + if (!(dom.childNodes.length === 1 && dom.firstChild.nodeType === 3)) { + while (dom.lastChild && dom.lastChild.nodeType !== 3) { + dom.removeChild(dom.lastChild); + } + dom.appendChild(document.createTextNode()); + } + // Set the data of the textNode + dom.firstChild.data = text; + }; + proto.unselectable = function() { + origUnselectable.call(this); + this.dom.onselectstart = function() { + return false; + }; + }; + } + function fixTransparent(dom, el, inline, style) { + var value = style[this.name] || ''; + return transparentRe.test(value) ? 'transparent' : value; + } + /* + * Helper function to create the function that will restore the selection. + */ + function makeSelectionRestoreFn(activeEl, start, end) { + return function() { + activeEl.selectionStart = start; + activeEl.selectionEnd = end; + }; + } + /* + * Creates a function to call to clean up problems with the work-around for the + * WebKit RightMargin bug. The work-around is to add "display: 'inline-block'" to + * the element before calling getComputedStyle and then to restore its original + * display value. The problem with this is that it corrupts the selection of an + * INPUT or TEXTAREA element (as in the "I-beam" goes away but the focus remains). + * To cleanup after this, we need to capture the selection of any such element and + * then restore it after we have restored the display style. + * + * @param {HTMLElement} target The top-most element being adjusted. + * @private + */ + function getRightMarginFixCleaner(target) { + var hasInputBug = supports.DisplayChangeInputSelectionBug, + hasTextAreaBug = supports.DisplayChangeTextAreaSelectionBug, + activeEl, tag, start, end; + if (hasInputBug || hasTextAreaBug) { + activeEl = Element.getActiveElement(); + tag = activeEl && activeEl.tagName; + if ((hasTextAreaBug && tag === 'TEXTAREA') || (hasInputBug && tag === 'INPUT' && activeEl.type === 'text')) { + if (Ext.fly(target).isAncestor(activeEl)) { + start = activeEl.selectionStart; + end = activeEl.selectionEnd; + if (Ext.isNumber(start) && Ext.isNumber(end)) { + // to be safe... + // We don't create the raw closure here inline because that + // will be costly even if we don't want to return it (nested + // function decls and exprs are often instantiated on entry + // regardless of whether execution ever reaches them): + return makeSelectionRestoreFn(activeEl, start, end); + } + } + } + } + return Ext.emptyFn; + } + // avoid special cases, just return a nop + function fixRightMargin(dom, el, inline, style) { + var result = style.marginRight, + domStyle, display; + // Ignore cases when the margin is correctly reported as 0, the bug only shows + // numbers larger. + if (result !== '0px') { + domStyle = dom.style; + display = domStyle.display; + domStyle.display = 'inline-block'; + result = (inline ? style : dom.ownerDocument.defaultView.getComputedStyle(dom, null)).marginRight; + domStyle.display = display; + } + return result; + } + function fixRightMarginAndInputFocus(dom, el, inline, style) { + var result = style.marginRight, + domStyle, cleaner, display; + if (result !== '0px') { + domStyle = dom.style; + cleaner = getRightMarginFixCleaner(dom); + display = domStyle.display; + domStyle.display = 'inline-block'; + result = (inline ? style : dom.ownerDocument.defaultView.getComputedStyle(dom, '')).marginRight; + domStyle.display = display; + cleaner(); + } + return result; + } + //TODO - this was fixed in Safari 3 - verify if this is still an issue + // Fix bug caused by this: https://bugs.webkit.org/show_bug.cgi?id=13343 + if (!supports.RightMargin) { + styleHooks.marginRight = styleHooks['margin-right'] = { + name: 'marginRight', + // TODO - Touch should use conditional compilation here or ensure that the + // underlying Ext.supports flags are set correctly... + get: (supports.DisplayChangeInputSelectionBug || supports.DisplayChangeTextAreaSelectionBug) ? fixRightMarginAndInputFocus : fixRightMargin + }; + } + if (!supports.TransparentColor) { + colorStyles = [ + 'background-color', + 'border-color', + 'color', + 'outline-color' + ]; + for (i = colorStyles.length; i--; ) { + name = colorStyles[i]; + camel = Element.normalize(name); + styleHooks[name] = styleHooks[camel] = { + name: camel, + get: fixTransparent + }; + } + } + // When elements are rotated 80 or 270 degrees, their border, margin and padding hooks + // need to be rotated as well. + proto.verticalStyleHooks90 = verticalStyleHooks90 = Ext.Object.chain(styleHooks); + proto.verticalStyleHooks270 = verticalStyleHooks270 = Ext.Object.chain(styleHooks); + verticalStyleHooks90.width = styleHooks.height || { + name: 'height' + }; + verticalStyleHooks90.height = styleHooks.width || { + name: 'width' + }; + verticalStyleHooks90['margin-top'] = { + name: 'marginLeft' + }; + verticalStyleHooks90['margin-right'] = { + name: 'marginTop' + }; + verticalStyleHooks90['margin-bottom'] = { + name: 'marginRight' + }; + verticalStyleHooks90['margin-left'] = { + name: 'marginBottom' + }; + verticalStyleHooks90['padding-top'] = { + name: 'paddingLeft' + }; + verticalStyleHooks90['padding-right'] = { + name: 'paddingTop' + }; + verticalStyleHooks90['padding-bottom'] = { + name: 'paddingRight' + }; + verticalStyleHooks90['padding-left'] = { + name: 'paddingBottom' + }; + verticalStyleHooks90['border-top'] = { + name: 'borderLeft' + }; + verticalStyleHooks90['border-right'] = { + name: 'borderTop' + }; + verticalStyleHooks90['border-bottom'] = { + name: 'borderRight' + }; + verticalStyleHooks90['border-left'] = { + name: 'borderBottom' + }; + verticalStyleHooks270.width = styleHooks.height || { + name: 'height' + }; + verticalStyleHooks270.height = styleHooks.width || { + name: 'width' + }; + verticalStyleHooks270['margin-top'] = { + name: 'marginRight' + }; + verticalStyleHooks270['margin-right'] = { + name: 'marginBottom' + }; + verticalStyleHooks270['margin-bottom'] = { + name: 'marginLeft' + }; + verticalStyleHooks270['margin-left'] = { + name: 'marginTop' + }; + verticalStyleHooks270['padding-top'] = { + name: 'paddingRight' + }; + verticalStyleHooks270['padding-right'] = { + name: 'paddingBottom' + }; + verticalStyleHooks270['padding-bottom'] = { + name: 'paddingLeft' + }; + verticalStyleHooks270['padding-left'] = { + name: 'paddingTop' + }; + verticalStyleHooks270['border-top'] = { + name: 'borderRight' + }; + verticalStyleHooks270['border-right'] = { + name: 'borderBottom' + }; + verticalStyleHooks270['border-bottom'] = { + name: 'borderLeft' + }; + verticalStyleHooks270['border-left'] = { + name: 'borderTop' + }; + /** + * @property {Boolean} scopeCss + * @member Ext + * Set this to true before onReady to prevent any styling from being added to + * the body element. By default a few styles such as font-family, and color + * are added to the body element via a "x-body" class. When this is set to + * `true` the "x-body" class is not added to the body element, but is added + * to the elements of root-level containers instead. + */ + if (!Ext.scopeCss) { + Ext.getBody().addCls(Ext.baseCSSPrefix + 'body'); + } + }, null, { + priority: 1500 + }); +}); +// onReady + +/** + * An `{@link Ext.mixin.Observable Observable}` through which Ext fires global events. + * + * Ext.on() and Ext.un() are shorthand for {@link #addListener} and {@link #removeListener} + * on this Observable. For example, to listen for the idle event: + * + * Ext.on('idle', function() { + * // do something + * }); + */ +Ext.define('Ext.GlobalEvents', { + extend: 'Ext.mixin.Observable', + alternateClassName: 'Ext.globalEvents', + // for compat with Ext JS 4.2 and earlier + requires: [ + 'Ext.dom.Element' + ], + observableType: 'global', + singleton: true, + /** + * @private + */ + resizeBuffer: 100, + /** + * @event added + * Fires when a Component is added to a Container. + * @param {Ext.Component} component + */ + /** + * @event beforeresponsiveupdate + * Fires before {@link Ext.mixin.Responsive} perform any updates in response to + * dynamic changes. This is prior to refreshing `responsiveFormulas`. + * @param {Object} context The context object used by `responsiveConfig` expressions. + * @since 5.0.1 + */ + /** + * @event beginresponsiveupdate + * Fires when {@link Ext.mixin.Responsive} is about to perform updates in response to + * dynamic changes. At this point all `responsiveFormulas` have been refreshed. + * @param {Object} context The context object used by `responsiveConfig` expressions. + * @since 5.0.1 + */ + /** + * @event responsiveupdate + * Fires after {@link Ext.mixin.Responsive} has performed updates in response to + * dynamic changes. + * @param {Object} context The context object used by `responsiveConfig` expressions. + * @since 5.0.1 + */ + /** + * @event collapse + * Fires when a Component is collapsed (e.g., a panel). + * @param {Ext.Component} component + */ + /** + * @event expand + * Fires when a Component is expanded (e.g., a panel). + * @param {Ext.Component} component + */ + /** + * @event hide + * Fires when a Component is hidden. + * @param {Ext.Component} component + */ + /** + * @event idle + * Fires when an event handler finishes its run, just before returning to + * browser control. + * + * This includes DOM event handlers, Ajax (including JSONP) event handlers, + * and {@link Ext.util.TaskRunner TaskRunners} + * + * When called at the tail of a DOM event, the event object is passed as the + * sole parameter. + * + * This can be useful for performing cleanup, or update tasks which need to + * happen only after all code in an event handler has been run, but which + * should not be executed in a timer due to the intervening browser + * reflow/repaint which would take place. + */ + /** + * @event onlinechange + * Fires when the online status of the page changes. See {@link Ext#method-isOnline} + * @param {Boolean} online `true` if in an online state. + * + * @since 6.2.1 + */ + /** + * @event removed + * Fires when a Component is removed from a Container. + * @param {Ext.Component} component + */ + /** + * @event resize + * Fires when the browser window is resized. To avoid running resize handlers + * too often resulting in sluggish window resizing, the resize event uses a buffer + * of 100 milliseconds in the Classic toolkit, and fires on animation frame + * in the Modern toolkit. + * @param {Number} width The new width + * @param {Number} height The new height + */ + /** + * @event show + * Fires when a Component is shown. + * @param {Ext.Component} component + */ + /** + * @event beforebindnotify + * Fires before a scheduled set of bindings are fired. This allows interested parties + * to react and do any required work. + * @param {Ext.util.Scheduler} scheduler The scheduler triggering the bindings. + * + * @private + * @since 5.1.0 + */ + /** + * @event mousedown + * A mousedown listener on the document that is immune to stopPropagation() + * used in cases where we need to know if a mousedown event occurred on the + * document regardless of whether some other handler tried to stop it. An + * example where this is useful is a menu that needs to be hidden whenever + * there is a mousedown event on the document. + * @param {Ext.event.Event} e The event object + */ + /** + * @event mouseup + * A mouseup listener on the document that is immune to stopPropagation() + * used in cases where we need to know if a mouseup event occurred on the + * document regardless of whether some other handler tried to stop it. An + * example where this is useful is a component which enters a "pressed" state + * upon mousedown, and needs to exit that state even if the mouse exits + * before being released. + * @param {Ext.event.Event} e The event object + */ + /** + * @property {Object} idleEventMask + * This object holds event names for events that should not trigger an `idle` event + * following their dispatch. + * @private + * @since 5.0.0 + */ + idleEventMask: { + mousemove: 1, + touchmove: 1, + pointermove: 1, + MSPointerMove: 1, + unload: 1 + }, + // @private + windowListeners: { + resize: { + fn: 'fireResize' + } + }, + constructor: function() { + var me = this; + me.callParent(); + Ext.onInternalReady(function() { + // using a closure here instead of attaching the event directly to the + // attachListeners method gives us a chance to override the method + me.attachListeners(); + }); + }, + setPressedComponent: function(component, e) { + var me = this, + pressedComponent = me.pressedComponent; + if (pressedComponent && pressedComponent.onRelease) { + pressedComponent.onRelease(e); + } + me.pressedComponent = component; + if (component) { + me.pressedScrollStart = Ext.on({ + scrollstart: function() { + me.setPressedComponent(null, e); + }, + destroyable: true + }); + } else { + me.pressedScrollStart = Ext.destroy(me.pressedScrollStart); + } + }, + attachListeners: function() { + var me = this, + win = Ext.getWin(), + winListeners = me.windowListeners; + me.onlineState = Ext.isOnline(); + // Capture width/height to compare later in fireResize + me.curHeight = Ext.Element.getViewportHeight(); + me.curWidth = Ext.Element.getViewportWidth(); + win.on({ + scope: me, + online: 'handleOnlineChange', + offline: 'handleOnlineChange' + }); + // This function is not entirely harmless but since it is not directly related + // to any component, element, or other destructible entity and effectively cannot + // be cleaned up, we have to pretend it's OK for this timer to go unnoticed. + me.fireResize.$skipTimerCheck = true; + // IE8 does its own thing + if (winListeners) { + winListeners.scope = me; + // CSS layouts only require buffering to the next animation frame + if (Ext.isModern) { + winListeners.resize.onFrame = true; + } else { + winListeners.resize.buffer = me.resizeBuffer; + } + win.on(winListeners); + } + Ext.getDoc().on({ + touchstart: 'fireMouseDown', + mousedown: 'fireMouseDown', + mouseup: 'fireMouseUp', + touchend: 'fireMouseUp', + drop: 'fireMouseUp', + dragend: 'fireMouseUp', + scope: me + }); + }, + fireMouseDown: function(e) { + this.fireEvent('mousedown', e); + // Synchronize floated component ordering. + // Note that this is an ASAP method and will complete asynchronously + // after this event has finished. + Ext.ComponentManager.handleDocumentMouseDown(e); + }, + fireMouseUp: function(e) { + this.fireEvent('mouseup', e); + this.setPressedComponent(null, e); + }, + fireResize: function() { + var me = this, + Element = Ext.Element, + w = Element.getViewportWidth(), + h = Element.getViewportHeight(); + // In IE the resize event will sometimes fire even though the w/h are the same. + if (me.curHeight !== h || me.curWidth !== w) { + me.curHeight = h; + me.curWidth = w; + if (me.hasListeners.resize) { + me.fireEvent('resize', w, h); + } + } + }, + handleOnlineChange: function() { + var online = Ext.isOnline(); + if (online !== this.onlineState) { + this.onlineState = online; + this.fireEvent('onlinechange', online); + } + } +}, function(GlobalEvents) { + /** + * @member Ext + * @method on + * Shorthand for {@link Ext.GlobalEvents#addListener}. + * @inheritdoc Ext.mixin.Observable#addListener + */ + Ext.on = function() { + return GlobalEvents.addListener.apply(GlobalEvents, arguments); + }; + /** + * @member Ext + * @method un + * Shorthand for {@link Ext.GlobalEvents#removeListener}. + * @inheritdoc Ext.mixin.Observable#removeListener + */ + Ext.un = function() { + return GlobalEvents.removeListener.apply(GlobalEvents, arguments); + }; + /** + * @member Ext + * @method fireEvent + * Shorthand for {@link Ext.GlobalEvents#fireEvent}. + * @inheritdoc Ext.mixin.Observable#fireEvent + * + * @since 6.2.0 + */ + Ext.fireEvent = function() { + return GlobalEvents.fireEvent.apply(GlobalEvents, arguments); + }; + /** + * @member Ext + * @method fireIdle + * Fires the global `idle` event if there are any listeners registered. + * + * @since 6.5.1 + * @private + */ + Ext.fireIdle = function() { + if (GlobalEvents.hasListeners.idle && !Ext._suppressIdle) { + GlobalEvents.fireEventArgs('idle'); + } + Ext._suppressIdle = false; + }; + Ext._suppressIdle = false; +}); + +// @tag core +/** + * @class Ext.GlobalEvents + */ +Ext.define('Ext.overrides.GlobalEvents', { + override: 'Ext.GlobalEvents', + /** + * @event resumelayouts + * Fires after global layout processing has been resumed in {@link + * Ext.Component#resumeLayouts}. + */ + attachListeners: function() { + var me = this, + docElement, bufferedFn; + // In IE9- when using legacy onresize event via attachEvent or onresize property, + // the event may fire for *content size changes* as well as actual document view + // size changes. See this: https://msdn.microsoft.com/en-us/library/ms536959(v=vs.85).aspx + // and this: http://stackoverflow.com/questions/1852751/window-resize-event-firing-in-internet-explorer + // The amount of these events firing all at once can be entirely staggering, and they + // often happen during layouts so we have to be über careful to execute as few JavaScript + // statements as possible to improve overall framework performance. + if (Ext.isIE8) { + docElement = Ext.getDoc().dom.documentElement; + bufferedFn = Ext.Function.createBuffered(me.fireResize, me.resizeBuffer, me); + Ext.getWin().dom.attachEvent('onresize', function() { + if (docElement.clientWidth !== Ext.GlobalEvents.curWidth || docElement.clientHeight !== Ext.GlobalEvents.curHeight) { + bufferedFn(); + } + }); + } + me.callParent(); + }, + deprecated: { + 5: { + methods: { + addListener: function(ename, fn, scope, options, order, caller, eventOptions) { + var name, readyFn; + // The "ready" event was removed from Ext.globalEvents in 5.0 in favor of + // Ext.onReady(). This function adds compatibility for the ready event + if (ename === 'ready') { + readyFn = fn; + } else if (typeof ename !== 'string') { + for (name in ename) { + if (name === 'ready') { + readyFn = ename[name]; + } + } + } + if (readyFn) { + Ext.log.warn("Ext.on('ready', fn) is deprecated. Please use Ext.onReady(fn) instead."); + Ext.onReady(readyFn); + } + this.callParent([ + ename, + fn, + scope, + options, + order, + caller, + eventOptions + ]); + } + } + } + } +}); + +/** + * @class Ext.Glyph + * @private + * A class which parses a `glyph` config and provides ways of creating the relevant DOM or yielding + * information about the selected codepoint and font. + */ +Ext.define('Ext.Glyph', { + /** + * @property {Boolean} isGlyph + * `true` in this class to identify an object as an instantiated Glyph, or subclass thereof. + */ + isGlyph: true, + /** + * @property {Number} codepoint + * The unicode codepoint of the configured glyph. + */ + /** + * @property {String} character + * A single character string representing the selected glyph. This may safely + * be injected directly into HTML. + */ + /** + * @property {String} fontFamily + * The name of the font family configured. If none was configured, it uses the library default. + * The default font-family for glyphs can be set globally using + * {@link Ext.app.Application#glyphFontFamily glyphFontFamily} application + * config or the {@link Ext#setGlyphFontFamily Ext.setGlyphFontFamily()} method. + * It is initially set to `'Pictos'`. + */ + /** + * + * @param {String/Number} glyph + * If a `string` is passed, it may be the character itself, or the unicode codepoint. + * for example: + * + * new Ext.Glyph('H'); // the "home" icon in the default (Pictos) font. + * new Ext.Glyph('x48'); // the "home" icon in the default (Pictos) font. + * new Ext.Glyph(72); // the "home" icon in the default (Pictos) font. + * + * An `@` separator may be used to denote the font: + * + * new Ext.Glyph('xf015@FontAwesome'); // The "home" icon in the FontAwesome font. + */ + constructor: function(glyph) { + glyph && this.setGlyph(glyph); + }, + /** + * + * @param {String/Number} glyph + * If a `string` is passed, it may be the character itself, or the unicode codepoint. + * for example: + * + * myGlyph.setGlyph('H'); // the "home" icon in the default (Pictos) font. + * myGlyph.setGlyph('x48'); // the "home" icon in the default (Pictos) font. + * myGlyph.setGlyph(72); // the "home" icon in the default (Pictos) font. + * + * An `@` separator may be used to denote the font: + * + * myGlyph.setGlyph('xf015@FontAwesome'); // The "home" icon in the FontAwesome font. + * + */ + setGlyph: function(glyph) { + var glyphParts; + this.glyphConfig = glyph; + if (typeof glyph === 'string') { + glyphParts = glyph.split('@'); + // If the glyph specification cannot be parsed as a number + // we use the codepoint of the first character. + // If the raw string isNaN, we prepend '0' so that a possible 'xf005' will parse as hex, + // otherwise parse it as decimal. + if (isNaN(glyph = isNaN(glyphParts[0]) ? parseInt('0' + glyphParts[0], 16) : parseInt(glyphParts[0], 10)) || !glyph) { + glyph = glyphParts[0].charCodeAt(0); + } + this.fontFamily = glyphParts[1] || Ext._glyphFontFamily; + } else { + this.fontFamily = Ext._glyphFontFamily; + } + this.codepoint = glyph; + this.character = Ext.String.fromCodePoint(this.codepoint); + return this; + }, + getStyle: function() { + return { + 'font-family': this.fontFamily + }; + }, + isEqual: function(other) { + return other && other.isGlyph && other.codepoint === this.codepoint && other.fontFamily === this.fontFamily; + }, + statics: (function() { + var instance; + return { + /** + * @method fly + * @static + * Returns a static, *singleton* `Glyph` instance encapsulating the passed configuration. + * See {@link #method-setGlyph} + * + * Note that the returned `Glyph` is reused upon each call, so only use this whwn the encapsulated + * information is consumed immediately. For a persistent `Glyph` instance, instantiate a new one. + * + * @param {String/Number} glyph + * If a `string` is passed, it may be the character itself, or the unicode codepoint. + * for example: + * + * Ext.Glyph.fly('H'); // the "home" icon in the default (Pictos) font. + * Ext.Glyph.fly('x48'); // the "home" icon in the default (Pictos) font. + * Ext.Glyph.fly(72); // the "home" icon in the default (Pictos) font. + * + * An `@` separator may be used to denote the font: + * + * Ext.Glyph.fly('xf015@FontAwesome'); // The "home" icon in the FontAwesome font. + * + * @returns {Ext.Glyph} A static `Glyph` instance encapsulating the passed configuration. + */ + fly: function(glyph) { + return glyph.isGlyph ? glyph : (instance || (instance = new Ext.Glyph())).setGlyph(glyph); + } + }; + })() +}); + +/** + * @property {Boolean} [USE_NATIVE_JSON=false] + * @member Ext + * Indicates whether to use native browser parsing for JSON methods. + * This option is ignored if the browser does not support native JSON methods. + * + * **Note:** Native JSON methods will not work with objects that have functions. + * Also, property names must be quoted, otherwise the data will not parse. + */ +Ext.USE_NATIVE_JSON = false; +/** + * Modified version of [Douglas Crockford's JSON.js][dc] that doesn't + * mess with the Object prototype. + * + * [dc]: http://www.json.org/js.html + * + * @class Ext.JSON + * @singleton + */ +Ext.JSON = (new (function() { + // @define Ext.JSON + // @require Ext + // @require Ext.Error + var me = this, + hasNative = window.JSON && JSON.toString() === '[object JSON]', + useHasOwn = !!{}.hasOwnProperty, + pad = function(n) { + return n < 10 ? "0" + n : n; + }, + doDecode = function(json) { + return eval("(" + json + ')'); + }, + // jshint ignore:line + doEncode = function(o, newline) { + // http://jsperf.com/is-undefined + if (o === null || o === undefined) { + return "null"; + } else if (Ext.isDate(o)) { + return me.encodeDate(o); + } else if (Ext.isString(o)) { + if (Ext.isMSDate(o)) { + return me.encodeMSDate(o); + } else { + return me.encodeString(o); + } + } else if (typeof o === "number") { + //don't use isNumber here, since finite checks happen inside isNumber + return isFinite(o) ? String(o) : "null"; + } else if (Ext.isBoolean(o)) { + return String(o); + } + // Allow custom zerialization by adding a toJSON method to any object type. + // Date/String have a toJSON in some environments, so check these first. + else if (o.toJSON) { + return o.toJSON(); + } else if (Ext.isArray(o)) { + return encodeArray(o, newline); + } else if (Ext.isObject(o)) { + return encodeObject(o, newline); + } else if (typeof o === "function") { + return "null"; + } + return 'undefined'; + }, + m = { + "\b": '\\b', + "\t": '\\t', + "\n": '\\n', + "\f": '\\f', + "\r": '\\r', + '"': '\\"', + "\\": '\\\\', + '\v': '\\u000b' + }, + //ie doesn't handle \v + charToReplace = /[\\\"\x00-\x1f\x7f-\uffff]/g, + encodeString = function(s) { + return '"' + s.replace(charToReplace, function(a) { + var c = m[a]; + return typeof c === 'string' ? c : '\\u' + ('0000' + a.charCodeAt(0).toString(16)).slice(-4); + }) + '"'; + }, + encodeMSDate = function(o) { + return '"' + o + '"'; + }, + encodeArrayPretty = function(o, newline) { + var len = o.length, + cnewline = newline + ' ', + sep = ',' + cnewline, + a = [ + "[", + cnewline + ], + // Note newline in case there are no members + i; + for (i = 0; i < len; i += 1) { + a.push(me.encodeValue(o[i], cnewline), sep); + } + // Overwrite trailing comma (or empty string) + a[a.length - 1] = newline + ']'; + return a.join(''); + }, + encodeObjectPretty = function(o, newline) { + var cnewline = newline + ' ', + sep = ',' + cnewline, + a = [ + "{", + cnewline + ], + // Note newline in case there are no members + i, val; + for (i in o) { + val = o[i]; + if (!useHasOwn || o.hasOwnProperty(i)) { + // To match JSON.stringify, we shouldn't encode functions or undefined + if (typeof val === 'function' || val === undefined || val.isInstance) { + + continue; + } + a.push(me.encodeValue(i) + ': ' + me.encodeValue(val, cnewline), sep); + } + } + // Overwrite trailing comma (or empty string) + a[a.length - 1] = newline + '}'; + return a.join(''); + }, + encodeArray = function(o, newline) { + if (newline) { + return encodeArrayPretty(o, newline); + } + var a = [ + "[", + "" + ], + // Note empty string in case there are no serializable members. + len = o.length, + i; + for (i = 0; i < len; i += 1) { + a.push(me.encodeValue(o[i]), ','); + } + // Overwrite trailing comma (or empty string) + a[a.length - 1] = ']'; + return a.join(""); + }, + encodeObject = function(o, newline) { + if (newline) { + return encodeObjectPretty(o, newline); + } + var a = [ + "{", + "" + ], + // Note empty string in case there are no serializable members. + i, val; + for (i in o) { + val = o[i]; + if (!useHasOwn || o.hasOwnProperty(i)) { + // To match JSON.stringify, we shouldn't encode functions or undefined + if (typeof val === 'function' || val === undefined) { + + continue; + } + a.push(me.encodeValue(i), ":", me.encodeValue(val), ','); + } + } + // Overwrite trailing comma (or empty string) + a[a.length - 1] = '}'; + return a.join(""); + }; + /** + * Encodes a String. This returns the actual string which is inserted into the JSON string as the literal + * expression. **The returned value includes enclosing double quotation marks.** + * + * To override this: + * + * Ext.JSON.encodeString = function(s) { + * return 'Foo' + s; + * }; + * + * @param {String} s The String to encode + * @return {String} The string literal to use in a JSON string. + * @method encodeString + */ + me.encodeString = encodeString; + /** + * The function which {@link #encode} uses to encode all javascript values to their JSON representations + * when {@link Ext#USE_NATIVE_JSON} is `false`. + * + * This is made public so that it can be replaced with a custom implementation. + * + * @param {Object} o Any javascript value to be converted to its JSON representation + * @return {String} The JSON representation of the passed value. + * @method encodeValue + */ + me.encodeValue = doEncode; + /** + * Encodes a Date. This returns the actual string which is inserted into the JSON string as the literal + * expression. **The returned value includes enclosing double quotation marks.** + * + * The default return format is `"yyyy-mm-ddThh:mm:ss"`. + * + * To override this: + * + * Ext.JSON.encodeDate = function(d) { + * return Ext.Date.format(d, '"Y-m-d"'); + * }; + * + * @param {Date} o The Date to encode + * @return {String} The string literal to use in a JSON string. + */ + me.encodeDate = function(o) { + return '"' + o.getFullYear() + "-" + pad(o.getMonth() + 1) + "-" + pad(o.getDate()) + "T" + pad(o.getHours()) + ":" + pad(o.getMinutes()) + ":" + pad(o.getSeconds()) + '"'; + }; + /** + * Encodes an Object, Array or other value. + * + * If the environment's native JSON encoding is not being used ({@link Ext#USE_NATIVE_JSON} is not set, + * or the environment does not support it), then ExtJS's encoding will be used. This allows the developer + * to add a `toJSON` method to their classes which need serializing to return a valid JSON representation + * of the object. + * + * @param {Object} o The variable to encode. + * @return {String} The JSON string. + */ + me.encode = function(o) { + // check USE_NATIVE_JSON here so it can be changed if needed + if (hasNative && Ext.USE_NATIVE_JSON) { + return JSON.stringify(o); + } + return me.encodeValue(o); + }; + /** + * Decodes (parses) a JSON string to an object. If the JSON is invalid, this function throws + * a SyntaxError unless the safe option is set. + * + * @param {String} json The JSON string. + * @param {Boolean} [safe=false] `true` to return null, otherwise throw an exception + * if the JSON is invalid. + * @return {Object} The resulting object. + */ + me.decode = function(json, safe) { + try { + // check USE_NATIVE_JSON here so it can be changed if needed + if (hasNative && Ext.USE_NATIVE_JSON) { + return JSON.parse(json); + } + return doDecode(json); + } catch (e) { + if (safe) { + return null; + } + Ext.raise({ + sourceClass: "Ext.JSON", + sourceMethod: "decode", + msg: "You're trying to decode an invalid JSON String: " + json + }); + } + }; + me.encodeMSDate = encodeMSDate; + // Alias for backwards compatibility + if (!Ext.util) { + Ext.util = {}; + } + Ext.util.JSON = me; + /** + * Shorthand for {@link Ext.JSON#encode} + * @member Ext + * @method encode + * @inheritdoc Ext.JSON#encode + */ + Ext.encode = me.encode; + /** + * Shorthand for {@link Ext.JSON#decode} + * @member Ext + * @method decode + * @inheritdoc Ext.JSON#decode + */ + Ext.decode = me.decode; +})()); + +/** + * @class Ext.Manifest + * **This is not a real JavaScript class and cannot be created. This is for documentation purposes only.** + * + * This documentation is for {@link Ext#manifest Ext.manifest} + * @since 5.0.0 + */ +/** + * @cfg {String/Object} compatibility + * An object keyed by package name with the value being to desired compatibility level as a + * version number. If this is just a string, this version is assumed to apply to the framework. + * Setting this value to less than 5 for 'ext' will enable the compatibility layer to assist + * in the application upgrade process. For details on the upgrade process, see the + * (Upgrade Guide)[#/guides/upgrade_50]. + */ +/** + * @cfg {Object} debug + * An object configuring the debugging characteristics of the framework. See `Ext.debugConfig` + * which is set to this value. + */ +/** + * @cfg {Object} packages + * An object keyed by package name with the value being a subset of the package's `"package.json"` + * descriptor. + */ + +/** + * A mixin that provides the functionality for inheritable configs. This allows linking + * components and containers via a prototype-chained object for accessing inherited + * values. + * + * ## Getting Inherited Properties + * + * A component's inherited state is used to keep track of aspects of a component's state + * that might be influenced by its ancestors like "collapsed" and "hidden". For example: + * + * var hidden = this.getInheritedConfig('hidden'); + * + * The above will produce `true` if this or any ancestor component has its `hidden` config + * set to `true`. + * + * ## Chained Objects + * + * Inheritable properties are implemented by chaining each component's inherited state + * object to its parent container's inherited state object via the prototype. The result + * is such that if a component's `inheritedState` does not have it's own property, it + * inherits the property from the nearest ancestor that does. + * + * In the case of a Container, two state objects are created. The primary ("outer") object + * is used for reading inherited properties. It is also what a child will prototype chain + * to if that child is not part of the container's `items` collection. Anything in the + * `items` collection will chain to the inheritedStateInner object instead. This object is + * prototype chained to inheritedState but allows for Container's layout to set inherited + * properties that specifically apply only to children of the container. This inner object + * is unlikely to be needed by user code. + * + * ## Publishing Inherited Properties + * + * The first step to publishing inherited properties is to override `initInheritedState` + * and add properties that have inheritable values. + * + * initInheritedState: function (inheritedState) { + * this.callParent(arguments); + * + * if (this.getHidden()) { + * inheritedState.hidden = true; + * } + * } + * + * The above is important because `initInheritedState` is called whenever the object needs + * to be repopulated. As you can see, only `true` values are added to `inheritedState` in + * this case because `false` would mask a `hidden` value of `true` from an ancestor. + * + * If these values change dynamically, these properties must be maintained. For example: + * + * updateHidden: function (hidden) { + * var inherited = this.getInherited(); + * + * if (hidden) { + * inherited.hidden = true; + * } else { + * // Unmask whatever may be inherited: + * delete inherited.hidden; + * } + * } + * + * ## Proper Usage + * + * ALWAYS access inherited state using `getInherited` or `getInheritedConfig`, not by + * accessing `inheritedState` directly. + * + * The `inheritedState` property does not exist until the first call to `getInherited`. At + * that point `getInherited` walks up the component tree to establish the `inheritedState` + * prototype chain. Additionally the `inheritedState` property should NOT be relied upon + * even after the initial call to `getInherited` because it is possible for it to become + * invalid. + * + * Invalidation typically happens when a component is moved to a new container. In such a + * case the `inheritedState` remains invalid until the next time `getInherited` is called + * on the component or one of its descendants. + * @private + * @since 5.0.0 + */ +Ext.define('Ext.mixin.Inheritable', { + extend: 'Ext.Mixin', + mixinConfig: { + id: 'inheritable' + }, + /** + * This method returns an object containing the inherited properties for this instance. + * + * @param {Boolean} [inner=false] Pass `true` to return `inheritedStateInner` instead + * of the normal `inheritedState` object. This is only needed internally and should + * not be passed by user code. + * + * @return {Object} The `inheritedState` object containing inherited properties. + * @since 5.0.0 + */ + getInherited: function(inner) { + var me = this, + inheritedState = (inner && me.inheritedStateInner) || me.inheritedState, + ownerCt = me.getRefOwner(), + isContainer = me.isContainer, + parent, inheritedStateInner, getInner, ownerLayout; + if (!inheritedState || inheritedState.invalid) { + // Use upward navigational link, not ownerCt. + // 99% of the time, this will use ownerCt/floatParent. + // Certain floating components do not have an ownerCt, but they are still linked + // into a navigational hierarchy. The getRefOwner method normalizes these differences. + parent = me.getRefOwner(); + ownerLayout = me.ownerLayout; + if (ownerCt) { + // For classic, this will only be true if the item is a "child" of its owning container + // For example, a docked item will not get the inner inheritedState. + // For modern, we currently don't have a decent way of telling the difference + // between a child item, or an item that belongs to the component. We may + // need to determine this in future, but currently have no use for it. + getInner = ownerLayout ? ownerLayout === ownerCt.layout : true; + } + me.inheritedState = inheritedState = // chain this component's inheritedState to that of its parent. If it + // doesn't have a parent, then chain to the rootInheritedState. This is + // done so that when there is a viewport, all component's will inherit + // from its inheritedState, even components that are not descendants of + // the viewport. + Ext.Object.chain(parent ? parent.getInherited(getInner) : Ext.rootInheritedState); + if (isContainer) { + me.inheritedStateInner = inheritedStateInner = Ext.Object.chain(inheritedState); + } + me.initInheritedState(inheritedState, inheritedStateInner); + // initInheritedState is allowed to replace the objects we provide, so we go + // back to the instance here at the end. + inheritedState = (isContainer && inner) ? me.inheritedStateInner : me.inheritedState; + } + return inheritedState; + }, + /** + * This method returns the value of a config property that may be inherited from some + * ancestor. + * + * In some cases, a config may be explicitly set on a component with the intent of + * *only* being presented to its children while that component should act upon the + * inherited value (see `referenceHolder` for example). In these cases the `skipThis` + * parameter should be specified as `true`. + * + * @param {String} property The name of the config property to return. + * @param {Boolean} [skipThis=false] Pass `true` if the property should be ignored if + * found on this instance. In other words, `true` means the property must be inherited + * and not explicitly set on this instance. + * @return {Mixed} The value of the requested `property`. + * @since 5.0.0 + */ + getInheritedConfig: function(property, skipThis) { + var state = this.inheritedState, + old, ret; + // Avoid the extra method call since user has already made one to get here + if (!state || state.invalid) { + state = this.getInherited(); + } + ret = state[property]; + if (skipThis && state.hasOwnProperty(property)) { + old = ret; + delete state[property]; + ret = state[property]; + state[property] = old; + } + return ret; + }, + /** + * Gets the Controller or Component that is used as the event root for this view. + * + * @param {Object} [defaultScope=this] The default scope to return if none is found. + * @param {Boolean} [skipThis] (private) + * @return {Ext.app.ViewController/Ext.container.Container} The default listener scope. + * + * @protected + * @since 5.0.0 + */ + resolveListenerScope: function(defaultScope, skipThis) { + var me = this, + hasSkipThis = (typeof skipThis === 'boolean'), + namedScope = Ext._namedScopes[defaultScope], + ret; + if (!namedScope) { + // If there is no named scope we know for sure that the listener was not + // declared on the class body (i.e. !namedScope.isSelf) and so we can skip + // this instance and resolve to defaultListenerScope upward in the hierarchy. + // scope: not a named scope so we default to this + ret = me.getInheritedConfig('defaultListenerScope', hasSkipThis ? skipThis : true) || defaultScope || me; + } else if (namedScope.isController) { + // scope:'controller' declared on the class body must include our own + // controller before ascending the hierarchy, but scope:'controller' declared + // on the instance must skip our own controller and search only for an + // inherited controller. + ret = me.getInheritedConfig('controller', hasSkipThis ? skipThis : !namedScope.isSelf); + } else if (namedScope.isOwner) { + ret = me.getRefOwner(); + } else if (namedScope.isSelf) { + // scope:'self' indicates listeners declared on the class body with unspecified + // scope. Include this instance when searching for an inherited default scope. + ret = me.getInheritedConfig('defaultListenerScope', hasSkipThis && skipThis) || me; + } else if (namedScope.isThis) { + // scope:'this' always resolves to this instance, regardless of whether the + // listener was declared on the class or instance + ret = me; + } + return ret || null; + }, + /** + * Returns the default listener scope for a "satellite" of this component. + * Used for resolving scope for observable objects that are not part of the normal + * Container/Component hierarchy (for example, plugins) + * + * @param {Ext.mixin.Observable} satellite + * @param {Object} [defaultScope] + * @return {Object} The listener scope + * @protected + * @since 5.1.1 + */ + resolveSatelliteListenerScope: function(satellite, defaultScope) { + var me = this, + namedScope = Ext._namedScopes[defaultScope], + ret; + // The logic here is the same as that in resolveListenerScope with a couple of + // exceptions: + // 1. If scope resolution failed, fall back to the satellite instance, not "this" + // for class-declared listeners, for instance-declared use "this" + // 2. Never pass skipThis to getInheritedConfig. The satellite is essentially + // treated as a "child" of this component and therefore should always consider + // its component/component's controller as candidates for listener scope + if (!namedScope) { + ret = me.getInheritedConfig('defaultListenerScope') || defaultScope || me; + } else if (namedScope.isController) { + ret = me.getInheritedConfig('controller'); + } else if (namedScope.isSelf) { + ret = me.getInheritedConfig('defaultListenerScope') || satellite; + } else if (namedScope.isThis) { + ret = satellite; + } + return ret || null; + }, + /** + * Gets the Form or Component that is used as the name holder for this component. + * + * @param {Boolean} [skipThis=true] `false` to return this as the name holder if + * this instance has set `nameHolder`. Unlike `getInheritedConfig` this method + * defaults to `true` because it is possible that a `name` property set by the + * owner of a component that is also a `nameHolder` itself. In this case, the + * `name` connects not to this component but to the parent nameHolder. + * + * @return {Ext.Component} The name holder. + * + * @private + * @since 6.5.0 + */ + lookupNameHolder: function(skipThis) { + return this.getInheritedConfig('nameHolder', skipThis !== false) || null; + }, + /** + * Gets the Controller or Component that is used as the reference holder for this view. + * + * @param {Boolean} [skipThis=true] `false` to return this as the reference holder if + * this instance has set `referenceHolder`. Unlike `getInheritedConfig` this method + * defaults to `true` because it is possible that a `reference` property set by the + * owner of a component that is also a `referenceHolder` itself. In this case, the + * `reference` connects not to this component but to the parent referenceHolder. + * + * @return {Ext.app.ViewController/Ext.container.Container} The reference holder. + * + * @private + * @since 5.0.0 + */ + lookupReferenceHolder: function(skipThis) { + return this.getInheritedConfig('referenceHolder', skipThis !== false) || null; + }, + /** + * Used by {@link Ext.ComponentQuery ComponentQuery}, and the {@link Ext.Component#up up} + * method to find the owning Component in the linkage hierarchy. + * + * By default this returns the Container which contains this Component. + * + * This may be overridden by Component authors who implement ownership hierarchies + * which are not based upon ownerCt, such as BoundLists being owned by Fields or Menus + * being owned by Buttons. + * @protected + */ + getRefOwner: function() { + var me = this; + // Look for both ownerCt (classic toolkit) and parent (modern toolkit) + // Look for ownerCmp before all containment links for scenarios like a button + // menu inside a floating window, or a submenu of a menu item. + // Floated items have the Viewport as their parent, and ownerCmp exists to + // override the containment tree. + return me.ownerCmp || me.ownerCt || me.parent || me.$initParent || me.floatParent; + }, + /** + * Bubbles up the {@link #method!getRefOwner} hierarchy, calling the specified function + * with each component. The scope (`this` reference) of the function call will be the + * scope provided or the current component. The arguments to the function will + * be the args provided or the current component. If the function returns false at any + * point, the bubble is stopped. + * + * @param {Function} fn The function to call + * @param {Object} [scope] The scope of the function. Defaults to current node. + * @param {Array} [args] The args to call the function with. Defaults to passing the current component. + */ + bubble: function(fn, scope, args) { + for (var target = this; target; target = target.getRefOwner()) { + if (fn.apply(scope || target, args || [ + target + ]) === false) { + break; + } + } + }, + /** + * Determines whether this component is the descendant of a passed component. + * @param {Ext.Component} ancestor A Component which may contain this Component. + * @return {Boolean} `true` if the component is the descendant of the passed component, + * otherwise `false`. + */ + isDescendantOf: function(ancestor) { + return ancestor ? ancestor.isAncestor(this) : false; + }, + /** + * Determines whether **this Component** is an ancestor of the passed Component. + * This will return `true` if the passed Component is anywhere within the subtree + * beneath this Component. + * @param {Ext.Component} possibleDescendant The Component to test for presence + * within this Component's subtree. + */ + isAncestor: function(possibleDescendant) { + while (possibleDescendant) { + if (possibleDescendant.getRefOwner() === this) { + return true; + } + possibleDescendant = possibleDescendant.getRefOwner(); + } + return false; + }, + /** + * This method is called to initialize the `inheritedState` objects for this instance. + * This amounts to typically copying certain properties from the instance to the given + * object. + * + * @param {Object} inheritedState The state object for this instance. + * @param {Object} [inheritedStateInner] This object is only provided for containers. + * @method initInheritedState + * @protected + * @since 5.0.0 + */ + /** + * This method marks the current inherited state as invalid. The next time a call is + * made to `getInherited` the objects will be recreated and initialized. + * @private + * @since 5.0.0 + */ + invalidateInheritedState: function() { + var inheritedState = this.inheritedState; + if (inheritedState) { + // if component has a inheritedState at this point we set an invalid flag in + // the inheritedState so descendants of this component know to re-initialize + // their inheritedState the next time it is requested (see getInherited()) + inheritedState.invalid = true; + // We can now delete the old inheritedState since it is invalid. IMPORTANT: + // the descendants are still linked to the old inheritedState via the + // prototype chain, and their inheritedState property will be synced up + // the next time their getInherited() method is called. For this reason + // inheritedState should always be accessed using getInherited() + delete this.inheritedState; + } + }, + privates: { + _fixName: function() { + var me = this, + owner; + if (me.name) { + owner = me.lookupNameHolder(); + if (owner && !owner.destroyed) { + owner.attachNameRef(me); + } + } + }, + /** + * Sets up a reference on our current reference holder. + * + * @private + */ + _fixReference: function() { + var me = this, + refHolder; + if (me.reference) { + refHolder = me.lookupReferenceHolder(); + if (refHolder) { + refHolder.attachReference(me); + } + } + }, + /** + * Called when this Inheritable is added to a parent + * @param parent + * @param {Boolean} instanced + */ + onInheritedAdd: function(parent, instanced) { + var me = this; + // The container constructed us, so it's not possible for our + // inheritedState to be invalid, so we only need to clear it + // if we've been added as an instance + if (me.inheritedState && instanced) { + me.invalidateInheritedState(); + } + if (me.name || me.reference) { + Ext.ComponentManager.markReferencesDirty(); + } + }, + /** + * Called when this inheritable is removed from a parent + * @param {Boolean} destroying `true` if this item will be destroyed by it's container + */ + onInheritedRemove: function(destroying) { + var me = this; + if (me.name || me.reference) { + Ext.ComponentManager.markReferencesDirty(); + } + if (me.inheritedState && !destroying) { + me.invalidateInheritedState(); + } + } + } +}, function() { + /** + * @property {Object} rootInheritedState + * The top level inheritedState to which all other inheritedStates are chained. If + * there is a `Viewport` instance, this object becomes the Viewport's inheritedState. + * See also {@link Ext.Component#getInherited}. + * + * @private + * @member Ext + * @since 5.0.0 + */ + Ext.rootInheritedState = {}; +}); + +/** + * This class is intended as a mixin for classes that want to provide a "bind" config that + * connects to a `ViewModel`. + * @private + * @since 5.0.0 + */ +Ext.define('Ext.mixin.Bindable', { + mixinId: 'bindable', + config: { + /** + * @cfg {Object/String} [bind] + * Setting this config option adds or removes data bindings for other configs. + * For example, to bind the `title` config: + * + * var panel = Ext.create({ + * xtype: 'panel', + * bind: { + * title: 'Hello {user.name}' + * } + * }); + * + * To dynamically add bindings: + * + * panel.setBind({ + * title: 'Greetings {user.name}!' + * }); + * + * To remove bindings: + * + * panel.setBind({ + * title: null + * }); + * + * The bind expressions are presented to `{@link Ext.app.ViewModel#bind}`. The + * `ViewModel` instance is determined by `lookupViewModel`. + * + * **Note:** If bind is passed as a string, it will use the {@link Ext.Component#property-defaultBindProperty} + * for the binding. + */ + bind: { + $value: null, + lazy: true + }, + // @cmd-auto-dependency { aliasPrefix: 'controller.' } + /** + * @cfg {String/Object/Ext.app.ViewController} controller + * A string alias, a configuration object or an instance of a `ViewController` for + * this container. Sample usage: + * + * Ext.define('MyApp.UserController', { + * alias: 'controller.user' + * }); + * + * Ext.define('UserContainer', { + * extend: 'Ext.container.container', + * controller: 'user' + * }); + * // Or + * Ext.define('UserContainer', { + * extend: 'Ext.container.container', + * controller: { + * type: 'user', + * someConfig: true + * } + * }); + * + * // Can also instance at runtime + * var ctrl = new MyApp.UserController(); + * var view = new UserContainer({ + * controller: ctrl + * }); + * + */ + controller: null, + /** + * @method getController + * Returns the {@link Ext.app.ViewController} instance associated with this + * component via the {@link #controller} config or {@link #setController} method. + * @return {Ext.app.ViewController} Returns this component's ViewController or + * null if one was not configured + */ + /** + * @cfg {Boolean} defaultListenerScope + * If `true`, this component will be the default scope (this pointer) for events + * specified with string names so that the scope can be dynamically resolved. The + * component will automatically become the defaultListenerScope if a + * {@link #controller} is specified. + * + * See the introductory docs for {@link Ext.container.Container} for some sample + * usages. + * + * **NOTE**: This value can only be reliably set at construction time. Setting it + * after that time may not correctly rewire all of the potentially effected + * listeners. + */ + defaultListenerScope: false, + /** + * @cfg {String/String[]/Object} publishes + * One or more names of config properties that this component should publish + * to its ViewModel. Generally speaking, only properties defined in a class config + * block (including ancestor config blocks and mixins) are eligible for publishing + * to the viewModel. Some components override this and publish their most useful + * configs by default. + * + * **Note:** We'll discuss publishing properties **not** found in the config block below. + * + * Values determined to be invalid by component (often form fields and model validations) + * will not be published to the ViewModel. + * + * This config uses the `{@link #cfg-reference}` to determine the name of the data + * object to place in the `ViewModel`. If `reference` is not set then this config + * is ignored. + * + * By using this config and `{@link #cfg-reference}` you can bind configs between + * components. For example: + * + * ... + * items: [{ + * xtype: 'textfield', + * reference: 'somefield', // component's name in the ViewModel + * publishes: 'value' // value is not published by default + * },{ + * ... + * },{ + * xtype: 'displayfield', + * bind: 'You have entered "{somefield.value}"' + * }] + * ... + * + * Classes must provide this config as an Object: + * + * Ext.define('App.foo.Bar', { + * publishes: { + * foo: true, + * bar: true + * } + * }); + * + * This is required for the config system to properly merge values from derived + * classes. + * + * For instances this value can be specified as a value as show above or an array + * or object as follows: + * + * { + * xtype: 'textfield', + * reference: 'somefield', + * publishes: [ + * 'value', + * 'rawValue', + * 'dirty' + * ] + * } + * + * // This achieves the same result as the above array form. + * { + * xtype: 'textfield', + * reference: 'somefield', + * publishes: { + * value: true, + * rawValue: true, + * dirty: true + * } + * } + * + * In some cases, users may want to publish a property to the viewModel that is not found in a class + * config block. In these situations, you may utilize {@link #publishState} if the property has a + * setter method. Let's use {@link Ext.form.Labelable#setFieldLabel setFieldLabel} as an example: + * + * setFieldLabel: function(fieldLabel) { + * this.callParent(arguments); + * this.publishState('fieldLabel', fieldLabel); + * } + * + * With the above chunk of code, fieldLabel may now be published to the viewModel. + * + * @since 5.0.0 + */ + publishes: { + $value: null, + lazy: true, + merge: function(newValue, oldValue) { + return this.mergeSets(newValue, oldValue); + } + }, + // @cmd-auto-dependency { directRef: 'Ext.data.Session' } + /** + * @cfg {Boolean/Object/Ext.data.Session} [session=null] + * If provided this creates a new `Session` instance for this component. If this + * is a `Container`, this will then be inherited by all child components. + * + * To create a new session you can specify `true`: + * + * Ext.create({ + * xtype: 'viewport', + * session: true, + * + * items: [{ + * ... + * }] + * }); + * + * Alternatively, a config object can be provided: + * + * Ext.create({ + * xtype: 'viewport', + * session: { + * ... + * }, + * + * items: [{ + * ... + * }] + * }); + * + */ + session: { + $value: null, + lazy: true + }, + /** + * @cfg {String/String[]/Object} twoWayBindable + * This object holds a map of `config` properties that will update their binding + * as they are modified. For example, `value` is a key added by form fields. The + * form of this config is the same as `{@link #cfg!publishes}`. + * + * This config is defined so that updaters are not created and added for all + * bound properties since most cannot be modified by the end-user and hence are + * not appropriate for two-way binding. + */ + twoWayBindable: { + $value: null, + lazy: true, + merge: function(newValue, oldValue) { + return this.mergeSets(newValue, oldValue); + } + }, + // @cmd-auto-dependency { aliasPrefix: 'viewmodel.', defaultType: 'default' } + /** + * @cfg {String/Object/Ext.app.ViewModel} viewModel + * The `ViewModel` is a data provider for this component and its children. The + * data contained in the `ViewModel` is typically used by adding `bind` configs + * to the components that want present or edit this data. + * + * When set, the `ViewModel` is created and links to any inherited `viewModel` + * instance from an ancestor container as the "parent". The `ViewModel` hierarchy, + * once established, only supports creation or destruction of children. The + * parent of a `ViewModel` cannot be changed on the fly. + * + * If this is a root-level `ViewModel`, the data model connection is made to this + * component's associated `{@link Ext.data.Session Data Session}`. This is + * determined by calling `getInheritedSession`. + * + */ + viewModel: { + $value: null, + lazy: true + } + }, + /** + * @property {String} [defaultBindProperty] + * This property is used to determine the property of a `bind` config that is just + * the value. For example, if `defaultBindProperty="value"`, then this shorthand + * `bind` config: + * + * bind: '{name}' + * + * Is equivalent to this object form: + * + * bind: { + * value: '{name}' + * } + * + * The `defaultBindProperty` is set to "value" for form fields and to "store" for + * grids and trees. + * @protected + */ + defaultBindProperty: null, + /** + * @cfg {Boolean} nameable + * Set to `true` for this component's `name` property to be tracked by its containing + * `nameHolder`. + */ + nameable: false, + /** + * @cfg {Boolean} shareableName + * Set to `true` to allow this component's `name` to be shared by other items in the + * same `nameHolder`. Such items will be returned in an array from `lookupName`. + */ + shareableName: false, + /** + * @cfg {String} reference + * Specifies a name for this component inside its component hierarchy. This name + * must be unique within its {@link Ext.container.Container#referenceHolder view} + * or its {@link Ext.app.ViewController ViewController}. See the documentation in + * {@link Ext.container.Container} for more information about references. + * + * **Note**: Valid identifiers start with a letter or underscore and are followed + * by zero or more additional letters, underscores or digits. References are case + * sensitive. + */ + reference: null, + /** + * @property {RegExp} + * Regular expression used for validating `reference` values. + * @private + */ + validRefRe: /^[a-z_][a-z0-9_]*$/i, + getReference: function() { + // Maintained for compatibility with <7 where reference used the config system + return this.reference; + }, + /** + * Called by `getInherited` to initialize the inheritedState the first time it is + * requested. + * @protected + */ + initInheritedState: function(inheritedState) { + var me = this, + reference = me.reference, + controller = me.getController(), + // Don't instantiate the view model here, we only need to know that + // it exists + viewModel = me.getConfig('viewModel', true), + session = me.getConfig('session', true), + defaultListenerScope = me.getDefaultListenerScope(); + if (controller) { + inheritedState.controller = controller; + } + if (defaultListenerScope) { + inheritedState.defaultListenerScope = me; + } else if (controller) { + inheritedState.defaultListenerScope = controller; + } + if (viewModel) { + // If we're not configured with an instance, just stamp the current component as + // the thing that holds the view model. When we ask to get the inherited view model, + // we will know that it's not an instance yet so we need to spin it up on this component. + // We need to initialize them from top-down, but we don't want to do it up front. + if (!viewModel.isViewModel) { + viewModel = me; + } + inheritedState.viewModel = viewModel; + } + // Same checks as the view model + if (session) { + if (!session.isSession) { + session = me; + } + inheritedState.session = session; + } + if (reference) { + me.referenceKey = (inheritedState.referencePath || '') + reference; + me.viewModelKey = (inheritedState.viewModelPath || '') + reference; + } + }, + /** + * Determines if the passed property name is bound to ViewModel data. + * @param {String} [name] The property name to test. Defaults to the {@link #defaultBindProperty} + * @returns {Boolean} `true` if the passed property receives data from a ViewModel. + * @since 6.5.0 + */ + isBound: function(name) { + var bind = this.getBind(); + return !!(bind && (bind[name || this.defaultBindProperty])); + }, + /** + * Gets the controller that controls this view. May be a controller that belongs + * to a view higher in the hierarchy. + * + * @param {Boolean} [skipThis=false] `true` to not consider the controller directly attached + * to this view (if it exists). + * @return {Ext.app.ViewController} The controller. `null` if no controller is found. + * + * @since 5.0.1 + */ + lookupController: function(skipThis) { + return this.getInheritedConfig('controller', skipThis) || null; + }, + /** + * Returns the `Ext.data.Session` for this instance. This property may come + * from this instance's `{@link #session}` or be inherited from this object's parent. + * @param {Boolean} [skipThis=false] Pass `true` to ignore a `session` configured on + * this instance and only consider an inherited session. + * @return {Ext.data.Session} + * @since 5.0.0 + */ + lookupSession: function(skipThis) { + // See lookupViewModel + var ret = skipThis ? null : this.getSession(); + // may be the initGetter! + if (!ret) { + ret = this.getInheritedConfig('session', skipThis); + if (ret && !ret.isSession) { + ret = ret.getInherited().session = ret.getSession(); + } + } + return ret || null; + }, + /** + * Returns the `Ext.app.ViewModel` for this instance. This property may come from this + * this instance's `{@link #viewModel}` or be inherited from this object's parent. + * @param {Boolean} [skipThis=false] Pass `true` to ignore a `viewModel` configured on + * this instance and only consider an inherited view model. + * @return {Ext.app.ViewModel} + * @since 5.0.0 + */ + lookupViewModel: function(skipThis) { + var ret = skipThis ? null : this.getViewModel(); + // may be the initGetter! + if (!ret) { + ret = this.getInheritedConfig('viewModel', skipThis); + // If what we get back is a component, it means the component was configured + // with a view model, however the construction of it has been delayed until + // we need it. As such, go and construct it and store it on the inherited state. + if (ret && !ret.isViewModel) { + ret = ret.getInherited().viewModel = ret.getViewModel(); + } + } + return ret || null; + }, + /** + * Publish this components state to the `ViewModel`. If no arguments are given (or if + * this is the first call), the entire state is published. This state is determined by + * the `publishes` property. + * + * This method is called only by component authors. + * + * @param {String} [property] The name of the property to update. + * @param {Object} [value] The value of `property`. Only needed if `property` is given. + * @protected + * @since 5.0.0 + */ + publishState: function(property, value) { + var me = this, + state = me.publishedState, + binds = me.getBind(), + binding = binds && property && binds[property], + count = 0, + name, publishes, vm, path; + if (!(arguments.length === 0 || arguments.length === 2)) { + Ext.raise('publishState must either be called with no args, or with both name AND value passed'); + } + if (binding && !binding.syncing && !binding.isReadOnly()) { + // If the binding has never fired & our value is either: + // a) undefined + // b) null + // c) The value we were initially configured with + // Then we don't want to publish it back to the view model. If we do, we'll be + // overwriting whatever is in the viewmodel and it will never have a chance to fire. + if (binding.calls || !(value == null || value === me.getInitialConfig()[property])) { + binding.setValue(value); + } + } + if (!(publishes = me.getPublishes())) { + return; + } + if (!(vm = me.lookupViewModel())) { + return; + } + // Important to access path after lookupViewModel, which will kick off + // our inheritedState if we don't have one + if (!(path = me.viewModelKey)) { + return; + } + state = state || (me.publishedState = {}); + if (property) { + if (!publishes[property]) { + return; + } + // If we are setting an individual property and that is not a {} or a [] then + // check to see if it is unchanged. + if (!(value && value.constructor === Object) && !(value instanceof Array)) { + if (state[property] === value) { + return; + } + } + path += '.'; + path += property; + } else { + for (name in publishes) { + ++count; + state[name] = me.getConfig(name); + } + if (!count) { + // if (no properties were put in "state") + return; + } + value = state; + } + vm.set(path, value); + }, + //========================================================================= + privates: { + /** + * Ensures that the given property (if it is a Config System config) has a proper + * "updater" method on this instance to sync changes to the config. + * @param {String} property The name of the config property. + * @private + * @since 5.0.0 + */ + addBindableUpdater: function(property) { + var me = this, + configs = me.self.$config.configs, + cfg = configs[property], + updateName; + // While we store the updater on this instance, the function is cached and + // re-used across all instances. + if (cfg && !me.hasOwnProperty(updateName = cfg.names.update)) { + me[updateName] = cfg.bindableUpdater || (cfg.root.bindableUpdater = me.makeBindableUpdater(cfg)); + } + }, + /** + * @param {String/Object} binds + * @param {Object} currentBindings + * @return {Object} + * @private + * @since 5.0.0 + */ + applyBind: function(binds, currentBindings) { + if (!binds) { + return binds; + } + var me = this, + viewModel = me.lookupViewModel(), + twoWayable = me.getTwoWayBindable(), + getBindTemplateScope = me._getBindTemplateScope, + b, property, descriptor, destroy; + me.$hasBinds = true; + if (!currentBindings || typeof currentBindings === 'string') { + currentBindings = {}; + } + if (!viewModel) { + Ext.raise('Cannot use bind config without a viewModel'); + } + if (Ext.isString(binds)) { + if (!me.defaultBindProperty) { + Ext.raise(me.$className + ' has no defaultBindProperty - ' + 'Please specify a bind object'); + } + b = binds; + binds = {}; + binds[me.defaultBindProperty] = b; + } + for (property in binds) { + descriptor = binds[property]; + b = currentBindings[property]; + if (b && b.isBinding) { + b.destroy(); + b = null; + destroy = true; + } + if (descriptor) { + b = viewModel.bind(descriptor, me.onBindNotify, me); + b._config = Ext.Config.get(property); + b.getTemplateScope = getBindTemplateScope; + if (!me[b._config.names.set]) { + Ext.raise('Cannot bind ' + property + ' on ' + me.$className + ' - missing a ' + b._config.names.set + ' method.'); + } + } + if (destroy) { + delete currentBindings[property]; + } else { + currentBindings[property] = b; + } + if (twoWayable && twoWayable[property]) { + if (destroy) { + me.clearBindableUpdater(property); + } else if (!b.isReadOnly()) { + me.addBindableUpdater(property); + } + } + } + return currentBindings; + }, + applyController: function(controller) { + if (controller) { + controller = Ext.Factory.controller(controller); + controller.setView(this); + } + // In classic, this is a no-op, in modern it will + // save a local reference + this.controller = controller; + return controller; + }, + updatePublishes: function(all) { + var me = this; + if (me.lookupViewModel()) { + for (var property in all) { + me.addBindableUpdater(property); + } + } + return all; + }, + /** + * Transforms a Session config to a proper instance. + * @param {Object} session + * @return {Ext.data.Session} + * @private + * @since 5.0.0 + */ + applySession: function(session) { + if (!session) { + return null; + } + if (!session.isSession) { + var parentSession = this.lookupSession(true), + // skip this component + config = (session === true) ? {} : session; + if (parentSession) { + session = parentSession.spawn(config); + } else { + // Mask this use of Session from Cmd - the dependency is not ours but + // the caller + session = new Ext.data['Session'](config); + } + } + return session; + }, + /** + * Transforms a ViewModel config to a proper instance. + * @param {String/Object/Ext.app.ViewModel} viewModel + * @return {Ext.app.ViewModel} + * @private + * @since 5.0.0 + */ + applyViewModel: function(viewModel) { + var me = this, + config, session; + if (!viewModel) { + return null; + } + if (!viewModel.isViewModel) { + config = { + parent: me.lookupViewModel(true), + // skip this component + // Ensure that VM construction activity can reach the view (for + // example events on stores) + view: me + }; + config.session = me.getSession(); + if (!session && !config.parent) { + config.session = me.lookupSession(); + } + if (viewModel) { + if (viewModel.constructor === Object) { + Ext.apply(config, viewModel); + } else if (typeof viewModel === 'string') { + config.type = viewModel; + } + } + viewModel = Ext.Factory.viewModel(config); + } + return viewModel; + }, + _getBindTemplateScope: function() { + // This method is called as a method on a Binding instance, so the "this" pointer + // is that of the Binding. The "scope" of the Binding is the component owning it. + return this.scope.resolveListenerScope(); + }, + clearBindableUpdater: function(property) { + var me = this, + configs = me.self.$config.configs, + cfg = configs[property], + updateName; + if (cfg && me.hasOwnProperty(updateName = cfg.names.update)) { + if (me[updateName].$bindableUpdater) { + delete me[updateName]; + } + } + }, + destroyBindable: function() { + var me = this, + viewModel = me.getConfig('viewModel', true), + session = me.getConfig('session', true), + controller = me.getController(); + if (viewModel && viewModel.isViewModel) { + viewModel.destroy(); + me.setViewModel(null); + } + if (session && session.isSession) { + if (session.getAutoDestroy()) { + session.destroy(); + } + me.setSession(null); + } + if (controller) { + me.setController(null); + controller.destroy(); + } + }, + /** + * This method triggers the lazy configs and must be called when it is time to + * fully boot up. The configs that must be initialized are: `bind`, `publishes`, + * `session`, `twoWayBindable` and `viewModel`. + * @private + * @since 5.0.0 + */ + initBindable: function() { + var me = this, + controller = me.controller; + me.initBindable = Ext.emptyFn; + me.getBind(); + me.getPublishes(); + // If we have binds, the applyBind method will call getTwoWayBindable to ensure + // we have the necessary updaters. If we have no binds then applyBind will not + // be called and we will ignore our twoWayBindable config (which is fine). + // + // If we have publishes or binds then the viewModel will be requested. + if (!me.viewModel) { + // Force VM creation now + me.getViewModel(); + } + if (controller) { + controller.initBindings(); + } + if (me.reference) { + // If we have no "reference" config then we do not publish our state to the + // viewmodel. + me.publishState(); + } + }, + /** + * Checks if a particular binding is synchronizing the value. + * @param {String} name The name of the property being bound to. + * @return {Boolean} `true` if the binding is syncing. + * + * @private + */ + isSyncing: function(name) { + var bindings = this.getBind(), + ret = false, + binding; + if (bindings) { + binding = bindings[name]; + if (binding) { + ret = binding.syncing > 0; + } + } + return ret; + }, + /** + * Returns an `update` method for the given Config that will call `{@link #publishState}` + * to ensure two-way bindings (via `bind`) as well as any `publishes` are updated. + * This method is cached on the `cfg` instance for re-use. + * @param {Ext.Config} cfg + * @return {Function} The updater function. + * @private + * @since 5.0.0 + */ + makeBindableUpdater: function(cfg) { + var updateName = cfg.names.update, + fn = function(newValue, oldValue) { + var me = this, + updater = me.self.prototype[updateName]; + if (updater) { + updater.call(me, newValue, oldValue); + } + // Regather the property value in case the updater mutated it + me.publishState(cfg.name, me[cfg.getInternalName(me)]); + }; + fn.$bindableUpdater = true; + return fn; + }, + notifyIf: function(skipThis) { + var vm = this.lookupViewModel(skipThis); + if (vm) { + vm.notify(); + } + }, + onBindNotify: function(value, oldValue, binding) { + binding.syncing = (binding.syncing + 1) || 1; + this[binding._config.names.set](value); + --binding.syncing; + }, + removeBindings: function() { + var me = this, + bindings, key, binding; + if (me.$hasBinds) { + bindings = me.getBind(); + if (bindings && typeof bindings !== 'string') { + for (key in bindings) { + binding = bindings[key]; + binding.destroy(); + binding._config = binding.getTemplateScope = null; + } + } + } + me.setBind(null); + }, + /** + * Updates the session config. + * @param {Ext.data.Session} session + * @private + */ + updateSession: function(session) { + var state = this.getInherited(); + if (session) { + state.session = session; + } else { + delete state.session; + } + }, + /** + * Updates the viewModel config. + * @param {Ext.app.ViewModel} viewModel + * @param {Ext.app.ViewModel} oldViewModel + * @private + */ + updateViewModel: function(viewModel, oldViewModel) { + var me = this, + state = me.getInherited(), + controller = me.getController(); + if (viewModel) { + me.hasVM = true; + state.viewModel = viewModel; + viewModel.setView(me); + if (controller) { + controller.initViewModel(viewModel); + } + } else { + delete state.viewModel; + } + // In classic, this is a no-op, in modern it will + // save a local reference + me.viewModel = viewModel; + } + } +}); +// private + +/** + * A mixin that gives Ext.Component and Ext.Widget the ability to process the "delegate" + * event option. + * @private + */ +Ext.define('Ext.mixin.ComponentDelegation', { + extend: 'Ext.Mixin', + mixinConfig: { + id: 'componentDelegation' + }, + privates: { + /** + * @private + * Adds a listeners with the "delegate" event option. Users should not invoke this + * method directly. Use the "delegate" event option of + * {@link Ext.util.Observable#addListener addListener} instead. + */ + addDelegatedListener: function(eventName, fn, scope, options, order, caller, manager) { + var me = this, + delegatedEvents, event, priority; + eventName = Ext.canonicalEventName(eventName); + // The following processing of the "order" option is typically done by the + // doAddListener method of Ext.mixin.Observable, but that method does not + // get called when adding a delegated listener, so we must do the conversion + // of order to priority here. + order = order || options.order; + if (order) { + priority = (options && options.priority); + if (!priority) { + // priority option takes precedence over order + // do not mutate the user's options + options = options ? Ext.Object.chain(options) : {}; + options.priority = me.$orderToPriority[order]; + } + } + if (options.target) { + Ext.raise("Cannot add '" + eventName + "' listener to component: '" + me.id + "' - 'delegate' and 'target' event options are incompatible."); + } + // Delegated events are tracked in a map keyed by event name, where the values + // are instances of Ext.util.Event that track all of the delegate listeners + // for the given event name. + delegatedEvents = me.$delegatedEvents || (me.$delegatedEvents = {}); + event = delegatedEvents[eventName] || (delegatedEvents[eventName] = new Ext.util.Event(me, eventName)); + if (event.addListener(fn, scope, options, caller, manager)) { + me.$hasDelegatedListeners._incr_(eventName); + } + }, + /** + * @private + * Clears all listeners that were attached using the "delegate" event option. + * Users should not invoke this method directly. It is called automatically as + * part of normal {@link Ext.util.Observable#clearListeners clearListeners} + * processing. + */ + clearDelegatedListeners: function() { + var me = this, + delegatedEvents = me.$delegatedEvents, + eventName, event, listenerCount; + if (delegatedEvents) { + for (eventName in delegatedEvents) { + event = delegatedEvents[eventName]; + listenerCount = event.listeners.length; + event.clearListeners(); + me.$hasDelegatedListeners._decr_(eventName, listenerCount); + delete delegatedEvents[eventName]; + } + } + }, + /** + * @private + * Fires a delegated event. Users should not invoke this method directly. It + * is called automatically by the framework as needed (see the "delegate" event + * option of {@link Ext.util.Observable#addListener addListener} for more + * details. + */ + doFireDelegatedEvent: function(eventName, args) { + var me = this, + ret = true, + owner, delegatedEvents, event; + // NOTE: $hasDelegatedListeners exists on the prototype of this mixin + // which means it is inherited by both Ext.Component and Ext.Widget + // This means that if any Component in the universe is listening for + // the given eventName in a delegated manner, we need to traverse up the + // hierarchy to see if that Component is in fact our ancestor, and if so + // we need to fire the event on the ancestor. + if (me.$hasDelegatedListeners[eventName]) { + owner = me.getRefOwner(); + while (owner) { + delegatedEvents = owner.$delegatedEvents; + if (delegatedEvents) { + event = delegatedEvents[eventName]; + if (event) { + ret = event.fireDelegated(me, args); + if (ret === false) { + break; + } + } + } + owner = owner.getRefOwner(); + } + } + return ret; + }, + /** + * @private + * Removes delegated listeners for a given eventName, function, and scope. + * Users should not invoke this method directly. It is called automatically by + * the framework as part of {@link #removeListener} processing. + */ + removeDelegatedListener: function(eventName, fn, scope) { + var me = this, + delegatedEvents = me.$delegatedEvents, + event; + if (delegatedEvents) { + event = delegatedEvents[eventName]; + if (event && event.removeListener(fn, scope)) { + me.$hasDelegatedListeners._decr_(eventName); + if (event.listeners.length === 0) { + delete delegatedEvents[eventName]; + } + } + } + }, + destroyComponentDelegation: function() { + if (this.clearPropertiesOnDestroy) { + this.$delegatedEvents = null; + } + } + }, + onClassMixedIn: function(T) { + // When a Component listener is attached with the "delegate" option, it means + // All components anywhere in the hierarchy MUST now fire the event just in case + // the Component with the delegate listener is an ancestor of the component that + // fired the event (otherwise the ancestor will not have a chance to intercept + // and process the event - see doFireDelegatedEvent). To ensure that this happens + // we chain the class-level hasListeners object of Ext.Component and Ext.Widget + // to the single $hasDelegatedListeners object (see class-creation callback + // of this class for more info) + function HasListeners() {} + T.prototype.HasListeners = T.HasListeners = HasListeners; + HasListeners.prototype = T.hasListeners = new Ext.mixin.ComponentDelegation.HasDelegatedListeners(); + } +}, function(ComponentDelegation) { + // Here We set up a HasListeners instance ($hasDelegatedListeners) that will be incremented + // and decremented any time a Component or Widget adds or removes a listener using the + // "delegate" event option. This HasListeners instance is stored on the prototype + // of the ComponentDelegation mixin, and therefore will be applied to the prototype + // of both Ext.Component and Ext.Widget. This means that Ext.Widget and Ext.Component + // (intentionally) share the same $hasDelegatedListeners instance. To understand the + // reason for this common instance one must first understand how delegated events are + // fired: + // + // When any component or widget fires an event of any kind, it must call doFireDelegatedEvent + // to process possible delegated listeners. The implementation of doFireDelegatedEvent + // traverses up the component hierarchy searching for any ancestors that may be listening + // for the event in a delegated manner; however, this traversal of the hierarchy can + // be skipped if there are no known Components with delegated listeners for the given event. + // The $hasDelegatedListeners instance is used to track whether or not there are any + // delegated listeners for the given event name for this purpose. Since Ext.Widgets + // and Ext.Components can be part of the same hierarchy they must share the same + // $hasDelegatesListeners instance. + function HasDelegatedListeners() {} + ComponentDelegation.HasDelegatedListeners = HasDelegatedListeners; + HasDelegatedListeners.prototype = ComponentDelegation.prototype.$hasDelegatedListeners = new Ext.mixin.Observable.HasListeners(); +}); + +/** + * This is the base class from which all plugins should extend. + * + * This class defines the essential API of plugins as used by Components by defining the + * following methods: + * + * - `init` : The plugin initialization method which the host Component calls during + * Component initialization. The Component passes itself as the sole parameter. + * Subclasses should set up bidirectional links between the plugin and its host + * Component here. + * + * - `destroy` : The plugin cleanup method which the host Component calls at Component + * destruction time. Use this method to break links between the plugin and the + * Component and to free any allocated resources. + */ +Ext.define('Ext.plugin.Abstract', { + alternateClassName: 'Ext.AbstractPlugin', + /** + * @property {Boolean} isPlugin + * The value `true` to identify objects of this class or a subclass thereof. + * @readonly + */ + isPlugin: true, + /** + * Initializes the plugin. + * @param {Object} [config] Configuration object. + */ + constructor: function(config) { + if (config) { + this.pluginConfig = config; + this.initConfig(config); + } + }, + /** + * Creates clone of the plugin. + * @param {Object} [overrideCfg] Additional config for the derived plugin. + */ + clonePlugin: function(overrideCfg) { + return new this.self(Ext.apply({}, overrideCfg, this.pluginConfig)); + }, + /** + * @method detachCmp + * Plugins that can be disconnected from their host component should implement + * this method. + * @since 6.2.0 + */ + /** + * Returns the component to which this plugin is attached. + * @return {Ext.Component} The owning host component. + */ + getCmp: function() { + return this.cmp; + }, + /** + * Sets the host component to which this plugin is attached. For a plugin to be + * removable without being destroyed, this method should be provided and be prepared + * to receive `null` for the component. + * @param {Ext.Component} host The owning host component. + */ + setCmp: function(host) { + this.cmp = host; + }, + /** + * @cfg {String} id + * An identifier for the plugin that can be set at creation time to later retrieve the + * plugin using the {@link #getPlugin getPlugin} method. For example: + * + * var panel = Ext.create({ + * xtype: 'panel', + * + * plugins: { + * foobar: { + * id: 'foo', + * ... + * } + * } + * }); + * + * // later on: + * var plugin = panel.getPlugin('foo'); + * @since 6.2.0 + */ + /** + * @cfg {String} pluginId + * @deprecated 6.2.0 Use `id` instead + */ + /** + * @method init + * The init method is invoked to formally associate the host component and the plugin. + * + * Subclasses should perform initialization and set up any requires links between the + * plugin and its host Component in their own implementation of this method. + * @param {Ext.Component} host The host Component which owns this plugin. + */ + init: Ext.emptyFn, + /** + * @method destroy + * + * The destroy method is invoked by the owning Component at the time the Component is + * being destroyed. + */ + destroy: function() { + this.cmp = this.pluginConfig = null; + this.callParent(); + }, + onClassExtended: function(cls, data, hooks) { + var alias = data.alias, + prototype = cls.prototype; + // Inject a ptype property so that findPlugin() works. + if (alias && !data.ptype) { + if (Ext.isArray(alias)) { + alias = alias[0]; + } + prototype.ptype = alias.split('plugin.')[1]; + } + }, + resolveListenerScope: function(defaultScope) { + var me = this, + cmp = me.getCmp(), + scope; + if (cmp) { + scope = cmp.resolveSatelliteListenerScope(me, defaultScope); + } + // If this method was called, it means the plugin subclass must + // have mixed in Observable, so we can rely on there being + // a "this.mixins.observable" even though Ext.plugin.Abstract + // does not mix it in directly + return scope || me.mixins.observable.resolveListenerScope.call(me, defaultScope); + }, + statics: { + decode: function(plugins, typeProp, include) { + if (plugins) { + var type = Ext.typeOf(plugins), + // 'object', 'array', 'string' + entry, key, obj, value; + if (type === 'string') { + obj = {}; + // allows for findPlugin to find a plugin + // defined as a string + obj[typeProp] = plugins; + plugins = [ + obj + ]; + } else if (plugins.isInstance) { + plugins = [ + plugins + ]; + } else if (type === 'object') { + if (plugins[typeProp]) { + plugins = [ + plugins + ]; + } else { + obj = include ? Ext.merge(Ext.clone(include), plugins) : plugins; + plugins = []; + for (key in obj) { + if (!(value = obj[key])) { + + continue; + } + entry = { + id: key + }; + entry[typeProp] = key; + if (key === 'responsive') { + entry.weight = -1000; + } + Ext.apply(entry, value); + plugins.push(entry); + } + plugins.sort(Ext.weightSortFn); + } + } else if (type !== 'array') { + Ext.raise('Invalid value for "plugins" config ("' + type + '"'); + } else { + plugins = plugins.slice(); + } + } + // so that all cases return mutable array + return plugins; + } + } +}); + +/** + * @class Ext.plugin.Abstract + */ +Ext.define('Ext.overrides.plugin.Abstract', { + override: 'Ext.plugin.Abstract', + $configStrict: false, + $configPrefixed: false, + disabled: false, + /** + * @cfg {String|Array} stateEvents + * The configured list of stateEvents used to (optionally) participate in Owner Component's state management. + * @member Ext.plugin.Abstract + */ + /** + * @method + * The getState method is invoked by the client Component's State mixin when one or more of the the specified {@link #stateEvents} are raised. + * + * The supplied implementation is empty. If plugin Subclasses are to (optionally) participate in the client Component's + * state management, implementers should provide a suitable method which returns a state object. + * @return {Object} state + * @member Ext.plugin.Abstract + */ + getState: null, + /** + * @method + * The applyState method is invoked by the client Component's State mixin after initComponent method has been run for the client. + * + * The supplied implementation is empty. If plugin Subclasses are to (optionally) participate in the client Component's + * state management, implementers should provide a suitable method to utilize it. + * @param {Object} state The current plugin state object to be applied. + * @param {Object} allState The current aggregate state of the Component and all plugins. + * @member Ext.plugin.Abstract + */ + applyState: null, + /** + * The base implementation just sets the plugin's `disabled` flag to `false` + * + * Plugin subclasses which need more complex processing may implement an overriding implementation. + * @member Ext.plugin.Abstract + */ + enable: function() { + this.disabled = false; + }, + /** + * The base implementation just sets the plugin's `disabled` flag to `true` + * + * Plugin subclasses which need more complex processing may implement an overriding implementation. + * @member Ext.plugin.Abstract + */ + disable: function() { + this.disabled = true; + } +}); + +/** + * This mixin provides support for a `plugins` config and related API's. + * + * If this mixin is used for non-Components, the statements regarding the host being a + * Component can be translated accordingly. The only requirement on the user of this class + * is that the plugins actually used be appropriate for their host. + * + * While `Ext.Component` in the Classic Toolkit supports `plugins`, it does not use this + * class to provide that support. This is due to backwards compatibility in regard to + * timing changes this implementation would present. + * + * **Important:** To ensure plugins are destroyed, call `setPlugins(null)`. + * @protected + * @since 6.2.0 + */ +Ext.define('Ext.mixin.Pluggable', function(Pluggable) { + return { + requires: [ + 'Ext.plugin.Abstract' + ], + config: { + /** + * @cfg {Array/Ext.enums.Plugin/Object/Ext.plugin.Abstract} plugins + * This config describes one or more plugin config objects used to create plugin + * instances for this component. + * + * Plugins are a way to bundle and reuse custom functionality. Plugins should extend + * `Ext.plugin.Abstract` but technically the only requirement for a valid plugin + * is that it contain an `init` method that accepts a reference to its owner. Once + * a plugin is created, the owner will call the `init` method, passing a reference + * to itself. Each plugin can then call methods or respond to events on its owner + * as needed to provide its functionality. + * + * This config's value can take several different forms. + * + * The value can be a single string with the plugin's {@link Ext.enums.Plugin alias}: + * + * var list = Ext.create({ + * xtype: 'list', + * itemTpl: '
{title}
', + * store: 'Items', + * + * plugins: 'listpaging' + * }); + * + * In the above examples, the string "listpaging" is the type alias for + * `Ext.dataview.plugin.ListPaging`. The full alias includes the "plugin." prefix + * (i.e., 'plugin.listpaging'). + * + * The preferred form for multiple plugins or to configure plugins is the + * keyed-object form (new in version 6.5): + * + * var list = Ext.create({ + * xtype: 'list', + * itemTpl: '
{title}
', + * store: 'Items', + * + * plugins: { + * pullrefresh: true, + * listpaging: { + * autoPaging: true, + * weight: 10 + * } + * } + * }); + * + * The object keys are the `id`'s as well as the default type alias. This form + * allows the value of the `plugins` to be merged from base class to derived class + * and finally with the instance configuration. This allows classes to define a + * set of plugins that derived classes or instantiators can further configure or + * disable. This merge behavior is a feature of the + * {@link Ext.Class#cfg!config config system}. + * + * The `plugins` config can also be an array of plugin aliases (arrays are not + * merged so this form does not respect plugins defined by the class author): + * + * var list = Ext.create({ + * xtype: 'list', + * itemTpl: '
{title}
', + * store: 'Items', + * + * plugins: ['listpaging', 'pullrefresh'] + * }); + * + * An array can also contain elements that are config objects with a `type` + * property holding the type alias: + * + * var list = Ext.create({ + * xtype: 'list', + * itemTpl: '
{title}
', + * store: 'Items', + * + * plugins: ['pullrefresh', { + * type: 'listpaging', + * autoPaging: true + * }] + * }); + */ + plugins: null + }, + /** + * Adds a plugin. For example: + * + * list.addPlugin('pullrefresh'); + * + * Or: + * + * list.addPlugin({ + * type: 'pullrefresh', + * pullRefreshText: 'Pull to refresh...' + * }); + * + * @param {Object/String/Ext.plugin.Abstract} plugin The plugin or config object or + * alias to add. + * @since 6.2.0 + */ + addPlugin: function(plugin) { + var me = this, + plugins = me.getPlugins(); + if (plugins) { + plugin = me.createPlugin(plugin); + plugin.init(me); + plugins.push(plugin); + } else { + me.setPlugins(plugin); + plugin = me.getPlugins()[0]; + } + return plugin; + }, + /** + * Removes and destroys a plugin. + * + * **Note:** Not all plugins are designed to be removable. Consult the documentation + * for the specific plugin in question to be sure. + * @param {String/Ext.plugin.Abstract} plugin The plugin or its `id` to remove. + * @return {Ext.plugin.Abstract} plugin instance or `null` if not found. + * @since 6.2.0 + */ + destroyPlugin: function(plugin) { + return this.removePlugin(plugin, true); + }, + /** + * Retrieves plugin by its `type` alias. For example: + * + * var list = Ext.create({ + * xtype: 'list', + * itemTpl: '
{title}
', + * store: 'Items', + * + * plugins: ['listpaging', 'pullrefresh'] + * }); + * + * list.findPlugin('pullrefresh').setPullRefreshText('Pull to refresh...'); + * + * **Note:** See also {@link #getPlugin}. + * + * @param {String} type The Plugin's `type` as specified by the class's + * {@link Ext.Class#cfg-alias alias} configuration. + * @return {Ext.plugin.Abstract} plugin instance or `null` if not found. + * @since 6.2.0 + */ + findPlugin: function(type) { + var plugins = this.getPlugins(), + n = plugins && plugins.length, + i, plugin, ret; + for (i = 0; i < n && !ret; i++) { + plugin = plugins[i]; + // Classic used ptype forever, so support it too but Core/Modern just use + // type. + if (plugin.type === type || plugin.ptype === type) { + ret = plugin; + } + } + return ret || null; + }, + /** + * Retrieves a plugin by its `id`. + * + * var list = Ext.create({ + * xtype: 'list', + * itemTpl: '
{title}
', + * store: 'Items', + * + * plugins: [{ + * type: 'pullrefresh', + * id: 'foo' + * }] + * }); + * + * list.getPlugin('foo').setPullRefreshText('Pull to refresh...'); + * + * **Note:** See also {@link #findPlugin}. + * + * @param {String} id The `id` of the plugin. + * @return {Ext.plugin.Abstract} plugin instance or `null` if not found. + * @since 6.2.0 + */ + getPlugin: function(id) { + var plugins = this.getPlugins(), + n = plugins && plugins.length, + i, plugin, ret; + for (i = 0; i < n && !ret; i++) { + plugin = plugins[i]; + // Classic used pluginId, so support it too but Core/Modern just use id. + if (plugin.id === id || plugin.pluginId === id) { + ret = plugin; + } + } + return ret || null; + }, + /** + * Removes and (optionally) destroys a plugin. + * + * **Note:** Not all plugins are designed to be removable. Consult the documentation + * for the specific plugin in question to be sure. + * @param {String/Ext.plugin.Abstract} plugin The plugin or its `id` to remove. + * @param {Boolean} [destroy] Pass `true` to not call `destroy()` on the plugin. + * @return {Ext.plugin.Abstract} plugin instance or `null` if not found. + * @since 6.2.0 + */ + removePlugin: function(plugin, destroy) { + var plugins = this.getPlugins(), + i = plugins && plugins.length || 0, + p; + while (i-- > 0) { + p = plugins[i]; + if (p === plugin || p.id === plugin) { + plugins.splice(i, 1); + if (destroy) { + if (p.destroy) { + p.destroy(); + } + } else if (p.detachCmp) { + p.detachCmp(); + if (p.setCmp) { + p.setCmp(null); + } + } + break; + } + p = null; + } + return p; + }, + privates: { + statics: { + idSeed: 0 + }, + /** + * Creates a particular plugin type if defined in the `plugins` configuration. + * @param {String} type The `type` of the plugin. + * @return {Ext.plugin.Abstract} The plugin that was created. + * @private + * @since 6.2.0 + */ + activatePlugin: function(type) { + var me = this, + config = me.initialConfig, + plugins = config && config.plugins, + ret = null, + i, include, p; + if (plugins) { + include = me.config.plugins; + include = (include && typeof include === 'object') ? include : null; + plugins = Ext.plugin.Abstract.decode(plugins, 'type', include); + for (i = plugins.length; i-- > 0; ) { + p = plugins[i]; + if (p === type || p.type === type) { + me.initialConfig = config = Ext.apply({}, config); + config.plugins = plugins; + // switch over to our copy + // Put the instance in the plugins array so it will be included in + // the applyPlugins loop for normal processing of plugins. + plugins[i] = ret = me.createPlugin(p); + break; + } + } + } + return ret; + }, + /** + * Applier for the `plugins` config property. + * @param {String[]/Object[]/Ext.plugin.Abstract[]} plugins The new plugins to use. + * @param {Ext.plugin.Abstract[]} oldPlugins The existing plugins in use. + * @private + */ + applyPlugins: function(plugins, oldPlugins) { + var me = this, + oldCount = oldPlugins && oldPlugins.length || 0, + count, i, plugin; + // Ensure we have an array if we got a single thing or a copy of the array + // if we got an array. + if (plugins) { + plugins = Ext.plugin.Abstract.decode(plugins, 'type'); + } + // We need to destroy() old plugins that aren't being brought forward in + // the new array... + // + for (i = 0; i < oldCount; ++i) { + oldPlugins[i].$dead = true; + } + // so paint the old ones + // Pass #1 (For historical reasons): Create all of the plugins. Prior versions + // did this pass first then called init() so we preserve the timings and do + // the same. + // + count = plugins && plugins.length || 0; + for (i = 0; i < count; ++i) { + plugins[i] = me.createPlugin(plugins[i]); + } + // ensure we have an instance + // Pass #2: Initialize the plugins that have not been and clear $dead for + // any returning for the next round. + // + for (i = 0; i < count; ++i) { + plugin = plugins[i]; + if (plugin.$dead) { + // if (it was in oldPlugins) + delete plugin.$dead; + } else // unpaint it (it's a keeper) + { + plugin.init(me); + } + } + // this one is new to the party + // Now we can teardown any plugins that aren't coming back. + // + for (i = 0; i < oldCount; ++i) { + if ((plugin = oldPlugins[i]).$dead) { + delete plugin.$dead; + Ext.destroy(plugin); + } + } + return plugins; + }, + /** + * Converts the provided type or config object into a plugin instance. + * @param {String/Object/Ext.plugin.Abstract} config The plugin type, config + * object or instance. + * @return {Ext.plugin.Abstract} + * @private + */ + createPlugin: function(config) { + if (typeof config === 'string') { + config = { + type: config + }; + } + var ret = config; + if (!config.isInstance) { + // The owner may be needed by plugin's initConfig so provide it: + config.cmp = this; + ret = Ext.factory(config, null, null, 'plugin'); + // Cleanup the user's config object: + delete config.cmp; + } + if (!ret.id) { + ret.id = ++Pluggable.idSeed; + } + if (ret.setCmp) { + ret.setCmp(this); + } + return ret; + } + } + }; +}); + +/** + * A mixin for components that need to interact with the keyboard. The primary config + * for this class is the `{@link #keyMap keyMap}` config. This config is an object + * with key names as its properties and with values that describe how the key event + * should be handled. + * + * Key names may key name as documented in `Ext.event.Event`, numbers (which are treated + * as `keyCode` values), single characters (for those that are not defined in + * `Ext.event.Event`) or `charCode` values prefixed by '#' (e.g., "#65" for `charCode=65`). + * + * Entries that use a `keyCode` will be processed in a `keydown` event listener, while + * those that use a `charCode` will be processed in `keypress`. This can be overridden + * if the `keyMap` entry specifies an `event` property. + * + * Key names may be preceded by key modifiers. The modifier keys can be specified + * by prepending the modifier name to the key name separated by `+` or `-` (e.g., + * "Ctrl+A" or "Ctrl-A"). Only one of these delimiters can be used in a given + * entry. + * + * Valid modifier names are: + * + * - Alt + * - Shift + * - Control (or "Ctrl" for short) + * - Command (or "Cmd" or "Meta") + * - CommandOrControl (or "CmdOrCtrl") for Cmd on Mac, Ctrl otherwise. + * + * *All these names are case insensitive and will be stored in upper case internally.* + * + * For example: + * + * Ext.define('MyChartPanel', { + * extend: 'Ext.panel.Panel', + * + * mixins: [ + * 'Ext.mixin.Keyboard' + * ], + * + * controller: 'mycontroller', + * + * // Map keys to methods (typically in a ViewController): + * keyMap: { + * ENTER: 'onEnterKey', + * + * "ALT+PRINT_SCREEN": 'doScreenshot', + * + * // Cmd on Mac OS X, Ctrl on Windows/Linux. + * "CmdOrCtrl+C": 'doCopy', + * + * // This one is handled by a class method. + * ESC: { + * handler: 'destroy', + * scope: 'this', + * event: 'keypress' // default would be keydown + * }, + * + * "ALT+DOWN": 'openExpander', + * + * // Match any key modifiers and invoke before any other DOWN keys + * // handlers with lower or default priority. + * "*+DOWN": { + * handler: 'preprocessDownKey', + * priority: 100 + * } + * } + * }); + * + * The method names are interpreted in the same way that event listener names are + * interpreted. + * + * @since 6.2.0 + */ +Ext.define('Ext.mixin.Keyboard', function(Keyboard) { + return { + extend: 'Ext.Mixin', + mixinConfig: { + id: 'keyboard' + }, + config: { + /** + * @cfg {Object} keyMap + * An object containing handlers for keyboard events. The property names of this + * object are the key name and any modifiers. The values of the properties are the + * descriptors of how to handle each event. + * + * The handler descriptor can be simply the handler function (either the + * literal function or the method name), or it can be an object with these + * properties: + * + * - `handler`: The function or its name to call to handle the event. + * - `scope`: The this pointer context (can be "this" or "controller"). + * - `event`: An optional override of the key event to which to listen. + * + * **Important:** Calls to `setKeyMap` do not replace the entire `keyMap` but + * instead update the provided mappings. That is, unless `null` is passed as the + * value of the `keyMap` which will clear the `keyMap` of all entries. + * + * @cfg {String} [keyMap.scope] The default scope to apply to key handlers + * which do not specify a scope. This is processed the same way as the scope of + * {@link #cfg-listeners}. It defaults to the `"controller"`, but using `'this'` + * means that an instance method will be used. + */ + keyMap: { + $value: null, + cached: true, + merge: function(value, baseValue, cls, mixin) { + // Allow nulling out parent class config + if (value === null) { + return value; + } + // We promote all values into objects but these objects do not get + // merged with base class values. Further, the keys get toUpperCased + // to normalize this aspect ('esc' vs 'ESC' vs 'Esc'). We do not want + // to overwrite a class baseValue with an instances value since those + // are additive (in applyKeyMap/combineKeyMaps). + var ret = (baseValue && !cls.isInstance) ? Ext.Object.chain(baseValue) : {}, + key, ucKey, v, vs; + for (key in value) { + if (key !== 'scope') { + ucKey = key.toUpperCase(); + if (!mixin || ret[ucKey] === undefined) { + // Promote to an object so we can always store the scope. + v = value[key]; + if (v) { + if (typeof v === 'string' || typeof v === 'function') { + v = { + handler: v + }; + } else { + v = Ext.apply({ + handler: v.fn + }, // overwritten by v.handler + v); + } + vs = v.scope || value.scope || 'self'; + v.scope = (vs === 'controller') ? 'self.controller' : vs; + } + ret[ucKey] = v; + } + } + } + return ret; + } + }, + /** + * @cfg {Boolean} keyMapEnabled + * Enables or disables processing keys in the `keyMap`. This value starts as + * `null` and if it is `null` when `initKeyMap` is called, it will automatically + * be set to `true`. Since `initKeyMap` is called by `Ext.Component` at the + * proper time, this is not something application code normally handles. + */ + keyMapEnabled: null + }, + /** + * @cfg {String} keyMapTarget + * The name of the member that should be used to listen for keydown/keypress events. + * This is intended to be controlled at the class level not per instance. + * @protected + */ + keyMapTarget: 'el', + applyKeyMap: function(keyMap, existingKeyMap) { + var me = this, + // During cached config setup, we don't yet have our own (instance) "config" + // so we can tell from that being present that we need our own keyMap. + own = me.hasOwnProperty('config'); + if (own && existingKeyMap && existingKeyMap.$owner !== me) { + // As a cached config, we can be created with an existing value, but + // we do not want to modify that shared instance, so make a copy. + existingKeyMap = Ext.apply({}, existingKeyMap); + } + keyMap = keyMap ? Keyboard.combineKeyMaps(existingKeyMap, keyMap, own && me) : null; + if (me._keyMapReady) { + me.setKeyMapListener(keyMap && me.getKeyMapEnabled()); + } + return keyMap; + }, + /** + * This method should be called when the instance is ready to start listening for + * keyboard events. This is called automatically for `Ext.Component` and derived + * classes. This is done after the component is rendered. + * @protected + */ + initKeyMap: function() { + var me = this, + enabled = me.getKeyMapEnabled(); + me._keyMapReady = true; + if (enabled === null) { + me.setKeyMapEnabled(true); + } else { + me.setKeyMapListener(enabled && me.getKeyMap()); + } + }, + disableKeyMapGroup: function(group) { + this.setKeyMapGroupEnabled(group, false); + }, + enableKeyMapGroup: function(group) { + this.setKeyMapGroupEnabled(group, true); + }, + setKeyMapGroupEnabled: function(group, state) { + var me = this, + disabledGroups = me.disabledKeyMapGroups || (me.disabledKeyMapGroups = {}); + disabledGroups[group] = !state; + }, + updateKeyMapEnabled: function(enabled) { + this.setKeyMapListener(enabled && this._keyMapReady && this.getKeyMap()); + }, + privates: { + _keyMapListenCount: 0, + _keyMapReady: false, + // Descending priority sort + comparePriorities: function(lhs, rhs) { + return (rhs.priority || 0) - (lhs.priority || 0); + }, + findKeyMapEntries: function(e) { + var me = this, + disabledGroups = me.disabledKeyMapGroups, + keyMap = me.getKeyMap(), + entries = keyMap && Keyboard.getKeyName(e), + entry, len, i, + result = []; + entries = entries && keyMap[entries]; + if (entries) { + // Ensure that the entries are in priority order + if (!entries.sorted) { + Ext.Array.sort(entries, me.comparePriorities); + entries.sorted = true; + } + len = entries.length; + for (i = 0; i < len; i++) { + entry = entries[i]; + // If the key code and the modifier flags match, add entry + // to invocation list. + if (!disabledGroups || !disabledGroups[entry.group]) { + if (Keyboard.matchEntry(entry, e)) { + result.push(entry); + } + } + } + } + return result; + }, + onKeyMapEvent: function(e) { + var me = this, + entries = me.getKeyMapEnabled() ? me.findKeyMapEntries(e) : null, + len = entries && entries.length, + i, entry, result; + for (i = 0; i < len && result !== false; i++) { + entry = entries[i]; + result = Ext.callback(entry.handler, entry.scope, [ + e, + this + ], 0, this); + } + return result; + }, + setKeyMapListener: function(enabled) { + var me = this, + listener = me._keyMapListener, + eventSource; + if (listener) { + // We always destroy the old listener since the eventSource could be + // different now... + listener.destroy(); + listener = null; + } + if (enabled) { + ++me._keyMapListenCount; + if (enabled) { + eventSource = me[me.keyMapTarget]; + if (typeof eventSource === 'function') { + eventSource = eventSource.call(me); + } + // eg, 'getFocusEl' + listener = eventSource.on({ + destroyable: true, + scope: me, + keydown: 'onKeyMapEvent', + keypress: 'onKeyMapEvent' + }); + } + } + me._keyMapListener = listener || null; + }, + statics: { + _charCodeRe: /^#([\d]+)$/, + _keySpecRe: /^(?:(?:(\*)[\+\-])|(?:([a-z\+\-]*)[\+\-]))?(?:([a-z0-9_]+|[\+\-]|(?:#?\d+))(?:\:([a-z]+))?)$/i, + _delimiterRe: /\-|\+/, + _keyMapEvents: { + charCode: 'keypress', + keyCode: 'keydown' + }, + combineKeyMaps: function(existingKeyMap, keyMap, owner) { + var defaultScope = keyMap.scope || 'controller', + entry, key, mapping, existingMapping; + for (key in keyMap) { + if (key === 'scope') { + + continue; + } + if (!(mapping = keyMap[key])) { + if (mapping === undefined) { + Ext.raise('keyMap entry "' + key + '" is undefined'); + } + // if we have no mapping (eg, "ESC: null") and no mappings to + // overwrite, we can skip over it. + if (!existingKeyMap) { + + continue; + } + } else { + if (typeof mapping === 'string' || typeof mapping === 'function') { + // Direct calls to setKeyMap() can get here because + // instance and class configs go through merge + mapping = { + handler: mapping, + scope: defaultScope + }; + } else if (mapping) { + mapping = Ext.apply({ + handler: mapping.fn, + // mapping.handler will override + scope: defaultScope + }, // mapping.scope will override + // all other properties of mapping are kept + mapping); + } + existingKeyMap = existingKeyMap || {}; + } + // we'll need a keyMap + if (Keyboard.parseEntry(key, entry = mapping || {})) { + // Key modifiers are stripped off the key name + // so we end up with an object like this: + // + // "PRINT_SCREEN": { + // handler: 'doSummat', + // scope: 'controller', + // altKey: true + // } + // + // or + // + // "UP": { + // handler: 'doSummat' + // scope: 'controller', + // ignoreModifiers: true + // } + // + existingMapping = existingKeyMap[entry.name]; + if (existingMapping) { + if (owner && existingMapping.$owner !== owner) { + existingKeyMap[entry.name] = existingMapping = existingMapping.slice(); + existingMapping.$owner = owner; + } + existingMapping.push(mapping); + existingMapping.sorted = false; + } else { + existingMapping = existingKeyMap[entry.name] = [ + mapping + ]; + existingMapping.$owner = owner; + existingMapping.sorted = true; + } + } else { + Ext.raise('Invalid keyMap key specification "' + key + '"'); + } + } + if (existingKeyMap && owner) { + existingKeyMap.$owner = owner; + } + return existingKeyMap || null; + }, + getKeyName: function(event) { + var keyCode; + if (event.isEvent) { + keyCode = event.keyCode || event.charCode; + event = event.browserEvent; + // If it's the combination code, 229, then use the W3C code property. + // https://developer.mozilla.org/en/docs/Web/API/KeyboardEvent/code + if (keyCode === 229 && 'code' in event) { + if (Ext.String.startsWith(event.code, 'Key')) { + return event.key.substr(3); + } + if (Ext.String.startsWith(event.code, 'Digit')) { + return event.key.substr(5); + } + } + } else { + keyCode = event; + } + // We are in a position of having a numeric key code, attempt to translate it to a name. + return Ext.event.Event.keyCodes[keyCode] || String.fromCharCode(keyCode); + }, + matchEntry: function(entry, e) { + var ev = e.browserEvent, + code; + if (e.type !== entry.event) { + return false; + } + if (!(code = entry.charCode)) { + if (entry.keyCode !== e.keyCode || (!entry.ignoreModifiers && !entry.shiftKey !== !ev.shiftKey)) { + // when using keyCode, SHIFT must match too + return false; + } + } else if (e.getCharCode() !== code) { + return false; + } + // NOTE: All modifier key properties are !-ed to ensure boolean-ness since + // they can be undefined... + // Entry can be flagged to ignore modifiers and invoke purely on key match. + return entry.ignoreModifiers || (!entry.ctrlKey === !ev.ctrlKey && !entry.altKey === !ev.altKey && !entry.metaKey === !ev.metaKey && !entry.shiftKey === !ev.shiftKey); + }, + parseEntry: function(key, entry) { + key = key.toUpperCase(); + var me = this, + Event = Ext.event.Event, + keyFlags = Event.keyFlags, + parts = me._keySpecRe.exec(key), + type = 'keyCode', + name, code, i, match, n; + // The _keySpecRe will split up a string thus: + // + // 'ALT+CTRL+A:GROUP' -> [.., undefined, "ALT+CTRL", "A", "GROUP"] + // + // '*+A:GROUP' -> [.., "*", undefined, "A", "GROUP"] + // + // 'ALT+CTRL+A' -> [.., undefined, "ALT+CTRL", "A", undefined] + // + // So parts is: + // [0] - Whole matched string + // [1] - All modifiers indicator, ie: '*' + // [2] - Delimited modifiers list, eg: 'ctrl+alt' + // [3] - The key name + // [4] - The optional group name + if (parts) { + name = parts[3]; + if (parts[4]) { + entry.group = parts[4]; + } + // If "*" modifier used, then means ignore modifiers and invoke + // on raw key match. + if (!(entry.ignoreModifiers = !!parts[1]) && parts[2]) { + // Otherwise set flags according to modifer names if any. + parts = parts[2].split(me._delimiterRe); + n = parts.length; + for (i = 0; i < n; i++) { + if (!keyFlags[parts[i]]) { + return false; + } + entry[keyFlags[parts[i]]] = true; + } + } + // Entry is named by the unmodified key name. + // Entries for the same key are kept as a prioritized array. + entry.name = name; + // Set the keyCode from the 'PRINT_SCREEN' key name. + if (isNaN(code = Event[name])) { + // Support charCode from a single letter or '#65' format. + if (!(match = me._charCodeRe.exec(name))) { + if (name.length === 1) { + code = name.charCodeAt(0); + } + } else { + code = +match[1]; + } + // #42 + if (code) { + type = 'charCode'; + } else { + // Last chance! Just a number (keyCode) like "27: 'onEscape'"? + code = +name; + } + entry.name = Keyboard.getKeyName(code); + } + entry.event = entry.event || me._keyMapEvents[type]; + return !isNaN(code) && (entry[type] = code); + } + } + } + } + }; +}); +// statics +// privates + +/** + * This mixin implements focus management functionality in Widgets and Components + */ +Ext.define('Ext.mixin.Focusable', { + mixinId: 'focusable', + $isFocusableEntity: true, + // tabIndex config is now defined in Ext.Component + /** + * @property {Boolean} focusable + * @readonly + * + * `true` for keyboard interactive Components or Widgets, `false` otherwise. + * For Containers, this property reflects interactiveness of the + * Container itself, not its children. See {@link #isFocusable}. + * + * **Note:** It is not enough to set this property to `true` to make + * a component keyboard interactive. You also need to make sure that + * the component's {@link #focusEl} is reachable via Tab key (tabbable). + * See also {@link #tabIndex}. + */ + focusable: false, + /** + * @property {Boolean} hasFocus `true` if this component's {@link #focusEl} is focused. + * See also {@link #containsFocus}. + * + * @readonly + */ + hasFocus: false, + /** + * @property {Boolean} containsFocus `true` if this currently focused element + * is within this Component's or Container's hierarchy. This property is set separately + * from {@link #hasFocus}, and can be `true` when `hasFocus` is `false`. + * + * Examples: + * + * + Text field with input element focused would be: + * focusable: true, + * hasFocus: true, + * containsFocus: true + * + * + Date field with drop-down picker currently focused would be: + * focusable: true, + * hasFocus: false, + * containsFocus: true + * + * + Form Panel with a child input field currently focused would be: + * focusable: false, + * hasFocus: false, + * containsFocus: true + * + * See also {@link #hasFocus}. + * + * @readonly + */ + containsFocus: false, + /** + * @cfg {String} [focusCls='x-focused'] CSS class that will be added to focused + * component's {@link #focusClsEl}, and removed when component blurs. + */ + focusCls: Ext.baseCSSPrefix + 'focused', + /** + * @property {Ext.dom.Element} focusEl The element that will be focused + * when {@link #method!focus} method is called on this component. Usually this is + * the same element that receives focus via mouse clicks, taps, and pressing + * Tab key. + */ + focusEl: 'el', + /** + * @property {Ext.dom.Element} focusClsEl The element that will have the + * {@link #focusCls} applied when component's {@link #focusEl} is focused. + */ + /** + * @event focus + * Fires when this Component's {@link #focusEl} receives focus. + * @param {Ext.Component/Ext.Widget} this + * @param {Ext.event.Event} event The focus event. + */ + /** + * @event blur + * Fires when this Component's {@link #focusEl} loses focus. + * @param {Ext.Component} this + * @param {Ext.event.Event} event The blur event. + */ + /** + * @event focusenter + * Fires when focus enters this Component's hierarchy. + * @param {Ext.Component} this + * @param {Ext.event.Event} event The focusenter event. + */ + /** + * @event focusleave + * Fires when focus leaves this Component's hierarchy. + * @param {Ext.Component} this + * @param {Ext.event.Event} event The focusleave event. + */ + /** + * Returns the main focus holder element associated with this Focusable, i.e. + * the element that will be focused when Focusable's {@link #method!focus} method is + * called. For most Focusables, this will be the {@link #focusEl}. + * + * @return {Ext.dom.Element} + * @protected + */ + getFocusEl: function() /* private e */ + { + var focusEl = this.focusEl; + return focusEl && focusEl.dom ? focusEl : null; + }, + /** + * Returns the element used to apply focus styling CSS class when Focusable's + * {@link #focusEl} becomes focused. By default it is {@link #focusEl}. + * + * @param {Ext.dom.Element} [focusEl] Return focus styling element for the given + * focused element. This is used by Components implementing multiple focusable + * elements. + * + * @return {Ext.dom.Element} The focus styling element. + * @protected + */ + getFocusClsEl: function() { + return this.getFocusEl(); + }, + /** + * Template method to do any Focusable related initialization that + * does not involve event listeners creation. + * @protected + */ + initFocusable: Ext.emptyFn, + /** + * Template method to do any event listener initialization for a Focusable. + * This generally happens after the focusEl is available. + * @protected + */ + initFocusableEvents: function(force) { + // If *not* naturally focusable, then we look for the tabIndex property + // to be defined which indicates that the element should be made focusable. + this.initFocusableElement(force); + }, + enableFocusable: Ext.emptyFn, + disableFocusable: function() { + var me = this; + // If this is disabled while focused, by default, focus would return to document.body. + // This must be avoided, both for the convenience of keyboard users, and also + // for when focus is tracked within a tree, such as below an expanded ComboBox. + if (me.hasFocus) { + me.revertFocus(); + } + me.removeFocusCls(); + }, + destroyFocusable: function() { + var me = this; + Ext.destroy(me.focusListeners); + me.focusListeners = me.focusEnterEvent = me.focusTask = null; + me.focusEl = me.ariaEl = null; + }, + /** + * Determine if this Focusable can receive focus at this time. + * + * Note that Containers can be non-focusable themselves while delegating + * focus treatment to a child Component; see {@link Ext.Container #defaultFocus} + * for more information. + * + * @param {Boolean} [deep=false] Optionally determine if the container itself + * is focusable, or if container's focus is delegated to a child component + * and that child is focusable. + * + * @return {Boolean} True if component is focusable, false if not. + */ + isFocusable: function(deep) { + var me = this, + focusEl; + if (!me.focusable && (!me.isContainer || !deep)) { + return false; + } + focusEl = me.getFocusEl(); + if (focusEl && me.canFocus()) { + // getFocusEl might return a Component if a Container wishes to + // delegate focus to a descendant. Both Component and Element + // implement isFocusable, so always ask that. + return focusEl && !focusEl.destroyed && focusEl.isFocusable(deep); + } + return false; + }, + /** + * Determines if this Component is inside a Component tree which is destroyed, *or + * is being destroyed*. + * @return {boolean} `true` if this Component, or any ancestor is destroyed, or + * is being destroyed. + * @private + */ + isDestructing: function() { + for (var c = this; c; c = c.getRefOwner()) { + if (c.destroying || c.destroyed) { + return true; + } + } + return false; + }, + canFocus: function(skipVisibility, includeFocusTarget) { + var me = this, + ownerFC = me.ownerFocusableContainer, + focusableIfDisabled = ownerFC && ownerFC.allowFocusingDisabledChildren, + canFocus; + // Containers may have focusable children while being non-focusable + // themselves; this is why we only account for me.focusable for + // ordinary Components here and below. + // MenuItems must accept focus when disabled. + canFocus = !me.destroyed && me.rendered && !me.isDestructing() && (me.isContainer || me.focusable) && (!me.isDisabled() || focusableIfDisabled) && (skipVisibility || me.isVisible(true)); + return canFocus || (includeFocusTarget && !!me.findFocusTarget()); + }, + /** + * Try to focus this component. + * + * If this component is disabled or otherwise not focusable, a close relation + * will be targeted for focus instead to keep focus localized for keyboard users. + * + * @param {Boolean/Number[]} [selectText] If applicable, `true` to also select all the text + * in this component, or an array consisting of start and end (defaults to start) + * position of selection. + * + * @return {Boolean} `true` if focus target was found and focusing was attempted, + * `false` if no focusing attempt was made. + */ + focus: function(selectText) { + var me = this, + focusTarget, focusElDom; + if ((!me.focusable && !me.isContainer) || me.destroyed || me.destroying) { + return false; + } + // Assignment in conditional here to fall through to else block + // if me.canFocus() returns true but there is no focus target + if (me.canFocus() && (focusTarget = me.getFocusEl())) { + // getFocusEl might return a child Widget or Component if a Container wishes + // to delegate focus to a descendant via its defaultFocus configuration. + if (focusTarget.$isFocusableEntity) { + return focusTarget.focus.apply(focusTarget, arguments); + } + focusElDom = focusTarget.dom; + // This is an Element instance + if (focusElDom) { + // NOT focusElDom.focus() here! Gotta run through possible Element overrides! + focusTarget.focus(); + if (selectText && (me.selectText || focusElDom.select)) { + if (me.selectText) { + if (Ext.isArray(selectText)) { + me.selectText.apply(me, selectText); + } else { + me.selectText(); + } + } else { + focusElDom.select(); + } + } + } + // Could be a Widget or something else with no dom property but focusable + else if (focusTarget.focus) { + focusTarget.focus(); + } else { + return false; + } + } else { + // If we are asked to focus while not able to focus though disablement/invisibility etc, + // focus may revert to document.body if the current focus is being hidden or destroyed. + // This must be avoided, both for the convenience of keyboard users, and also + // for when focus is tracked within a tree, such as below an expanded ComboBox. + focusTarget = me.findFocusTarget(); + if (focusTarget && focusTarget != me) { + return focusTarget.focus.apply(focusTarget, arguments); + } else { + return false; + } + } + return true; + }, + /** + * @private + */ + onBlur: function(e) { + var me = this, + container = me.ownerFocusableContainer; + me.hasFocus = false; + if (me.beforeBlur && !me.beforeBlur.$emptyFn) { + me.beforeBlur(e); + } + if (container) { + container.beforeFocusableChildBlur(me, e); + } + me.removeFocusCls(e); + if (me.hasListeners.blur) { + me.fireEvent('blur', me, e); + } + if (me.postBlur && !me.postBlur.$emptyFn) { + me.postBlur(e); + } + if (container) { + container.afterFocusableChildBlur(me, e); + } + }, + /** + * @private + */ + onFocus: function(e) { + var me = this, + container = me.ownerFocusableContainer; + if (me.canFocus()) { + if (me.beforeFocus && !me.beforeFocus.$emptyFn) { + me.beforeFocus(e); + } + if (container) { + container.beforeFocusableChildFocus(me, e); + } + me.addFocusCls(e); + if (!me.hasFocus) { + me.hasFocus = true; + me.fireEvent('focus', me, e); + } + if (me.postFocus && !me.postFocus.$emptyFn) { + me.postFocus(e); + } + if (container) { + container.afterFocusableChildFocus(me, e); + } + } + }, + /** + * Return the actual tabIndex for this Focusable. + * + * @return {Number} tabIndex attribute value + */ + getTabIndex: function() { + var me = this, + el, index; + if (!me.focusable) { + return; + } + el = me.getFocusEl(); + if (el) { + // getFocusEl may return a child Widget or Component + if (el.$isFocusableEntity) { + index = el.getTabIndex(); + } else if (el.isElement && el.dom) { + // We can't query el.dom.tabIndex because IE8 will return 0 + // when tabIndex attribute is not present, and Chrome will + // return -1. Can't trust a browser to do a simplest thing. :/ + index = el.dom.getAttribute('tabIndex'); + // This contraption is here because we can't simply coerce + // the returned attribute value to a number. If the attribute + // is not present, the value returned will be null, and coercing + // null gives 0. Wondrous JavaScript. :/ + if (index !== null) { + index -= 0; + } + } else // A component can be configured with el: '#id' to look up + // its main element from the DOM rather than render it; in + // such case getTabIndex() may happen to be called before + // said lookup has happened; indeterminate result follows. + { + return; + } + } + if (typeof index !== 'number') { + index = me.tabIndex; + } + return index; + }, + /** + * Set the tabIndex property for this Focusable. If the focusEl + * is available, set tabIndex attribute on it, too. + * + * @param {Number} newTabIndex new tabIndex to set + * @param {HTMLElement} [focusEl] (private) + */ + setTabIndex: function(newTabIndex, focusEl) { + var me = this, + ownerFC = me.ownerFocusableContainer, + focusableIfDisabled = ownerFC && ownerFC.allowFocusingDisabledChildren, + el; + // See comments for definition of forceTabIndex as to why this is needed + if (!me.focusable && !me.forceTabIndex) { + return; + } + me.tabIndex = newTabIndex; + // We must not do this if we are destroyed, or if we are incapable of being focused. + // Handle our owning FocusableContainer having allowFocusingDisabledChildren + if (me.destroying || me.destroyed || (me.isDisabled() && !focusableIfDisabled)) { + return; + } + el = focusEl || me.getFocusEl(); + if (el) { + // getFocusEl may return a child Widget or Component + if (el.$isFocusableEntity) { + el.setTabIndex(newTabIndex); + } + // Or if a component is configured with el: '#id', it may + // still be a string by the time setTabIndex is called from + // owner FocusableContainer. + else if (el.isElement && el.dom) { + // setTabIndex is aware of saved tabbable state + el.setTabIndex(newTabIndex); + } + } + }, + /** + * @template + * @protected + * Called when focus enters this Component's hierarchy + * @param {Object} e + * @param {Ext.event.Event} e.event The underlying DOM event. + * @param {HTMLElement} e.target The element gaining focus. + * @param {HTMLElement} e.relatedTarget The element losing focus. + * @param {Ext.Component} e.toComponent The Component gaining focus. + * @param {Ext.Component} e.fromComponent The Component losing focus. + * @param {Boolean} e.backwards `true` if the `fromComponent` is *after* the `toComponent* + * in the DOM tree, indicating that the user used `SHIFT+TAB` to move focus. Note that setting + * `tabIndex` values to affect tabbing order can cause this to be incorrect. Setting + * `tabIndex` values is not advised. + */ + onFocusEnter: function(e) { + var me = this; + // We DO NOT check if `me` is focusable here. The reason is that + // non-focusable containers need to track focus entering their + // children so that revertFocus would work if these children + // become unavailable. + if (me.destroying || me.destroyed) { + return; + } + // Save all information about how we received focus so that + // we can do appropriate things when asked to revertFocus + me.focusEnterEvent = e; + me.containsFocus = true; + if (me.hasListeners.focusenter) { + me.fireEvent('focusenter', me, e); + } + }, + /** + * @template + * @protected + * Called when focus exits from this Component's hierarchy + * @param {Ext.event.Event} e + * @param {Ext.event.Event} e.event The underlying DOM event. + * @param {HTMLElement} e.target The element gaining focus. + * @param {HTMLElement} e.relatedTarget The element losing focus. + * @param {Ext.Component} e.toComponent The Component gaining focus. + * @param {Ext.Component} e.fromComponent The Component losing focus. + */ + onFocusLeave: function(e) { + var me = this; + // Same as in onFocusEnter + if (me.destroying || me.destroyed) { + return; + } + me.focusEnterEvent = null; + me.containsFocus = false; + if (me.hasListeners.focusleave) { + me.fireEvent('focusleave', me, e); + } + }, + /** + * @template + * @method + * @protected + * Called when focus moves *within* this Component's hierarchy + * @param {Object} info + * @param {Ext.event.Event} info.event The underlying Event object. + * @param {HTMLElement} info.toElement The element gaining focus. + * @param {HTMLElement} info.fromElement The element losing focus. + * @param {Ext.Component} info.toComponent The Component gaining focus. + * @param {Ext.Component} info.fromComponent The Component losing focus. + * @param {Boolean} info.backwards `true` if the focus movement is backward in DOM order + */ + onFocusMove: Ext.emptyFn, + privates: { + // This private flag was introduced to work around an issue where + // the tab index would not be stamped onto the component. + // Consider a tool, which is focusable by default and has tabIndex: 0 + // on the class definition. If a non-focusable tool is required, setting + // focusable: false is not enough, the tabIndex also needs to be considered. + // However, the default behaviour is to not modify the tabIndex on non + // focusable items. This config can go away if that behaviour is changed. + // Arguably, a non-focusable widget probably shouldn't retain a tab index + // if it's explicitly configured. + forceTabIndex: false, + /** + * Returns focus to the Component or element found in the cached + * focusEnterEvent. + * + * @private + */ + revertFocus: function() { + var me = this, + focusEvent = me.focusEnterEvent, + activeElement = Ext.Element.getActiveElement(), + focusTarget, fromComponent, reverted; + // If we have a record of where focus arrived from, + // and have not been told to avoid refocusing, + // and we contain the activeElement. + // Then, before hiding, restore focus to what was focused before we were focused. + if (focusEvent && !me.preventRefocus && me.el.contains(activeElement)) { + fromComponent = focusEvent.fromComponent; + // If the default focus reversion target is in shifting ground, fall back to document.body + if (fromComponent && (fromComponent.destroyed || fromComponent.isDestructing())) { + focusTarget = document.body; + } else // Preferred focus target is the actual element from which focus entered this component. + // It will be up to its encapsulating component to handle this in an appropriate way. + // For example, a grid, upon having focus pushed to a certain cell will set its + // navigation position to that cell and highlight it as focused. + // Likewise an input field must handle its field acquiring focus. + { + focusTarget = focusEvent.relatedTarget; + } + // If focus was from the body, try to keep it closer than that + if (focusTarget === document.body) { + fromComponent = me.findFocusTarget(); + if (fromComponent) { + focusTarget = fromComponent.getFocusEl(); + } + } + if (focusTarget && focusTarget.$isFocusableEntity) { + if (!focusTarget.destroyed && focusTarget.isFocusable()) { + focusTarget.focus(); + } + } + // If the element is in the document and focusable, then we're good. The owning component will handle it. + else if (Ext.getDoc().contains(focusTarget) && Ext.fly(focusTarget).isFocusable()) { + fromComponent = Ext.Component.from(focusTarget); + // Allow the focus recieving component to modify the focus sequence. + if (fromComponent) { + fromComponent.revertFocusTo(focusTarget); + } else { + focusTarget.focus(); + } + } + // If the element has gone, or is hidden, we will have to rely on the intelligent focus diversion + // of components to send focus back to somewhere that is least surprising for the user. + else if (focusEvent.fromComponent && focusEvent.fromComponent.focus) { + reverted = focusEvent.fromComponent.focus(); + // The component was not able to find a suitable target. + // Important: Touch platforms do not blur programatically focused elements + // when they become hidden, so we must force the issue in order to maintain + // focus tracking. + if (!reverted) { + activeElement.blur(); + } + } + } + }, + /** + * This field is on the recieving end of a call from {@link #method!revertFocus}. + * + * It is called when focus is being pushed back into this Component from a Component + * that is focused and is being hidden or disabled. + * + * We must focus the passed element. + * + * Subclasses may perform some extra processing to prepare for refocusing. + * @param target + */ + revertFocusTo: function(target) { + target.focus(); + }, + /** + * Finds an alternate Component to focus if this Component is disabled while focused, or + * focused while disabled, or otherwise unable to focus. + * + * In both cases, focus must not be lost to document.body, but must move to an intuitively + * connectible Component, either a sibling, or uncle or nephew. + * + * This is both for the convenience of keyboard users, and also for when focus is tracked + * within a Component tree such as for ComboBoxes and their dropdowns. + * + * For example, a ComboBox with a PagingToolbar in is BoundList. If the "Next Page" + * button is hit, the LoadMask shows and focuses, the next page is the last page, so + * the "Next Page" button is disabled. When the LoadMask hides, it attempt to focus the + * last focused Component which is the disabled "Next Page" button. In this situation, + * focus should move to a sibling within the PagingToolbar. + * + * @return {Ext.Component} A closely related focusable Component to which focus can move. + * @private + */ + findFocusTarget: function() { + var me = this, + parentAxis, candidate, len, i, focusTargets, focusIndex; + if (me.preventRefocus) { + return null; + } + // Create an axis of visible, enabled, stable parent components which we + // will walk up looking for ancestors to revert focus to. + // + // First, find all enabled parents. + for (parentAxis = [] , candidate = me.getRefOwner(); candidate; candidate = candidate.getRefOwner()) { + if (!candidate.isDisabled()) { + parentAxis.unshift(candidate); + } + } + // Then walk downwards until we encounter a non-targetable parent + // which means hidden of destroying. All candidates *above* that + // are potential sources of focus targets. + for (i = 0 , len = parentAxis.length; i < len; i++) { + candidate = parentAxis[i]; + if (candidate.destroying || !candidate.isVisible()) { + parentAxis.length = i; + break; + } + } + // Walk up the parent axis checking each parent for focus targets. + for (i = parentAxis.length - 1; i >= 0; i--) { + candidate = parentAxis[i]; + // Use CQ to find a target that is fully focusable (:canfocus, NOT the theoretical :focusable) + // Cannot use :focusable(true) because that consults findFocusTarget and would cause infinite recursion. + // Exclude the component which currently has focus. + // Cannot use candidate.child() because the parent might not be a Container. + // Non-Container Components may still have ownership relationships with + // other Components. eg: BoundList with PagingToolbar + focusTargets = Ext.ComponentQuery.query(':canfocus()', candidate); + if (focusTargets.length) { + focusIndex = Ext.Array.indexOf(focusTargets, Ext.ComponentManager.getActiveComponent()); + // Return the next focusable, or the previous focusable, or the first focusable + return focusTargets[focusIndex + 1] || focusTargets[focusIndex - 1] || focusTargets[0]; + } + // We found no focusable siblings in our candidate, but the candidate may itself be focusable, + // it is not always a Container - could be the owning Field of a BoundList. + if (candidate.isFocusable && candidate.isFocusable()) { + return candidate; + } + } + }, + /** + * Sets up the focus listener on this Component's {@link #getFocusEl focusEl} if it has one. + * + * Form Components which must implicitly participate in tabbing order usually have a naturally + * focusable element as their {@link #getFocusEl focusEl}, and it is the DOM event of that + * receiving focus which drives the Component's `onFocus` handling, and the DOM event of it + * being blurred which drives the `onBlur` handling. + * @private + */ + initFocusableElement: function(force) { + var me = this, + tabIndex = me.getTabIndex(), + focusEl = me.getFocusEl(); + if (focusEl && !focusEl.$isFocusableEntity) { + // focusEl is not available until after rendering, and rendering tabIndex + // into focusEl is not always convenient. So we apply it here if Component's + // tabIndex property is set and Component is otherwise focusable. + // Note that for Widgets and Modern Components we might not have the rendered + // flag set yet but can force setting the property. + if (tabIndex != null && (force || me.canFocus(true))) { + me.setTabIndex(tabIndex, focusEl); + } + // This attribute is a shortcut to look up a Component by its Elements + // It only makes sense on focusable elements, so we set it here unless + // our focusEl is delegated to the focusEl of an owned Component and it + // already has ownership stamped into it. + if (!focusEl.dom.hasAttribute('data-componentid')) { + focusEl.dom.setAttribute('data-componentid', me.id); + } + } + }, + addFocusCls: function(e) { + var focusCls = this.focusCls, + el; + el = this.getFocusClsEl(); + if (focusCls) { + el = this.getFocusClsEl(e); + if (el) { + el.addCls(focusCls); + } + } + }, + removeFocusCls: function(e) { + var focusCls = this.focusCls, + el; + if (focusCls) { + el = this.getFocusClsEl(e); + if (el) { + el.removeCls(focusCls); + } + } + }, + /** + * @private + */ + handleFocusEvent: function(e) { + var me = this, + event; + if (!me.focusable || me.destroying || me.destroyed) { + return; + } + // handleFocusEvent and handleBlurEvent are called by ComponentManager + // passing the normalized element event that might or might not cause + // component focus or blur. The component itself makes the decision + // whether focus/blur happens or not. This is necessary for components + // that might have more than one focusable element within the component's + // DOM structure, like Ext.button.Split. + if (me.isFocusing(e)) { + event = new Ext.event.Event(e.event); + event.type = 'focus'; + event.relatedTarget = e.fromElement; + event.target = e.toElement; + me.onFocus(event); + } + }, + /** + * @private + */ + handleBlurEvent: function(e) { + var me = this, + event; + if (!me.focusable || me.destroying || me.destroyed) { + return; + } + // Must process blur if toElement is document.body + // Blurs caused by the app losing focus are processed synchronously + // for obvious reasons, so the activeElement will still be the + // focusEl, so isBlurring will return false, and reject this op. + if (e.toElement === document.body || me.isBlurring(e)) { + event = new Ext.event.Event(e.event); + event.type = 'blur'; + event.target = e.fromElement; + event.relatedTarget = e.toElement; + me.onBlur(event); + } + }, + /** + * @private + */ + isFocusing: function(e) { + var focusEl = this.getFocusEl(); + if (focusEl) { + if (focusEl.isFocusing) { + return focusEl.isFocusing(e); + } else { + // Sometimes focusing an element may cause reaction from other entities + // that will focus something else instead. So before unraveling the + // event chain we better make sure our focusEl is *indeed* focused. + return focusEl.dom === document.activeElement && e.toElement === focusEl.dom && e.fromElement !== e.toElement; + } + } + return false; + }, + /** + * @private + */ + isBlurring: function(e) { + var focusEl = this.getFocusEl(); + if (focusEl) { + if (focusEl.isFocusing) { + return focusEl.isBlurring(e); + } else { + // Ditto for blurring: in some cases freshly blurred element can be + // refocused by external forces so we need to check if our focusEl + // *indeed* is not focused before we can call it blurring. + return focusEl.dom !== document.activeElement && e.fromElement === focusEl.dom && e.fromElement !== e.toElement; + } + } + return false; + }, + /** + * @private + */ + blur: function() { + var me = this, + focusEl; + if (!me.focusable || !me.canFocus()) { + return; + } + focusEl = me.getFocusEl(); + if (focusEl) { + me.blurring = true; + focusEl.blur(); + delete me.blurring; + } + }, + isTabbable: function() { + var me = this, + focusEl; + if (me.focusable) { + focusEl = me.getFocusEl(); + if (focusEl && focusEl.isTabbable()) { + return focusEl.isTabbable(); + } + } + return false; + }, + disableTabbing: function() { + var me = this, + el = me.el, + focusEl; + // We DO NOT check for me.focusable here, because this should work + // for containers with focus delegates, too! + if (me.destroying || me.destroyed) { + return; + } + // We're disabling tabbability for all elements of a given Component; + // focusEl might be outside of the hierarchy which is checked below. + if (el) { + el.saveTabbableState(); + } + focusEl = me.getFocusEl(); + if (focusEl) { + // focusEl may happen to be a focus delegate for a container + if (focusEl.$isFocusableEntity) { + focusEl.disableTabbing(); + } + // Alternatively focusEl may happen to be outside of the main el, + // or else it can be a string reference to an element that + // has not been resolved yet + else if (focusEl.isElement && el && !el.contains(focusEl)) { + focusEl.saveTabbableState(); + } + } + }, + enableTabbing: function(reset) { + var me = this, + el = me.el, + focusEl; + // We DO NOT check for me.focusable here, because this should work + // for containers with focus delegates, too! + if (me.destroying || me.destroyed) { + return; + } + focusEl = me.getFocusEl(); + if (focusEl) { + if (focusEl.$isFocusableEntity) { + focusEl.enableTabbing(); + } else if (focusEl.isElement && el && !el.contains(focusEl)) { + focusEl.restoreTabbableState(); + } + } + if (el) { + el.restoreTabbableState({ + reset: reset + }); + } + } + } +}, function() { + var keyboardModeCls = Ext.baseCSSPrefix + 'keyboard-mode', + keyboardMode = false; + /** + * @property {Boolean} keyboardMode + * @member Ext + * A flag which indicates that the last UI interaction from the user was a keyboard gesture + */ + /** + * @property {Boolean} touchMode + * @member Ext + * A flag which indicates that the last UI interaction from the user was a touch gesture + */ + Ext.setKeyboardMode = Ext.setKeyboardMode || function(keyboardMode) { + Ext.keyboardMode = keyboardMode; + Ext.getBody().toggleCls(keyboardModeCls, keyboardMode); + }; + Ext.isTouchMode = function() { + return (Ext.now() - Ext.lastTouchTime) < 500; + }; + function syncKeyboardMode(e) { + var type = e.type; + if (type === 'pointermove') { + // On pointer move we want to track that the user has switched from keyboard + // to mouse, but we do not remove the visual focus style until a pointerdown + // occurs or the focus changes. This accomodates menus which change focus + // based on mouseenter of a menu item + keyboardMode = false; + } else { + keyboardMode = (type === 'keydown'); + Ext.lastTouchTime = e.pointerType === 'touch' && Ext.now(); + Ext.setKeyboardMode(keyboardMode); + } + } + Ext.onReady(function() { + Ext.getWin().on({ + pointerdown: syncKeyboardMode, + pointermove: syncKeyboardMode, + keydown: syncKeyboardMode, + capture: true, + delegated: false + }); + Ext.on('focus', function() { + if (keyboardMode !== Ext.getBody().hasCls(keyboardModeCls)) { + Ext.setKeyboardMode(keyboardMode); + } + }); + }); +}); + +/** + * This mixin defines certain config options, properties, and APIs to be used + * by Components that implement accessible traits according to WAI-ARIA 1.0 specification. + * + * @private + */ +Ext.define('Ext.mixin.Accessible', { + extend: 'Ext.Mixin', + mixinConfig: { + id: 'accessible' + }, + /** + * @cfg {String} [ariaLabel] ARIA label for this Component. It is best to use + * {@link #ariaLabelledBy} option instead, because screen readers prefer + * `aria-labelledby` attribute to `aria-label`. {@link #ariaLabel} and + * {@link #ariaLabelledBy} config options are mutually exclusive. + */ + /** + * @cfg {String} [ariaLabelledBy] DOM selector for a child element that is to be used + * as label for this Component, set in `aria-labelledby` attribute. + * If the selector is by `#id`, the label element can be any existing element, + * not necessarily a child of the main Component element. + * + * {@link #ariaLabelledBy} and {@link #ariaLabel} config options are + * mutually exclusive, and `ariaLabelledBy` has the higher precedence. + */ + /** + * @cfg {String} [ariaDescribedBy] DOM selector for a child element that is to be used + * as description for this Component, set in `aria-describedby` attribute. + * The selector works the same way as {@link #ariaLabelledBy}. + */ + config: { + /** + * @cfg {Object} ariaAttributes An object containing ARIA attributes to be set + * on this Component's ARIA element. Use this to set the attributes that cannot be + * determined by the Component's state, such as `aria-live`, `aria-flowto`, etc. + * + * **Note** that this config is only meaningful at the Component rendering time, + * and setting it after that will do nothing. + */ + ariaAttributes: { + $value: null, + lazy: true + } + }, + /** + * @property {String} [ariaRole] ARIA role for this Component, defaults to no role. + * With no role, no other ARIA attributes are set. + * + * @readonly + */ + /** + * @property {Object} [ariaRenderAttributes] **Instance specific** ARIA attributes + * to render into Component's ariaEl. This object is only used during rendering, + * and is discarded afterwards. + * + * @private + */ + /** + * @property {String} [ariaEl='el'] The name of the Component property that holds + * a reference to the Element that serves as that Component's ARIA element. + * This property will be replaced with the actual Element reference after rendering. + * + * Most of the simple Components will have their main element as ariaEl. + * + * @private + * @readonly + * @since 6.0.0 + */ + ariaEl: 'el', + privates: { + /** + * Find component(s) that label or describe this component, + * and return the id(s) of their ariaEl elements. + * + * @param {Function/String/String[]} [reference] Component reference, + * or array of component references, or a function that should return + * the proper attribute string. The function will be called in the + * context of the labelled component. + * + * @return {Ext.Element} Element id string, or null + * @private + */ + getAriaLabelEl: function(reference) { + var ids = [], + refHolder, i, len, cmp, result; + if (reference) { + if (Ext.isFunction(reference)) { + return reference.call(this); + } else { + if (!Ext.isArray(reference)) { + reference = [ + reference + ]; + } + refHolder = this.lookupReferenceHolder(); + if (refHolder) { + for (i = 0 , len = reference.length; i < len; i++) { + cmp = refHolder.lookupReference(reference[i]); + if (cmp) { + ids.push(cmp.ariaEl.id); + } + } + } + } + } + return ids.length ? ids.join(' ') : null; + } + } +}); + +/** + * Ext.Widget is a light-weight Component that consists of nothing more than a template + * Element that can be cloned to quickly and efficiently replicate many instances. + * Ext.Widget is typically not instantiated directly, because the default template is + * just a single element with no listeners. Instead Ext.Widget should be extended to + * create Widgets that have a useful markup structure and event listeners. + * + * For example: + * + * Ext.define('MyWidget', { + * extend: 'Ext.Widget', + * + * // The element template passed to Ext.Element.create() + * element: { + * reference: 'element', + * listeners: { + * click: 'onClick' + * }, + * children: [{ + * reference: 'innerElement', + * listeners: { + * click: 'onInnerClick' + * } + * }] + * }, + * + * constructor: function(config) { + * // It is important to remember to call the Widget superclass constructor + * // when overriding the constructor in a derived class. This ensures that + * // the element is initialized from the template, and that initConfig() is + * // is called. + * this.callParent([config]); + * + * // After calling the superclass constructor, the Element is available and + * // can safely be manipulated. Reference Elements are instances of + * // Ext.Element, and are cached on each Widget instance by reference name. + * Ext.getBody().appendChild(this.element); + * }, + * + * onClick: function() { + * // listeners use this Widget instance as their scope + * console.log('element clicked', this); + * }, + * + * onInnerClick: function() { + * // access the innerElement reference by name + * console.log('inner element clicked', this.innerElement); + * } + * }); + * + * @since 5.0.0 + * @disable {DuplicateAlternateClassName} + */ +Ext.define('Ext.Widget', { + extend: 'Ext.Evented', + xtype: 'widget', + alternateClassName: 'Ext.Gadget', + requires: [ + 'Ext.dom.Element' + ], + mixins: [ + 'Ext.mixin.Inheritable', + 'Ext.mixin.Bindable', + 'Ext.mixin.ComponentDelegation', + 'Ext.mixin.Pluggable', + 'Ext.mixin.Keyboard', + 'Ext.mixin.Factoryable', + 'Ext.mixin.Focusable', + 'Ext.mixin.Accessible' + ], + isWidget: true, + factoryConfig: { + creator: null, + defaultProperty: 'xtype', + defaultType: 'component', + typeProperty: 'xtype' + }, + /** + * @property {Object} element + * A configuration object for Ext.Element.create() that is used to create the Element + * template. Subclasses should avoid overriding this property and instead add elements + * using {@link #template}. + * + * Supports all the standard options of a Ext.Element.create() config and adds 3 + * additional options: + * + * 1. `reference` - this option specifies a name for Element references. These + * references names become properties of the Widget instance and refer to Ext.Element + * instances that were created using the template: + * + * element: { + * reference: 'element', + * children: [{ + * reference: 'innerElement' + * }] + * } + * + * After construction of a widget the reference elements are accessible as follows: + * + * var foo = new FooWidget(), + * innerEl = foo.innerElement; // an Ext.Element that wraps the innerElement + * + * The reference attribute is optional, but all Widgets must have a `'element'` + * reference on some element within the template (usually the outermost one). + * + * 2. `listeners` - a standard listeners object as specified by {@link Ext.mixin.Observable}. + * + * element: { + * reference: 'element', + * listeners: { + * click: 'onClick' + * }, + * children: [{ + * reference: 'innerElement', + * listeners: { + * click: 'onInnerClick' + * } + * }] + * } + * + * Since listeners cannot be attached without an Ext.Element reference the `reference` + * property MUST be specified in order to use `listeners`. + * + * The Widget instance is used as the scope for all listeners specified in this way, + * so it is invalid to use the `scope` option in the `listeners` config since it will + * always be overwritten using `this`. + * + * 3. `uiCls` - a suffix to be appended to the ui-specific CSS class for each `{@link #ui}` + * for this widget. These ui classes are constructed by appending the `ui` to each + * `{@link #classCls}` or `{@link #baseCls}` for the widget. As such, `uiCls` should + * never be used on the main `element` reference, as its `uiCls` is computed automatically. + * + * For example, assume a widget is defined with a `ui` of `'alt action'` and a + * `uiCls` of `'inner-el'` on its `innerElement` reference element: + * + * Ext.define('Doodad', { + * extend: 'Ext.Widget', + * xtype: 'doodad', + * + * classCls: 'x-doodad', + * + * ui: 'alt action', + * + * element: { + * reference: 'element', + * + * children: [{ + * reference: 'innerElement', + * cls: 'x-inner-el', + * uiCls: 'inner-el' + * }] + * } + * }); + * + * This would result in the following markup when rendered: + * + *
+ *
+ *
+ * + * These additional classes can be used to style the reference element for a particular + * ui; however, use of `uiCls` is not typically necessary or recommended. Reference + * elements should usually be styled using simple descendant selectors: + * + * .x-doodad-alt .x-inner-el { + * color: red; + * } + * + * When there is a possibility that widgets can be nested it is best to use direct + * child selectors to avoid the possibility of selecting all descendants instead + * of just the reference element for the intended widget: + * + * .x-doodad-alt > .x-inner-el { + * color: red; + * } + * + * Only use `uiCls` when there is a possibility of nesting, AND there may be a variable + * number of elements between the main `element` and the reference element in question. + * For example, Ext.Container with docked items has a different number of elements + * in between its `element` and its `bodyElement` than a Container without docked items + * because of the wrapping elements that are dynamically added to support docking. + * To ensure it does not style all descendants it must use a `uiCls` to style its + * `bodyElement`: + * + * .x-container-alt-body-el { + * background: #fff; + * } + * + * Note that when `uiCls` is specified it also adds a class name that does not contain + * the `ui` using just the `classCls` and/or `baseCls` as the prefix. This class name + * can be used for base-level styling that does not relate to any particular UI: + * + * .x-container-body-el { + * position: relative; + * } + * + * @protected + */ + element: { + reference: 'element' + }, + observableType: 'component', + cachedConfig: { + /** + * @cfg {String/String[]} cls The CSS class to add to this widget's element, in + * addition to the {@link #baseCls}. In many cases, this property will be specified + * by the derived widget class. See {@link #userCls} for adding additional CSS + * classes to widget instances (such as items in a {@link Ext.Container}). + * @accessor + */ + cls: null, + /** + * @cfg {String/Object} style + * Additional CSS styles that will be rendered into an inline style attribute when + * the widget is rendered. + * + * You can pass either a string syntax: + * + * style: 'background:red' + * + * Or by using an object: + * + * style: { + * background: 'red' + * } + * + * When using the object syntax, you can define CSS Properties by using a string: + * + * style: { + * 'border-left': '1px solid red' + * } + * + * Although the object syntax is much easier to read, we suggest you to use the + * string syntax for better performance. + * @accessor set + */ + style: null, + /** + * @cfg {Boolean} border Enables or disables bordering on this component. + * The following values are accepted: + * + * - `null` or `true (default): Do nothing and allow the border to be specified by the theme. + * - `false`: suppress the default border provided by the theme. + * + * Please note that enabling bordering via this config will not add a `border-color` + * or `border-style` CSS property to the component; you provide the `border-color` + * and `border-style` via CSS rule or {@link #style} configuration + * (if not already provide by the theme). + * + * ## Using {@link #style}: + * + * Ext.Viewport.add({ + * centered: true, + * width: 100, + * height: 100, + * + * style: 'border: 1px solid blue;' + * // ... + * }); + * + * ## Using CSS: + * + * Ext.Viewport.add({ + * centered: true, + * width: 100, + * height: 100, + * + * cls: 'my-component' + * // ... + * }); + * + * And your CSS file: + * + * .my-component { + * border: 1px solid red; + * } + * + * @accessor + */ + border: null, + /** + * @cfg {Object} + * + * Emulates the behavior of the CSS + * [touch-action](https://www.w3.org/TR/pointerevents/#the-touch-action-css-property) + * property in a cross-browser compatible manner. + * + * Keys in this object are touch action names, and values are `false` to disable + * a touch action or `true` to enable it. Accepted keys are: + * + * - `panX` + * - `panY` + * - `pinchZoom` + * - `doubleTapZoom` + * + * All touch actions are enabled (`true`) by default, so it is usually only necessary + * to specify which touch actions to disable. For example, the following disables + * only horizontal scrolling and pinch-to-zoom on the component's main element: + * + * touchAction: { + * panX: false, + * pinchZoom: false + * } + * + * Touch actions can be specified on reference elements using the reference element + * name, for example: + * + * // disables horizontal scrolling on the main element, and double-tap-zoom + * // on the child element named "body" + * touchAction: { + * panY: false + * body: { + * doubleTapZoom: false + * } + * } + * + * The primary motivation for setting the touch-action of an element is to prevent + * the browser's default handling of a gesture such as pinch-to-zoom, or + * drag-to-scroll, so that the application can implement its own handling of that + * gesture on the element. Suppose, for example, a component has a custom drag + * handler on its element and wishes to prevent horizontal scrolling of its container + * while it is being dragged: + * + * Ext.create('Ext.Widget', { + * touchAction: { + * panX: false + * }, + * listeners: { + * drag: function(e) { + * // implement drag logic + * } + * } + * }); + */ + touchAction: null, + /** + * @cfg {Object} eventHandlers A map of event type to the corresponding handler method + * name. This is used internally by native event handling mechanism. + * @private + */ + eventHandlers: { + focus: 'handleFocusEvent', + blur: 'handleBlurEvent' + } + }, + /** + * @cfg {String} name Name for the widget to be used with {@link Ext.Container#lookupName} et al. + */ + name: null, + config: { + /** + * @cfg {Ext.Element} [renderTo] Optional element to render this Component to. + * Not required if this component is an {@link Ext.Container#items item} of a Container of a Container. + */ + renderTo: null, + /** + * @cfg {String/String[]} ui The ui or uis to be used on this Component + * + * When a ui is configured, CSS class names are added to the {@link #element}, created + * by appending the ui name(s) to each {@link #classCls} and/or {@link #baseCls}. + */ + ui: null, + /** + * @cfg {String/String[]} userCls + * One or more CSS classes to add to the component's primary element. This config + * is intended solely for use by the component instantiator (the "user"), not by + * derived classes. + * + * For example: + * + * items: [{ + * xtype: 'button', + * userCls: 'my-button' + * ... + * }] + */ + userCls: null, + /** + * @cfg {Boolean/Object/String} ripple + * Set to truthy, Color or Object value for the ripple. + * @cfg {String} ripple.color The background color of the ripple. + * @cfg {Array} ripple.position Position for the ripple to start at [x,y]. + * Determines if a Ripple effect should happen whenever this element is pressed. + * + * For example: + * { + * ripple: true + * } + * + * Or: + * + * { + * ripple: { + * color: 'red' + * } + * } + * + * For complex components, individual elements can suppress ripples by adding the + * `x-no-ripple` class to disable rippling for a tree of elements. + * + * @since 6.5.0 + */ + ripple: null, + /** + * @cfg {'clip'/'display'/'offsets'/'opacity'/'visibility'} [hideMode='display'] + * A String which specifies how this component's DOM element will be hidden. The + * accepted values are any of these: + * + * - `'clip'` : Hide using {@link Ext.dom.Element#CLIP clip}. + * - `'display'` : Hide using {@link Ext.dom.Element#DISPLAY display}. + * - `'offsets'` : Hide using positioning {@link Ext.dom.Element#OFFSETS offsets}. + * - `'opacity'` : Hide using {@link Ext.dom.Element#OPACITY opacity}. + * - `'visibility'` : Hide using {@link Ext.dom.Element#VISIBILITY visibility}. + * + * Hiding using ``display`` results in having no dimensions as well as resetting + * scroll positions to 0. + * + * The other modes overcome this but may have different trade-offs in certain + * circumstances. + * + * @since 6.5.0 + */ + hideMode: null, + /** + * @cfg {String/String[]} instanceCls + * + * An extra CSS class or classes to augment the {@link #classCls} on an individual instance + * + * @private + * @since 6.5.0 + */ + instanceCls: null + }, + eventedConfig: { + /** + * @cfg {Number/String} width + * The width of this Component; must be a valid CSS length value, e.g: `300`, `100px`, `30%`, etc. + * By default, if this is not explicitly set, this Component's element will simply have its own natural size. + * If set to `auto`, it will set the width to `null` meaning it will have its own natural size. + * @accessor + * @evented + */ + width: null, + /** + * @cfg {Number/String} height + * The height of this Component; must be a valid CSS length value, e.g: `300`, `100px`, `30%`, etc. + * By default, if this is not explicitly set, this Component's element will simply have its own natural size. + * If set to `auto`, it will set the width to `null` meaning it will have its own natural size. + * @accessor + * @evented + */ + height: null, + /** + * @cfg {Boolean} [hidden] + * Whether or not this Component is hidden (its CSS `display` property is set to `none`). + * + * Defaults to `true` for {@link #floated} Components. + * @accessor + * @evented + */ + hidden: null, + /** + * @cfg {Boolean} [disabled] + * Whether or not this component is disabled + * @accessor + * @evented + */ + disabled: null + }, + /** + * @property {Array} template + * An array of child elements to use as the children of the main element in the {@link + * #element} template. Only used if "children" are not specified explicitly in the + * {@link #element} template. + * @protected + */ + template: [], + /** + * The base CSS class to apply to this widget's element. + * Used as the prefix for {@link #ui}-specific class names. + * Defaults to the value of {@link #classCls} or (`x-` + the {@link #xtype}) of the widget + * if {@link #classCls} is `null` + * @protected + * @property + */ + baseCls: null, + /** + * A CSS class to apply to the main element that will be inherited down the class + * hierarchy. Subclasses may override this property on their prototype to add their + * own CSS class in addition to the CSS classes inherited from ancestor classes via + * the prototype chain. For example + * + * Ext.define('Foo', { + * extend: 'Ext.Widget', + * classCls: 'foo' + * }); + * + * Ext.define('Bar', { + * extend: 'Foo', + * classCls: 'bar' + * }); + * + * var bar = new Bar(); + * + * console.log(bar.element.className); // outputs 'foo bar' + * + * @protected + * @property + */ + classCls: null, + /** + * When set to `true` during widget class definition, that class will be the "root" for + * {@link #classCls} inheritance. Derived classes may set this to `true` to avoid + * inheriting a {@link #classCls} from their superclass. + * @property + * @protected + */ + classClsRoot: true, + // default empty classClsList since Ext.Widget has no classCls of its own + classClsList: [], + clearPropertiesOnDestroy: 'async', + focusEl: 'element', + ariaEl: 'element', + spaceRe: /\s+/, + /** + * @property {String} [noBorderCls] The CSS class to add to this component should not have a border. + * @private + * @readonly + */ + noBorderCls: Ext.baseCSSPrefix + 'noborder-trbl', + borderedCls: Ext.baseCSSPrefix + 'bordered', + disabledCls: Ext.baseCSSPrefix + 'disabled', + heightedCls: Ext.baseCSSPrefix + 'heighted', + widthedCls: Ext.baseCSSPrefix + 'widthed', + constructor: function(config) { + var me = this, + baseCls = me.baseCls, + renderTo = config && config.renderTo, + controller; + me.$iid = ++Ext.$nextIid; + if (baseCls == null || baseCls === true) { + me.baseCls = me.classCls || Ext.baseCSSPrefix + me.xtype; + } + if (config && ('baseCls' in config)) { + Ext.raise('baseCls cannot be used as an instance config. It must be specified at class definition time.'); + } + // We want to determine very early on whether or not we are a reference holder, + // so peek at either the incoming config or the class config to see if we have + // a controller defined. + if ((config && config.controller) || me.config.controller) { + me.referenceHolder = true; + } + me.initId(config); + me.initElement(); + if (renderTo) { + config = Ext.apply({}, config); + delete config.renderTo; + } + me.mixins.observable.constructor.call(me, config); + // Wait until configs have run to do this + if (me.focusable) { + me.initFocusableEvents(true); + } + if (renderTo) { + me.setRenderTo(renderTo); + } + me.syncUiCls(); + Ext.ComponentManager.register(me); + controller = me.getController(); + if (controller) { + controller.init(me); + } + }, + afterCachedConfig: function() { + // This method runs once for the first instance of this Widget type that is + // created. It runs after the element config has been processed for the first + // instance, and after all the cachedConfigs (whose appliers/updaters may modify + // the element) have been initialized. At this point we are ready to take the + // DOM that was generated for the first Element instance, clone it, and cache it + // on the prototype, so that it can be cloned by future instance to create their + // elements (see initElement). + var me = this, + prototype = me.self.prototype, + referenceList = me.referenceList, + renderElement = me.renderElement, + renderTemplate, element, i, ln, reference, elements; + // This is where we take the first instance's DOM and clone it as the template + // for future instances + prototype.renderTemplate = renderTemplate = document.createDocumentFragment(); + renderTemplate.appendChild(renderElement.clone(true, true)); + elements = renderTemplate.querySelectorAll('[id]'); + for (i = 0 , ln = elements.length; i < ln; i++) { + element = elements[i]; + element.removeAttribute('id'); + } + // initElement skips removal of reference attributes for the first instance so that + // the reference attributes will be present in the cached element when it is cloned. + // Now that we're done cloning and caching the template element, it is safe to + // remove the reference attributes from this instance's elements + for (i = 0 , ln = referenceList.length; i < ln; i++) { + reference = referenceList[i]; + me[reference].dom.removeAttribute('reference'); + } + }, + applyHidden: function(hidden) { + return !!hidden; + }, + applyDisabled: function(disabled) { + return !!disabled; + }, + updateDisabled: function(disabled) { + var me = this, + container = me.ownerFocusableContainer; + if (container) { + if (disabled) { + if (!container.beforeFocusableChildDisable.$nullFn) { + container.beforeFocusableChildDisable(me); + } + } else { + if (!container.beforeFocusableChildEnable.$nullFn) { + container.beforeFocusableChildEnable(me); + } + } + } + me.element.toggleCls(me.disabledCls, disabled); + if (me.focusable) { + if (disabled) { + me.disableFocusable(); + } else { + me.enableFocusable(); + } + } + if (container) { + if (disabled) { + if (!container.onFocusableChildDisable.$nullFn) { + container.onFocusableChildDisable(me); + } + } else { + if (!container.onFocusableChildEnable.$nullFn) { + container.onFocusableChildEnable(me); + } + } + } + }, + /** + * Disables this Component + */ + disable: function() { + this.setDisabled(true); + }, + /** + * Enables this Component + */ + enable: function() { + this.setDisabled(false); + }, + /** + * Returns `true` if this Component is currently disabled. + * @return {Boolean} `true` if currently disabled. + */ + isDisabled: function() { + return this.getDisabled(); + }, + /** + * Returns `true` if this Component is not currently disabled. + * @return {Boolean} `true` if not currently disabled. + */ + isEnabled: function() { + return !this.getDisabled(); + }, + applyTouchAction: function(touchAction, oldTouchAction) { + if (oldTouchAction != null) { + touchAction = Ext.merge({}, oldTouchAction, touchAction); + } + return touchAction; + }, + applyWidth: function(width) { + return this.filterLengthValue(width); + }, + applyHeight: function(height) { + return this.filterLengthValue(height); + }, + updateBorder: function(border) { + var me = this; + // If the border is null it means we should not suppress the border + border = border || border === null; + me.toggleCls(me.noBorderCls, !border); + me.toggleCls(me.borderedCls, !!border); + }, + clearListeners: function() { + var me = this; + me.mixins.observable.clearListeners.call(me); + me.mixins.componentDelegation.clearDelegatedListeners.call(me); + }, + /** + * Destroys the Widget. This method should not be overridden in custom Widgets, + * because it sets the flags and does final cleanup that must go last. Instead, + * override {@link #doDestroy} method to add functionality at destruction time. + */ + destroy: function() { + var me = this; + // isDestroying added for compat reasons + me.isDestroying = me.destroying = true; + me.doDestroy(); + // We need to defer clearing listeners until after doDestroy() completes, + // to let the interested parties fire events until the very end. + me.clearListeners(); + me.isDestroying = me.destroying = false; + // ComponentDelegation mixin does not install "after" interceptor on the + // base class destructor so we need to call it explicitly. + me.mixins.componentDelegation.destroyComponentDelegation.call(me); + me.callParent(); + }, + /** + * Perform the actual destruction sequence. This is the method to override in your + * subclasses to add steps specific to the destruction of custom Component or Widget. + * + * As a rule of thumb, subclasses should destroy their child Components, Elements, + * and/or other objects before calling parent method. Any object references will be + * nulled after this method has finished, to prevent the possibility of memory leaks. + * + * @since 6.2.0 + */ + doDestroy: function() { + var me = this, + referenceList = me.referenceList, + container = me.ownerFocusableContainer, + i, ln, reference; + // Many non-contained Widgets use the ownerCmp link to find their logical owner. + me.ownerCmp = null; + if (container && !container.onFocusableChildDestroy.$nullFn) { + container.onFocusableChildDestroy(me); + } + // Destroy all element references + for (i = 0 , ln = referenceList.length; i < ln; i++) { + reference = referenceList[i]; + if (me.hasOwnProperty(reference)) { + me[reference].destroy(); + me[reference] = null; + } + } + me.destroyBindable(); + Ext.ComponentManager.unregister(me); + }, + doFireEvent: function(eventName, args, bubbles) { + var me = this, + ret; + ret = me.mixins.observable.doFireEvent.call(me, eventName, args, bubbles); + // Could have been destroyed in event handler + if (ret !== false && !me.destroyed) { + ret = me.mixins.componentDelegation.doFireDelegatedEvent.call(me, eventName, args); + } + return ret; + }, + getBubbleTarget: function() { + return this.getRefOwner(); + }, + /** + * A template method for modifying the {@link #element} config before it is processed. + * By default adds the result of `this.getTemplate()` as the `children` array of + * {@link #element} if `children` were not specified in the original + * {@link #element} config. Typically this method should not need to be implemented + * in subclasses. Instead the {@link #element} property should be use to configure + * the element template for a given Widget subclass. + * + * This method is called once when the first instance of each Widget subclass is + * created. The element config object that is returned is cached and used as the template + * for all successive instances. The scope object for this method is the class prototype, + * not the instance. + * + * @return {Object} the element config object + * @protected + */ + getElementConfig: function() { + var me = this, + el = me.element; + if (!('children' in el)) { + el = Ext.apply({ + children: me.getTemplate() + }, el); + } + return el; + }, + /** + * Returns the height and width of the Component. + * @return {Object} The current `height` and `width` of the Component. + * @return {Number} return.width + * @return {Number} return.height + */ + getSize: function() { + return this.el.getSize(); + }, + getTemplate: function() { + return Ext.clone(this.template); + }, + /** + * @private + */ + getClassCls: function() { + var proto = this.self.prototype, + prototype = proto, + classes, classCls, i, ln; + while (prototype) { + classCls = prototype.hasOwnProperty('classCls') ? prototype.classCls : null; + if (classCls) { + if (classCls instanceof Array) { + for (i = 0 , ln = classCls.length; i < ln; i++) { + (classes || (classes = [])).push(classCls[i]); + } + } else { + (classes || (classes = [])).push(classCls); + } + } + if (prototype.classClsRoot && prototype.hasOwnProperty('classClsRoot')) { + break; + } + prototype = prototype.superclass; + } + if (classes) { + proto.classClsList = classes; + } + return classes; + }, + hide: function() { + this.setHidden(true); + }, + /** + * Initializes the Element for this Widget instance. If this is the first time a + * Widget of this type has been instantiated the {@link #element} config will be + * processed to create an Element. This Element is then cached on the prototype (see + * afterCachedConfig) so that future instances can obtain their element by simply + * cloning the Element that was cached by the first instance. + * @protected + */ + initElement: function() { + var me = this, + prototype = me.self.prototype, + id = me.getId(), + // The double assignment is intentional to workaround a JIT issue that prevents + // me.referenceList from being assigned in random scenarios. The issue occurs on 4th gen + // iPads and lower, possibly other older iOS devices. See EXTJS-16494. + referenceList = me.referenceList = me.referenceList = [], + isFirstInstance = !prototype.hasOwnProperty('renderTemplate'), + /** + * @property {Object} uiReferences + * @private + * A map that tracks all reference elements configured with a `uiCls`. + * Contains the `element` reference by default since the `element` always gets + * non-suffixed ui-specific CSS class names added to it (see {@link #syncUiCls}) + */ + uiReferences = prototype.hasOwnProperty('uiReferences') ? prototype.uiReferences : (prototype.uiReferences = { + element: '' + }), + renderTemplate, renderElement, renderConfig, element, referenceNodes, i, ln, referenceNode, reference, classCls, uiCls, baseCls, referenceElement; + if (isFirstInstance) { + // this is the first instantiation of this widget type. Process the element + // config from scratch to create our Element. + renderTemplate = document.createDocumentFragment(); + renderConfig = me.processElementConfig.call(prototype); + renderElement = Ext.Element.create(renderConfig, true); + renderTemplate.appendChild(renderElement); + // Collect all nodes that were configured with a uiCls and stash the reference + // and uiCls names in a map so they can be used to update the ui class names + // at a later time (see syncUiCls). + referenceNodes = renderTemplate.querySelectorAll('[uiCls]'); + for (i = 0 , ln = referenceNodes.length; i < ln; i++) { + referenceNode = referenceNodes[i]; + reference = referenceNode.getAttribute('reference'); + uiCls = referenceNode.getAttribute('uiCls'); + if (!reference) { + Ext.raise('Cannot render element with uiCls="' + uiCls + '". uiCls is only allowed on elements that have a reference name.'); + } + uiReferences[reference] = uiCls; + // uiCls attribute has served its purpose - we have cached it in the + // uiReferences map so it does not need to remain in the template + referenceNode.removeAttribute('uiCls'); + } + } else { + // we have already created an instance of this Widget type, so the element + // config has already been processed, and the resulting DOM has been cached on + // the prototype (see afterCachedConfig). This means we can obtain our element + // by simply cloning the cached element. + renderTemplate = me.renderTemplate.cloneNode(true); + renderElement = renderTemplate.firstChild; + } + referenceNodes = renderTemplate.querySelectorAll('[reference]'); + for (i = 0 , ln = referenceNodes.length; i < ln; i++) { + referenceNode = referenceNodes[i]; + reference = referenceNode.getAttribute('reference'); + if (!isFirstInstance) { + // on first instantiation we do not clean the reference attributes here. + // This is because this instance's element will be used as the template + // for future instances, and we need the reference attributes to be + // present in the template so that future instances can resolve their + // references. afterCachedConfig is responsible for removing the + // reference attributes from the DOM for the first instance after the + // Element has been cloned and cached as the template. + referenceNode.removeAttribute('reference'); + } + if (reference === 'element') { + if (element) { + // already resolved a reference named element - can't have two + Ext.raise("Duplicate 'element' reference detected in '" + me.$className + "' template."); + } + referenceNode.id = id; + // element reference needs to be established ASAP, so add the reference + // immediately, not "on-demand" + element = me.el = me.addElementReference(reference, referenceNode); + // Poke our id in our magic attribute to enable Component#from + element.dom.setAttribute('data-componentid', id); + if (isFirstInstance) { + classCls = me.getClassCls(); + if (classCls) { + element.addCls(classCls); + } + baseCls = me.baseCls; + if (baseCls && (baseCls !== me.classCls)) { + element.addCls(baseCls); + } + } + } else { + uiCls = uiReferences[reference]; + if (uiCls && isFirstInstance) { + // Elements configured with a uiCls must always have non-ui-specific + // class names for base styling. For example, if the classCls is x-foo + // a reference element with a uiCls of 'bar' must always have a class + // name of x-foo-bar, regardless of whether or not the widget was + // configured with a ui. + // On the first instance these element must be immediately instantiated + // so that the CSS class names can be added in the render template, + // but they can be lazily instantiated on successive instances. + referenceElement = me.addElementReference(reference, referenceNode); + me.initUiReference(reference, uiCls, false); + } else { + me.addElementReferenceOnDemand(reference, referenceNode); + } + } + // At this point focusEl and ariaEl are still reference names + if (reference === me.focusEl) { + me.addElementReference('focusEl', referenceNode); + } + if (reference === me.ariaEl) { + me.addElementReferenceOnDemand('ariaEl', referenceNode); + } + referenceList.push(reference); + } + if (!element) { + Ext.raise("No 'element' reference found in '" + me.$className + "' template."); + } + if (renderElement === element.dom) { + me.renderElement = element; + } else { + me.addElementReferenceOnDemand('renderElement', renderElement); + } + renderElement.setAttribute(me.dataXid, me.$iid); + }, + dataXid: 'data-' + Ext.baseCSSPrefix.substr(0, Ext.baseCSSPrefix.length - 1) + 'id', + /** + * Tests whether this Widget matches a {@link Ext.ComponentQuery ComponentQuery} + * selector string. + * @param {String} selector The selector string to test against. + * @return {Boolean} `true` if this Widget matches the selector. + */ + is: function(selector) { + return Ext.ComponentQuery.is(this, selector); + }, + /** + * Returns `true` if this Component is currently hidden. + * @param {Boolean/Ext.Widget} [deep=false] `true` to check if this component + * is hidden because a parent container is hidden. Alternatively, a reference to the + * top-most parent at which to stop climbing. + * @return {Boolean} `true` if currently hidden. + */ + isHidden: function(deep) { + var hidden = !!this.getHidden(), + owner; + if (!hidden && deep) { + owner = this.getRefOwner(); + while (owner && owner !== deep && !hidden) { + hidden = !!owner.getHidden(); + owner = owner.getRefOwner(); + } + } + return hidden; + }, + /** + * Returns `true` if this Component is currently visible. + * + * A Widget is visible if its element is not hidden, *and* has been + * {@link #property!rendered} *and* has not been destroyed. + * + * @param {Boolean} [deep=false] `true` to check if this component + * is visible and all parents are also visible. + * + * Contrast this with the {@link #isHidden} method which just checks the + * hidden state of the component. + * @return {Boolean} `true` if currently visible. + */ + isVisible: function(deep) { + return this.rendered && !this.destroyed && !this.isHidden(deep); + }, + /** + * Tests whether or not this Component is of a specific xtype. This can test whether this Component is descended + * from the xtype (default) or whether it is directly of the xtype specified (`shallow = true`). + * **If using your own subclasses, be aware that a Component must register its own xtype + * to participate in determination of inherited xtypes.__ + * + * For a list of all available xtypes, see the {@link Ext.Component} header. + * + * Example usage: + * + * var t = new Ext.field.Text(); + * var isText = t.isXType('textfield'); // true + * var isBoxSubclass = t.isXType('field'); // true, descended from Ext.field.Field + * var isBoxInstance = t.isXType('field', true); // false, not a direct Ext.field.Field instance + * + * @param {String} xtype The xtype to check for this Component. + * @param {Boolean} shallow (optional) `false` to check whether this Component is descended from the xtype (this is + * the default), or `true` to check whether this Component is directly of the specified xtype. + * @return {Boolean} `true` if this component descends from the specified xtype, `false` otherwise. + */ + isXType: function(xtype, shallow) { + return shallow ? (Ext.Array.indexOf(this.xtypes, xtype) !== -1) : !!this.xtypesMap[xtype]; + }, + /** + * Gets a named template instance for this class. See {@link Ext.XTemplate#getTpl}. + * @param {String} name The name of the property that holds the template. + * @return {Ext.XTemplate} The template, `null` if not found. + * + * @since 6.2.0 + */ + lookupTpl: function(name) { + return Ext.XTemplate.getTpl(this, name); + }, + owns: function(element) { + var result = false, + cmp; + if (element.isEvent) { + element = element.target; + } else if (element.isElement) { + element = element.dom; + } + cmp = Ext.Component.from(element); + if (cmp) { + result = (cmp === this) || (!!cmp.up(this)); + } + return result; + }, + render: function(container, insertBeforeElement) { + if (container && container.isWidget) { + container = container.el; + } + var dom = this.renderElement.dom, + containerDom = Ext.getDom(container), + insertBeforeChildDom; + if (Ext.isNumber(insertBeforeChildDom)) { + insertBeforeElement = containerDom.childNodes[insertBeforeElement]; + } + insertBeforeChildDom = Ext.getDom(insertBeforeElement); + if (containerDom) { + if (insertBeforeChildDom) { + containerDom.insertBefore(dom, insertBeforeChildDom); + } else { + containerDom.appendChild(dom); + } + // A component is rendered if it is in the document. + // A display:none component will have no offsetParent + // so offsetParent is not a valid test for renderedness. + this.setRendered(Ext.getBody().contains(dom), true); + } + }, + /** + * Toggles the specified CSS class on this element (removes it if it already exists, + * otherwise adds it). + * @param {String} className The CSS class to toggle. + * @param {Boolean} [state] If specified as `true`, causes the class to be added. If + * specified as `false`, causes the class to be removed. + * @chainable + */ + toggleCls: function(className, state) { + this.element.toggleCls(className, state); + return this; + }, + resolveListenerScope: function(defaultScope, skipThis) { + // break the tie between Observable and Inheritable resolveListenerScope + return this.mixins.inheritable.resolveListenerScope.call(this, defaultScope, skipThis); + }, + /** + * Sets the size of the Component. + * @param {Number} width The new width for the Component. + * @param {Number} height The new height for the Component. + */ + setSize: function(width, height) { + // Allow setSize to be called with a result from getSize. + if (width && typeof width === 'object') { + return this.setSize(width.width, width.height); + } + if (width !== undefined) { + this.setWidth(width); + } + if (height !== undefined) { + this.setHeight(height); + } + }, + show: function() { + this.setHidden(false); + }, + /** + * Adds a CSS class (or classes) to this Component's rendered element. + * @param {String/String[]} cls The CSS class(es) to add. + * @param {String} [prefix=""] Optional prefix to add to each class. + * @param {String} [suffix=""] Optional suffix to add to each class. + */ + addCls: function(cls, prefix, suffix) { + if (!this.destroyed) { + this.el.replaceCls(null, cls, prefix, suffix); + } + }, + applyCls: function(cls) { + return cls && Ext.dom.Element.splitCls(cls); + }, + applyUi: function(ui) { + return this.parseUi(ui, true); + }, + /** + * Removes the given CSS class(es) from this widget's primary element. + * @param {String/String[]} cls The class(es) to remove. + * @param {String} [prefix=""] Optional prefix to prepend before each class. + * @param {String} [suffix=""] Optional suffix to append to each class. + */ + removeCls: function(cls, prefix, suffix) { + if (!this.destroyed) { + this.el.replaceCls(cls, null, prefix, suffix); + } + }, + /** + * Replaces specified classes with the newly specified classes. + * It uses the {@link #addCls} and {@link #removeCls} methods, so if the class(es) you + * are removing don't exist, it will still add the new classes. + * @param {String/String[]} oldCls The class(es) to remove. + * @param {String/String[]} newCls The class(es) to add. + * @param {String} [prefix=""] Optional prefix to prepend before each class. + * @param {String} [suffix=""] Optional suffix to append to each class. + */ + replaceCls: function(oldCls, newCls, prefix, suffix) { + if (!this.destroyed) { + this.el.replaceCls(oldCls, newCls, prefix, suffix); + } + }, + /** + * Checks if the specified CSS class exists on this element's DOM node. + * @param {String} className The CSS class to check for. + * @return {Boolean} `true` if the class exists, else `false`. + * @method + */ + hasCls: function(className) { + return this.el.hasCls(className); + }, + /** + * @private + * All cls methods directly report to the {@link #cls} configuration, so anytime it changes, {@link #updateCls} will be called + */ + updateCls: function(newCls, oldCls) { + this.element.replaceCls(oldCls, newCls); + }, + updateHidden: function(hidden) { + var me = this, + element = me.renderElement, + container = me.ownerFocusableContainer; + // If we are owned by a FocusableContainer, allow that to redirect + // focus if we are being hidden. + if (container) { + if (hidden) { + if (!container.beforeFocusableChildHide.$nullFn) { + container.beforeFocusableChildHide(me); + } + } else { + if (!container.beforeFocusableChildShow.$nullFn) { + container.beforeFocusableChildShow(me); + } + } + } + // Not owned by a FocusableContainer - revert focus to previous focus holder. + else if (hidden) { + // Part of the Focusable mixin API. + // If we have focus now, move focus back to whatever had it before. + me.revertFocus(); + } + if (element && !element.destroyed) { + if (hidden) { + element.hide(); + } else { + element.show(); + } + } + if (me.focusableContainer && me.activateFocusableContainer) { + me.activateFocusableContainer(!hidden); + } + if (container) { + if (hidden) { + if (!container.onFocusableChildHide.$nullFn) { + container.onFocusableChildHide(me); + } + } else { + if (!container.onFocusableChildShow.$nullFn) { + container.onFocusableChildShow(me); + } + } + } + }, + updateRipple: function(ripple) { + var me = this, + el = me.el; + if (el) { + el.un('touchstart', 'onRippleStart', me); + el.un('touchend', 'onRippleStart', me); + el.destroyAllRipples(); + if (ripple.release) { + el.on('touchend', 'onRippleStart', me); + } else { + el.on('touchstart', 'onRippleStart', me); + } + } + }, + shouldRipple: function(e) { + var me = this, + disabled = me.getDisabled && me.getDisabled(), + el = me.el, + ripple = !disabled && me.getRipple(), + target; + if (ripple && e) { + target = e.getTarget(me.noRippleSelector); + if (target) { + if ((el.dom === target) || el.contains(target)) { + ripple = null; + } + } + } + return ripple; + }, + onRippleStart: function(e) { + var ripple = this.shouldRipple(e); + if (e.button === 0 && ripple) { + this.el.ripple(e, ripple); + } + }, + /** + * @protected + */ + applyStyle: function(style, oldStyle) { + // If we're doing something with data binding, say: + // style: { + // backgroundColor: 'rgba({r}, {g}, {b}, 1)' + // } + // The inner values will change, but the object won't, so force + // a copy to be created here if necessary + if (oldStyle && style === oldStyle && Ext.isObject(oldStyle)) { + style = Ext.apply({}, style); + } + this.element.applyStyles(style); + return null; + }, + getStyle: function() { + Ext.Error.raise("'style' is a write-only config. To query element styles use the Ext.dom.Element API."); + }, + updateRenderTo: function(newContainer) { + this.render(newContainer); + }, + updateTouchAction: function(touchAction) { + var name, childEl, value, hasRootActions; + for (name in touchAction) { + childEl = this[name]; + value = touchAction[name]; + if (childEl && childEl.isElement) { + childEl.setTouchAction(value); + } else { + hasRootActions = true; + } + } + if (hasRootActions) { + this.el.setTouchAction(touchAction); + } + }, + updateUi: function() { + if (!this.isConfiguring) { + this.syncUiCls(); + } + }, + /** + * @param width + * @protected + */ + updateWidth: function(width) { + var el = this.el; + el.setWidth(width); + el.toggleCls(this.widthedCls, width != null && width !== 'auto'); + }, + /** + * @param height + * @protected + */ + updateHeight: function(height) { + var el = this.el; + el.setHeight(height); + el.toggleCls(this.heightedCls, height != null && height !== 'auto'); + }, + /** + * @private + */ + isWidthed: function() { + var width = this.getWidth(); + return width != null && width !== 'auto'; + }, + /** + * @private + */ + isHeighted: function() { + var height = this.getHeight(); + return height != null && height !== 'auto'; + }, + /** + * Walks up the ownership hierarchy looking for an ancestor Component which matches + * the passed simple selector. + * + * Example: + * + * var owningTabPanel = grid.up('tabpanel'); + * + * @param {String} selector (optional) The simple selector to test. + * @param {String/Number/Ext.Component} [limit] This may be a selector upon which to stop the upward scan, or a limit of the number of steps, or Component reference to stop on. + * @return {Ext.Container} The matching ancestor Container (or `undefined` if no match was found). + */ + up: function(selector, limit) { + var result = this.getRefOwner(), + limitSelector = typeof limit === 'string', + limitCount = typeof limit === 'number', + limitComponent = limit && limit.isComponent, + steps = 0; + if (selector) { + for (; result; result = result.getRefOwner()) { + if (result.destroyed) { + return null; + } + steps++; + if (selector.isComponent || selector.isWidget) { + if (result === selector) { + return result; + } + } else { + if (Ext.ComponentQuery.is(result, selector)) { + return result; + } + } + // Stop when we hit the limit selector + if (limitSelector && result.is(limit)) { + return; + } + if (limitCount && steps === limit) { + return; + } + if (limitComponent && result === limit) { + return; + } + } + } + return result; + }, + updateLayout: Ext.emptyFn, + // empty fn for modern/classic compat + updateInstanceCls: function(instanceCls, oldInstanceCls) { + var me = this, + el = me.el, + classClsList = me.classClsList, + Array = Ext.Array, + uiReferences = me.uiReferences, + referenceName, referenceElement, i, ln, cls, uiCls; + if (oldInstanceCls) { + el.removeCls(oldInstanceCls); + oldInstanceCls = Array.from(oldInstanceCls); + for (i = 0 , ln = oldInstanceCls.length; i < ln; i++) { + cls = oldInstanceCls[i]; + Array.remove(classClsList, cls); + for (referenceName in uiReferences) { + referenceElement = me[referenceName]; + uiCls = uiReferences[referenceName]; + referenceElement.removeCls(cls + '-' + uiCls); + } + } + } + if (instanceCls) { + el.addCls(instanceCls); + instanceCls = Array.from(instanceCls); + // clone the classClsList so that the instanceCls is not shared on the prototype + me.classClsList = classClsList.concat(instanceCls); + for (i = 0 , ln = instanceCls.length; i < ln; i++) { + cls = instanceCls[i]; + for (referenceName in uiReferences) { + referenceElement = me[referenceName]; + uiCls = uiReferences[referenceName]; + referenceElement.addCls(cls + '-' + uiCls); + } + } + } + if (!me.isConfiguring) { + me.syncUiCls(); + } + }, + // getter for backward compatibility with < 6.5 where baseCls was a config + getBaseCls: function() { + return this.baseCls; + }, + setBaseCls: function() { + Ext.raise('baseCls cannot be reconfigured. It must be specified at class definition time.'); + }, + onClassExtended: function(Class, members) { + if (members.config && members.config.baseCls) { + Ext.raise('baseCls must be declared directly on the class body. Please move it outside of the config block.'); + } + }, + //------------------------------------------------------------------------- + privates: { + _hideModes: { + clip: 'CLIP', + display: 'DISPLAY', + offsets: 'OFFSETS', + opacity: 'OPACITY', + visibility: 'VISIBILITY' + }, + noRippleSelector: '.' + Ext.baseCSSPrefix + 'no-ripple', + /** + * Reduces instantiation time for a Widget by lazily instantiating Ext.Element + * references the first time they are used. This optimization only works for elements + * with no listeners specified. + * + * @param {String} name The name of the reference + * @param {HTMLElement} domNode + * @private + */ + addElementReferenceOnDemand: function(name, domNode) { + if (this._elementListeners[name]) { + // if the element was configured with listeners then we cannot add the + // reference on demand because we need to make sure the element responds + // immediately to any events, even if its reference is never accessed + this.addElementReference(name, domNode); + } else { + // no listeners - element reference can be resolved on demand. + // TODO: measure if this has any significant performance impact. + Ext.Object.defineProperty(this, name, { + get: function() { + if (this.destroyed) { + return; + } + // remove the property that was defined using defineProperty because + // addElementReference will set the property on the instance, - the + // getter is not needed after the first access. + delete this[name]; + return this.addElementReference(name, domNode); + }, + configurable: true + }); + } + }, + /** + * Adds an element reference to this Widget instance. + * @param {String} name The name of the reference + * @param {HTMLElement} domNode + * @return {Ext.dom.Element} + * @private + */ + addElementReference: function(name, domNode) { + var me = this, + referenceEl = me[name] = Ext.get(domNode), + listeners = me._elementListeners[name], + eventName, listener; + referenceEl.skipGarbageCollection = true; + referenceEl.component = me; + if (listeners) { + // TODO: These references will be needed when we use delegation to listen + // for element events, but for now, we'll just attach the listeners directly + // referenceEl.reference = name; + // referenceEl.component = me; + // referenceEl.listeners = listeners; + // At this point "listeners" exists on the class prototype. We need to clone + // it before poking the scope reference onto it, because it is used as the + // options object by Observable and so can't be safely shared. + // + listeners = Ext.clone(listeners); + // If the listener is specified as an object it needs to have the scope + // option added to that object, for example: + // + // { + // click: { + // fn: 'onClick', + // scope: this + // } + // } + // + for (eventName in listeners) { + listener = listeners[eventName]; + if (typeof listener === 'object') { + listener.scope = me; + } + } + // The outermost listeners object always needs the scope option. This covers + // a listeners object with the following shape: + // + // { + // click: 'onClick' + // scope: this + // } + // + listeners.scope = me; + // do this *after* the above loop over listeners + // Hopefully in the future we can stop calling on() here, and just use + // event delegation to dispatch events to Widgets that have declared their + // listeners in their template. + // + referenceEl.on(listeners); + } + return referenceEl; + }, + detachFromBody: function() { + // See reattachToBody + Ext.getDetachedBody().appendChild(this.element, true); + this.isDetached = true; + }, + reattachToBody: function() { + var detachedBody; + if (this.isDetached) { + detachedBody = Ext.getDetachedBody(); + if (detachedBody.contains(this.element)) { + Ext.getBody().appendChild(this.element, true); + } + } + // See detachFromBody + this.isDetached = false; + }, + /** + * @private + */ + doAddListener: function(name, fn, scope, options, order, caller, manager) { + var me = this, + elementName = options && options.element, + delegate = options && options.delegate, + listeners, eventOptions, option; + if (elementName) { + if (Ext.Array.indexOf(me.referenceList, elementName) === -1) { + Ext.Logger.error("Adding event listener with an invalid element reference of '" + elementName + "' for this component. Available values are: '" + me.referenceList.join("', '") + "'", me); + } + listeners = {}; + listeners[name] = fn; + if (scope) { + listeners.scope = scope; + } + eventOptions = Ext.Element.prototype.$eventOptions; + for (option in options) { + if (eventOptions[option]) { + listeners[option] = options[option]; + } + } + me.mon(me[elementName], listeners); + return; + } else if (delegate) { + me.mixins.componentDelegation.addDelegatedListener.call(me, name, fn, scope, options, order, caller, manager); + return; + } + me.callParent([ + name, + fn, + scope, + options, + order, + caller, + manager + ]); + }, + doRemoveListener: function(eventName, fn, scope) { + var me = this; + me.mixins.observable.doRemoveListener.call(me, eventName, fn, scope); + me.mixins.componentDelegation.removeDelegatedListener.call(me, eventName, fn, scope); + }, + filterLengthValue: function(value) { + if (!value && value !== 0) { + return null; + } + return value; + }, + /** + * Called for the first instance of this Widget to create an object that contains the + * listener configs for all of the element references keyed by reference name. The + * object is cached on the prototype and has the following shape: + * + * _elementListeners: { + * element: { + * click: 'onClick', + * scope: this + * }, + * fooReference: { + * tap: { + * fn: someFunction, + * delay: 100 + * } + * } + * } + * + * The returned object is prototype chained to the _elementListeners object of its + * superclass, and each key in the object is prototype chained to object with the + * corresponding key in the superclass _elementListeners. This allows element + * listeners to be inherited and overridden when subclassing widgets. + * + * This method is invoked with the prototype object as the scope + * + * @private + */ + initElementListeners: function(elementConfig) { + var prototype = this, + superPrototype = prototype.self.superclass, + superElementListeners = superPrototype._elementListeners, + reference = elementConfig.reference, + children = elementConfig.children, + elementListeners, listeners, superListeners, ln, i; + if (prototype.hasOwnProperty('_elementListeners')) { + elementListeners = prototype._elementListeners; + } else { + elementListeners = prototype._elementListeners = (superElementListeners ? Ext.Object.chain(superElementListeners) : {}); + } + if (reference) { + listeners = elementConfig.listeners; + if (listeners) { + if (superElementListeners) { + superListeners = superElementListeners[reference]; + if (superListeners) { + listeners = Ext.Object.chain(superListeners); + Ext.apply(listeners, elementConfig.listeners); + } + } + elementListeners[reference] = listeners; + // null out the listeners on the elementConfig, since we are going to pass + // it to Element.create(), and don't want "listeners" to be treated as an + // attribute + elementConfig.listeners = null; + } + } + if (children) { + for (i = 0 , ln = children.length; i < ln; i++) { + prototype.initElementListeners(children[i]); + } + } + }, + initId: function(config) { + var me = this, + defaultConfig = me.config, + id = (config && config.id) || (defaultConfig && defaultConfig.id); + if (id) { + // setId() will normally be inherited from Identifiable, unless "id" is a + // proper config, in which case it will be generated by the config system. + me.setId(id); + me.id = id; + } else { + // if no id configured, generate one (Identifiable) + me.getId(); + } + }, + measure: function(dimension) { + return this.element.measure(dimension); + }, + /** + * Recursively processes the element templates for this class and its superclasses, + * ascending the hierarchy until it reaches a superclass whose element template + * has already been processed. This method is invoked using the prototype as the scope. + * + * @private + * @return {Object} + */ + processElementConfig: function() { + var prototype = this, + superPrototype = prototype.self.superclass, + elementConfig; + if (prototype.hasOwnProperty('_elementConfig')) { + elementConfig = prototype._elementConfig; + } else { + // cache the elementConfig on the prototype, since we may end up here multiple + // times if there are multiple subclasses + elementConfig = prototype._elementConfig = prototype.getElementConfig(); + if (superPrototype.isWidget) { + // Before initializing element listeners we must process the element template + // for our superclass so that we can chain our listeners to the superclass listeners + prototype.processElementConfig.call(superPrototype); + } + // initElementListeners needs to be called BEFORE passing the element config + // along to Ext.Element.create(). This ensures that the listener meta data is + // saved, and then the listeners objects are removed from the element config + // so that they do not get added as attributes by create() + prototype.initElementListeners(elementConfig); + } + return elementConfig; + }, + parseUi: function(ui, asString) { + ui = Ext.String.splitWords(ui); + if (asString) { + ui = ui.join(' '); + } + return ui; + }, + addUi: function(ui) { + this.setUi(this.doAddUi(ui, this.getUi())); + }, + doAddUi: function(ui, oldUi) { + var me = this, + newUi = null, + i, u, len; + if (ui) { + ui = me.parseUi(ui); + len = ui.length; + oldUi = me.parseUi(oldUi); + for (i = 0; i < len; i++) { + u = ui[i]; + if (Ext.Array.indexOf(oldUi, u) === -1) { + oldUi.push(u); + } + } + newUi = oldUi.join(' '); + } + return newUi; + }, + removeUi: function(ui) { + this.setUi(this.doRemoveUi(ui, this.getUi())); + }, + doRemoveUi: function(ui, oldUi) { + var me = this, + newUi = null, + i, u, index, len; + if (ui) { + ui = me.parseUi(ui); + len = ui.length; + oldUi = me.parseUi(oldUi); + for (i = 0; i < len; i++) { + u = ui[i]; + index = Ext.Array.indexOf(oldUi, u); + if (index !== -1) { + oldUi.splice(index, 1); + } + } + newUi = oldUi.join(' '); + } + return newUi; + }, + /** + * Initializes a "uiReference". Ui rerefences are reference elements that have + * classCls and ui info in their CSS class names. They can be used by setting + * uiCls in the template, or by invoking this method to setup the ui reference + * after element/template initialization (Toolable uses this for its dock wrapper) + * @param {String} referenceName + * @param {String} uiCls + * @param {Boolean} [isInstance=false] pass `false` if this is not an instance-level + * reference + * @private + */ + initUiReference: function(referenceName, uiCls, isInstance) { + var me = this, + referenceElement = me[referenceName], + baseCls = me.baseCls, + classClsList = me.classClsList, + cls = [], + i, n; + isInstance = (isInstance !== false); + if (isInstance) { + // clone so we don't modify the prototype uiReferences + if (!me.hasOwnProperty('uiReferences')) { + me.uiReferences = Ext.clone(me.uiReferences); + } + me.uiReferences[referenceName] = uiCls; + } + uiCls = '-' + uiCls; + if (baseCls && (baseCls !== me.classCls)) { + cls.push(baseCls + uiCls); + } + if (classClsList) { + for (i = 0 , n = classClsList.length; i < n; i++) { + cls.push(classClsList[i] + uiCls); + } + } + referenceElement.addCls(cls); + if (isInstance && !me.isConfiguring) { + me.syncUiCls(); + } + }, + syncUiCls: function(refs) { + var me = this, + ui = me.getUi(), + currentUiCls = me.currentUiCls || (me.currentUiCls = {}), + baseCls = me.baseCls, + uiReferences = refs || me.uiReferences, + classClsList = me.classClsList, + classClsListLen = classClsList ? classClsList.length : 0, + uiCls, uiLen, refName, refEl, cls, suffix, uiSuffix, i, j; + if (ui) { + ui = me.parseUi(ui); + uiLen = ui.length; + } + for (refName in uiReferences) { + refEl = me[refName]; + uiCls = []; + if (refEl) { + cls = currentUiCls[refName]; + if (cls) { + refEl.removeCls(cls); + } + if (ui) { + suffix = uiReferences[refName]; + suffix = suffix ? ('-' + suffix) : ''; + for (i = 0; i < uiLen; i++) { + uiSuffix = '-' + ui[i] + suffix; + if (baseCls && (baseCls !== me.classCls)) { + uiCls.push(baseCls + uiSuffix); + } + if (classClsList) { + for (j = 0; j < classClsListLen; j++) { + uiCls.push(classClsList[j] + uiSuffix); + } + } + } + refEl.addCls(uiCls); + currentUiCls[refName] = uiCls; + } + } + } + }, + applyHideMode: function(mode) { + return mode || 'display'; + }, + updateHideMode: function(mode) { + var me = this, + el = me.el, + shouldToggle = me.getHidden(); + if (!me._hideModes[mode]) { + Ext.raise('Invalid hideMode: "' + mode + '" (must be one of: "' + Object.keys(me._hideModes).join('", "') + '")'); + } + if (shouldToggle) { + el.show(); + } + me.renderElement.setVisibilityMode(Ext.Element[me._hideModes[mode]]); + if (shouldToggle) { + el.hide(); + } + }, + updateUserCls: function(newCls, oldCls) { + this.element.replaceCls(oldCls, newCls); + } + } +}, function(Widget) { + var prototype = Widget.prototype; + // event options for listeners that use the "element" event options must also include + // event options from Ext.Element + (prototype.$elementEventOptions = Ext.Object.chain(Ext.Element.prototype.$eventOptions)).element = 1; + (prototype.$eventOptions = Ext.Object.chain(prototype.$eventOptions)).delegate = 1; + /** + * @member Ext + * @method updateWidget + * @inheritdoc Ext.Factory#update + * @since 6.5.1 + */ + Ext.updateWidget = Ext.Factory.widget.update; +}); + +/** + * @class Ext.Widget + */ +Ext.define('Ext.overrides.Widget', { + override: 'Ext.Widget', + uses: [ + 'Ext.Component', + 'Ext.layout.component.Auto' + ], + $configStrict: false, + isComponent: true, + liquidLayout: true, + // in Ext JS the rendered flag is set as soon as a component has its element. Since + // widgets always have an element when constructed, they are always considered to be + // "rendered" + rendered: true, + rendering: true, + config: { + renderTo: null + }, + constructor: function(config) { + var me = this, + renderTo; + me.callParent([ + config + ]); + // initialize the component layout + me.getComponentLayout(); + renderTo = me.getRenderTo(); + if (renderTo) { + me.render(renderTo); + } + }, + addClsWithUI: function(cls) { + this.el.addCls(cls); + }, + afterComponentLayout: Ext.emptyFn, + updateLayout: function() { + var owner = this.getRefOwner(); + if (owner) { + owner.updateLayout(); + } + }, + destroy: function() { + var me = this, + ownerCt = me.ownerCt; + if (ownerCt && ownerCt.remove) { + ownerCt.remove(me, false); + } + me.callParent(); + }, + finishRender: function() { + this.rendering = false; + this.initBindable(); + this.initKeyMap(); + }, + getAnimationProps: function() { + // see Ext.util.Animate mixin + return {}; + }, + getComponentLayout: function() { + var me = this, + layout = me.componentLayout; + if (!layout) { + layout = me.componentLayout = new Ext.layout.component.Auto(); + layout.setOwner(me); + } + return layout; + }, + getEl: function() { + return this.element; + }, + /** + * @private + * Needed for when widget is rendered into a grid cell. The class to add to the cell element. + * @member Ext.Widget + */ + getTdCls: function() { + return Ext.baseCSSPrefix + this.getTdType() + '-' + (this.ui || 'default') + '-cell'; + }, + /** + * @private + * Partner method to {@link #getTdCls}. + * + * Returns the base type for the component. Defaults to return `this.xtype`, but + * All derived classes of {@link Ext.form.field.Text TextField} can return the type 'textfield', + * and all derived classes of {@link Ext.button.Button Button} can return the type 'button' + * @member Ext.Widget + */ + getTdType: function() { + return this.xtype; + }, + getItemId: function() { + // needed by ComponentQuery + return this.itemId || this.id; + }, + getSizeModel: function() { + return Ext.Component.prototype.getSizeModel.apply(this, arguments); + }, + onAdded: function(container, pos, instanced) { + var me = this; + me.ownerCt = container; + me.onInheritedAdd(me, instanced); + // this component is no longer detached from the body + me.isDetached = false; + }, + onRemoved: function(destroying) { + this.onInheritedRemove(destroying); + this.ownerCt = this.ownerLayout = null; + }, + parseBox: function(box) { + return Ext.Element.parseBox(box); + }, + removeClsWithUI: function(cls) { + this.el.removeCls(cls); + }, + render: function(container, position) { + var me = this, + element = me.element, + proto = Ext.Component.prototype, + nextSibling; + if (!me.ownerCt || me.floating) { + if (Ext.scopeCss) { + element.addCls(proto.rootCls); + } + element.addCls(proto.borderBoxCls); + } + if (position) { + nextSibling = container.childNodes[position]; + if (nextSibling) { + Ext.fly(container).insertBefore(element, nextSibling); + return; + } + } + Ext.fly(container).appendChild(element); + me.finishRender(); + }, + setPosition: function(x, y) { + this.el.setLocalXY(x, y); + }, + up: function() { + return Ext.Component.prototype.up.apply(this, arguments); + }, + isAncestor: function() { + return Ext.Component.prototype.isAncestor.apply(this, arguments); + }, + onFocusEnter: function() { + return Ext.Component.prototype.onFocusEnter.apply(this, arguments); + }, + onFocusLeave: function() { + return Ext.Component.prototype.onFocusLeave.apply(this, arguments); + }, + isLayoutChild: function(candidate) { + var ownerCt = this.ownerCt; + return ownerCt ? (ownerCt === candidate || ownerCt.isLayoutChild(candidate)) : false; + }, + privates: { + doAddListener: function(name, fn, scope, options, order, caller, manager) { + if (name == 'painted' || name == 'resize') { + this.element.doAddListener(name, fn, scope || this, options, order); + } + this.callParent([ + name, + fn, + scope, + options, + order, + caller, + manager + ]); + }, + doRemoveListener: function(name, fn, scope) { + if (name == 'painted' || name == 'resize') { + this.element.doRemoveListener(name, fn, scope); + } + this.callParent([ + name, + fn, + scope + ]); + } + } +}, function(Cls) { + var prototype = Cls.prototype; + if (Ext.isIE9m) { + // Since IE8/9 don't not support Object.defineProperty correctly we can't add the reference + // nodes on demand, so we just fall back to adding all references up front. + prototype.addElementReferenceOnDemand = prototype.addElementReference; + } +}); + +/** + * @private + */ +Ext.define('Ext.ProgressBase', { + mixinId: 'progressbase', + config: { + /** + * @cfg {Number} [value=0] + * A floating point value between 0 and 1 (e.g., .5) + */ + value: 0, + /** + * @cfg {String/Ext.XTemplate} [textTpl] + * A template used to create this ProgressBar's background text given two values: + * + * `value ' - The raw progress value between 0 and 1 + * 'percent' - The value as a percentage between 0 and 100 + */ + textTpl: null + }, + applyTextTpl: function(textTpl) { + if (!textTpl.isTemplate) { + textTpl = new Ext.XTemplate(textTpl); + } + return textTpl; + }, + applyValue: function(value) { + return value || 0; + } +}); + +/** + * A simple progress bar widget. + * + * You are responsible for showing, updating (via {@link #setValue}) and clearing the + * progress bar as needed from your own code. This method is most appropriate when you + * want to show progress throughout an operation that has predictable points of interest + * at which you can update the control. + */ +Ext.define('Ext.Progress', { + extend: 'Ext.Gadget', + xtype: [ + 'progress', + 'progressbarwidget' + ], + alternateClassName: 'Ext.ProgressBarWidget', + mixins: [ + 'Ext.ProgressBase' + ], + config: { + /** + * @cfg {String} [text] + * The background text + */ + text: null, + /** + * @cfg {Boolean} [animate=false] + * Specify as `true` to have this progress bar animate to new extent when updated. + */ + animate: false + }, + cachedConfig: { + textCls: Ext.baseCSSPrefix + 'progress-text', + cls: null + }, + baseCls: Ext.baseCSSPrefix + 'progress', + template: [ + { + reference: 'backgroundEl' + }, + { + reference: 'barEl', + cls: Ext.baseCSSPrefix + 'progress-bar', + children: [ + { + reference: 'textEl' + } + ] + } + ], + defaultBindProperty: 'value', + updateCls: function(cls, oldCls) { + var el = this.element; + if (oldCls) { + el.removeCls(oldCls); + } + if (cls) { + el.addCls(cls); + } + }, + updateUi: function(ui, oldUi) { + var element = this.element, + barEl = this.barEl, + baseCls = this.baseCls + '-'; + this.callParent([ + ui, + oldUi + ]); + if (oldUi) { + element.removeCls(baseCls + oldUi); + barEl.removeCls(baseCls + 'bar-' + oldUi); + } + element.addCls(baseCls + ui); + barEl.addCls(baseCls + 'bar-' + ui); + }, + updateTextCls: function(textCls) { + this.backgroundEl.addCls(textCls + ' ' + textCls + '-back'); + this.textEl.addCls(textCls); + }, + updateValue: function(value, oldValue) { + var me = this, + textTpl = me.getTextTpl(); + if (textTpl) { + me.setText(textTpl.apply({ + value: value, + percent: Math.round(value * 100) + })); + } + if (!me.isConfiguring && me.getAnimate()) { + me.stopBarAnimation(); + me.startBarAnimation(Ext.apply({ + from: { + width: (oldValue * 100) + '%' + }, + to: { + width: (value * 100) + '%' + } + }, me.animate)); + } else { + me.barEl.setStyle('width', (value * 100) + '%'); + } + }, + updateText: function(text) { + this.backgroundEl.setHtml(text); + this.textEl.setHtml(text); + }, + doDestroy: function() { + this.stopBarAnimation(); + this.callParent(); + }, + privates: { + startBarAnimation: Ext.privateFn, + stopBarAnimation: Ext.privateFn + } +}); + +/** + * @class Ext.Progress + * + * @example + * Ext.create({ + * xtype: 'grid', + * title: 'Simpsons', + * store: { + * data: [ + * { name: 'Lisa', progress: .159 }, + * { name: 'Bart', progress: .216 }, + * { name: 'Homer', progress: .55 }, + * { name: 'Maggie', progress: .167 }, + * { name: 'Marge', progress: .145 } + * ] + * }, + * columns: [ + * { text: 'Name', dataIndex: 'name' }, + * { + * text: 'Progress', + * xtype: 'widgetcolumn', + * width: 120, + * dataIndex: 'progress', + * widget: { + * xtype: 'progress' + * } + * } + * ], + * height: 200, + * width: 400, + * renderTo: Ext.getBody() + * }); + */ +Ext.define('Ext.overrides.Progress', { + override: 'Ext.Progress', + config: { + ui: 'default' + }, + updateWidth: function(width, oldWidth) { + var me = this; + me.callParent([ + width, + oldWidth + ]); + width -= me.element.getBorderWidth('lr'); + me.backgroundEl.setWidth(width); + me.textEl.setWidth(width); + }, + privates: { + startBarAnimation: function(o) { + this.barEl.animate(o); + }, + stopBarAnimation: function() { + this.barEl.stopAnimation(); + } + } +}); + +/** + * @class Ext.util.Format + * + * This class is a centralized place for formatting functions. It includes + * functions to format various different types of data, such as text, dates and numeric values. + * + * ## Localization + * + * This class contains several options for localization. These can be set once the library has loaded, + * all calls to the functions from that point will use the locale settings that were specified. + * + * Options include: + * + * - thousandSeparator + * - decimalSeparator + * - currenyPrecision + * - currencySign + * - currencyAtEnd + * + * This class also uses the default date format defined here: {@link Ext.Date#defaultFormat}. + * + * ## Using with renderers + * + * There are two helper functions that return a new function that can be used in conjunction with + * grid renderers: + * + * columns: [{ + * dataIndex: 'date', + * renderer: Ext.util.Format.dateRenderer('Y-m-d') + * }, { + * dataIndex: 'time', + * renderer: Ext.util.Format.numberRenderer('0.000') + * }] + * + * Functions that only take a single argument can also be passed directly: + * + * columns: [{ + * dataIndex: 'cost', + * renderer: Ext.util.Format.usMoney + * }, { + * dataIndex: 'productCode', + * renderer: Ext.util.Format.uppercase + * }] + * + * ## Using with XTemplates + * + * XTemplates can also directly use Ext.util.Format functions: + * + * new Ext.XTemplate([ + * 'Date: {startDate:date("Y-m-d")}', + * 'Cost: {cost:usMoney}' + * ]); + * + * @singleton + */ +Ext.define('Ext.util.Format', function() { + var me; + // holds our singleton instance + return { + requires: [ + 'Ext.Error', + 'Ext.Number', + 'Ext.String', + 'Ext.Date' + ], + singleton: true, + /** + * The global default date format. + */ + defaultDateFormat: 'm/d/Y', + /** + * @property {String} thousandSeparator + * The character that the {@link #number} function uses as a thousand separator. + * + * This may be overridden in a locale file. + * @locale + */ + thousandSeparator: ',', + /** + * @property {String} decimalSeparator + * The character that the {@link #number} function uses as a decimal point. + * + * This may be overridden in a locale file. + * @locale + */ + decimalSeparator: '.', + /** + * @property {Number} currencyPrecision + * The number of decimal places that the {@link #currency} function displays. + * + * This may be overridden in a locale file. + * @locale + */ + currencyPrecision: 2, + /** + * @property {String} currencySign + * The currency sign that the {@link #currency} function displays. + * + * This may be overridden in a locale file. + * @locale + */ + currencySign: '$', + /** + * @property {String} currencySpacer + * True to add a space between the currency and the value + * + * This may be overridden in a locale file. + * @since 6.2.0 + * @locale + */ + currencySpacer: '', + /** + * @property {String} percentSign + * The percent sign that the {@link #percent} function displays. + * + * This may be overridden in a locale file. + * @locale + */ + percentSign: '%', + /** + * @property {Boolean} currencyAtEnd + * This may be set to true to make the {@link #currency} function + * append the currency sign to the formatted value. + * + * This may be overridden in a locale file. + * @locale + */ + currencyAtEnd: false, + stripTagsRe: /<\/?[^>]+>/gi, + stripScriptsRe: /(?:)((\n|\r|.)*?)(?:<\/script>)/ig, + nl2brRe: /\r?\n/g, + hashRe: /#+$/, + allHashes: /^#+$/, + // Match a format string characters to be able to detect remaining "literal" characters + formatPattern: /[\d,\.#]+/, + // A RegExp to remove from a number format string, all characters except digits and '.' + formatCleanRe: /[^\d\.#]/g, + // A RegExp to remove from a number format string, all characters except digits and the local decimal separator. + // Created on first use. The local decimal separator character must be initialized for this to be created. + I18NFormatCleanRe: null, + // Cache ofg number formatting functions keyed by format string + formatFns: {}, + constructor: function() { + me = this; + }, + // we are a singleton, so cache our this pointer in scope + /** + * Returns a non-breaking space ("NBSP") for any "blank" value. + * @param {Mixed} value + * @param {Boolean} [strict=true] Pass `false` to convert all falsey values to an + * NBSP. By default, only '', `null` and `undefined` will be converted. + * @return {Mixed} + * @since 6.2.0 + */ + nbsp: function(value, strict) { + strict = strict !== false; + if (strict ? value === '' || value == null : !value) { + value = '\xa0'; + } + return value; + }, + /** + * Checks a reference and converts it to empty string if it is undefined. + * @param {Object} value Reference to check + * @return {Object} Empty string if converted, otherwise the original value + */ + undef: function(value) { + return value !== undefined ? value : ""; + }, + /** + * Checks a reference and converts it to the default value if it's empty. + * @param {Object} value Reference to check + * @param {String} [defaultValue=""] The value to insert of it's undefined. + * @return {String} + */ + defaultValue: function(value, defaultValue) { + return value !== undefined && value !== '' ? value : defaultValue; + }, + /** + * Returns a substring from within an original string. + * @param {String} value The original text + * @param {Number} start The start index of the substring + * @param {Number} length The length of the substring + * @return {String} The substring + * @method + */ + substr: 'ab'.substr(-1) != 'b' ? function(value, start, length) { + var str = String(value); + return (start < 0) ? str.substr(Math.max(str.length + start, 0), length) : str.substr(start, length); + } : function(value, start, length) { + return String(value).substr(start, length); + }, + /** + * Converts a string to all lower case letters. + * @param {String} value The text to convert + * @return {String} The converted text + */ + lowercase: function(value) { + return String(value).toLowerCase(); + }, + /** + * Converts a string to all upper case letters. + * @param {String} value The text to convert + * @return {String} The converted text + */ + uppercase: function(value) { + return String(value).toUpperCase(); + }, + /** + * Format a number as US currency. + * @param {Number/String} value The numeric value to format + * @return {String} The formatted currency string + */ + usMoney: function(value) { + return me.currency(value, '$', 2); + }, + /** + * Format a number as a currency. + * @param {Number/String} value The numeric value to format + * @param {String} [currencySign] The currency sign to use (defaults to {@link #currencySign}) + * @param {Number} [decimals] The number of decimals to use for the currency + * (defaults to {@link #currencyPrecision}) + * @param {Boolean} [end] True if the currency sign should be at the end of the string + * (defaults to {@link #currencyAtEnd}) + * @param {String} [currencySpacer] True to add a space between the currency and value + * @return {String} The formatted currency string + */ + currency: function(value, currencySign, decimals, end, currencySpacer) { + var negativeSign = '', + format = ",0", + i = 0; + value = value - 0; + if (value < 0) { + value = -value; + negativeSign = '-'; + } + decimals = Ext.isDefined(decimals) ? decimals : me.currencyPrecision; + format += (decimals > 0 ? '.' : ''); + for (; i < decimals; i++) { + format += '0'; + } + value = me.number(value, format); + if (currencySpacer == null) { + currencySpacer = me.currencySpacer; + } + if ((end || me.currencyAtEnd) === true) { + return Ext.String.format("{0}{1}{2}{3}", negativeSign, value, currencySpacer, currencySign || me.currencySign); + } else { + return Ext.String.format("{0}{1}{2}{3}", negativeSign, currencySign || me.currencySign, currencySpacer, value); + } + }, + /** + * Formats the passed date using the specified format pattern. + * Note that this uses the native Javascript Date.parse() method and is therefore subject to its idiosyncrasies. + * Most formats assume the local timezone unless specified. One notable exception is 'YYYY-MM-DD' (note the dashes) + * which is typically interpreted in UTC and can cause date shifting. + * + * @param {String/Date} value The value to format. Strings must conform to the format + * expected by the JavaScript Date object's + * [parse() method](http://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/Date/parse). + * @param {String} [format] Any valid date format string. Defaults to {@link Ext.Date#defaultFormat}. + * @return {String} The formatted date string. + */ + date: function(value, format) { + if (!value) { + return ""; + } + if (!Ext.isDate(value)) { + value = new Date(Date.parse(value)); + } + return Ext.Date.dateFormat(value, format || Ext.Date.defaultFormat); + }, + /** + * Returns a date rendering function that can be reused to apply a date format multiple times efficiently. + * @param {String} format Any valid date format string. Defaults to {@link Ext.Date#defaultFormat}. + * @return {Function} The date formatting function + */ + dateRenderer: function(format) { + return function(v) { + return me.date(v, format); + }; + }, + /** + * Returns the given number as a base 16 string at least `digits` in length. If + * the number is fewer digits, 0's are prepended as necessary. If `digits` is + * negative, the absolute value is the *exact* number of digits to return. In this + * case, if then number has more digits, only the least significant digits are + * returned. + * + * expect(Ext.util.Format.hex(0x12e4, 2)).toBe('12e4'); + * expect(Ext.util.Format.hex(0x12e4, -2)).toBe('e4'); + * expect(Ext.util.Format.hex(0x0e, 2)).toBe('0e'); + * + * @param {Number} value The number to format in hex. + * @param {Number} digits + * @return {string} + */ + hex: function(value, digits) { + var s = parseInt(value || 0, 10).toString(16); + if (digits) { + if (digits < 0) { + digits = -digits; + if (s.length > digits) { + s = s.substring(s.length - digits); + } + } + while (s.length < digits) { + s = '0' + s; + } + } + return s; + }, + /** + * Returns this result: + * + * value || orValue + * + * The usefulness of this formatter method is in templates. For example: + * + * {foo:or("bar")} + * + * @param {Boolean} value The "if" value. + * @param {Mixed} orValue + */ + or: function(value, orValue) { + return value || orValue; + }, + /** + * If `value` is a number, returns the argument from that index. For example + * + * var s = Ext.util.Format.pick(2, 'zero', 'one', 'two'); + * // s === 'two' + * + * Otherwise, `value` is treated in a truthy/falsey manner like so: + * + * var s = Ext.util.Format.pick(null, 'first', 'second'); + * // s === 'first' + * + * s = Ext.util.Format.pick({}, 'first', 'second'); + * // s === 'second' + * + * The usefulness of this formatter method is in templates. For example: + * + * {foo:pick("F","T")} + * + * {bar:pick("first","second","third")} + * + * @param {Boolean} value The "if" value. + * @param {Mixed} firstValue + * @param {Mixed} secondValue + */ + pick: function(value, firstValue, secondValue) { + if (Ext.isNumber(value)) { + var ret = arguments[value + 1]; + if (ret) { + return ret; + } + } + return value ? secondValue : firstValue; + }, + /** + * Compares `value` against `threshold` and returns: + * + * - if `value` < `threshold` then it returns `below` + * - if `value` > `threshold` then it returns `above` + * - if `value` = `threshold` then it returns `equal` or `above` when `equal` is missing + * + * The usefulness of this formatter method is in templates. For example: + * + * {foo:lessThanElse(0, 'negative', 'positive')} + * + * {bar:lessThanElse(200, 'lessThan200', 'greaterThan200', 'equalTo200')} + * + * @param {Number} value Value that will be checked + * @param {Number} threshold Value to compare against + * @param {Mixed} below Value to return when `value` < `threshold` + * @param {Mixed} above Value to return when `value` > `threshold`. If `value` = `threshold` and + * `equal` is missing then `above` is returned. + * @param {Mixed} equal Value to return when `value` = `threshold` + * @return {Mixed} + */ + lessThanElse: function(value, threshold, below, above, equal) { + var v = Ext.Number.from(value, 0), + t = Ext.Number.from(threshold, 0), + missing = !Ext.isDefined(equal); + return v < t ? below : (v > t ? above : (missing ? above : equal)); + }, + /** + * Checks if `value` is a positive or negative number and returns the proper param. + * + * The usefulness of this formatter method is in templates. For example: + * + * {foo:sign("clsNegative","clsPositive")} + * + * @param {Number} value + * @param {Mixed} negative + * @param {Mixed} positive + * @param {Mixed} zero + * @return {Mixed} + */ + sign: function(value, negative, positive, zero) { + if (zero === undefined) { + zero = positive; + } + return me.lessThanElse(value, 0, negative, positive, zero); + }, + /** + * Strips all HTML tags. + * @param {Object} value The text from which to strip tags + * @return {String} The stripped text + */ + stripTags: function(value) { + return !value ? value : String(value).replace(me.stripTagsRe, ""); + }, + /** + * Strips all script tags. + * @param {Object} value The text from which to strip script tags + * @return {String} The stripped text + */ + stripScripts: function(value) { + return !value ? value : String(value).replace(me.stripScriptsRe, ""); + }, + /** + * @method + * Simple format for a file size (xxx bytes, xxx KB, xxx MB). + * @param {Number/String} size The numeric value to format + * @return {String} The formatted file size + */ + fileSize: (function() { + var byteLimit = 1024, + kbLimit = 1048576, + mbLimit = 1073741824; + return function(size) { + var out; + if (size < byteLimit) { + if (size === 1) { + out = '1 byte'; + } else { + out = size + ' bytes'; + } + } else if (size < kbLimit) { + out = (Math.round(((size * 10) / byteLimit)) / 10) + ' KB'; + } else if (size < mbLimit) { + out = (Math.round(((size * 10) / kbLimit)) / 10) + ' MB'; + } else { + out = (Math.round(((size * 10) / mbLimit)) / 10) + ' GB'; + } + return out; + }; + })(), + /** + * It does simple math for use in a template, for example: + * + * var tpl = new Ext.Template('{value} * 10 = {value:math("* 10")}'); + * + * @return {Function} A function that operates on the passed value. + * @method + */ + math: (function() { + var fns = {}; + return function(v, a) { + if (!fns[a]) { + fns[a] = Ext.functionFactory('v', 'return v ' + a + ';'); + } + return fns[a](v); + }; + }()), + /** + * Rounds the passed number to the required decimal precision. + * @param {Number/String} value The numeric value to round. + * @param {Number} [precision] The number of decimal places to which to round the + * first parameter's value. If `undefined` the `value` is passed to `Math.round` + * otherwise the value is returned unmodified. + * @return {Number} The rounded value. + */ + round: function(value, precision) { + var result = Number(value); + if (typeof precision === 'number') { + precision = Math.pow(10, precision); + result = Math.round(value * precision) / precision; + } else if (precision === undefined) { + result = Math.round(result); + } + return result; + }, + /** + * Formats the passed number according to the passed format string. + * + * The number of digits after the decimal separator character specifies the number of + * decimal places in the resulting string. The *local-specific* decimal character is + * used in the result. + * + * The *presence* of a thousand separator character in the format string specifies that + * the *locale-specific* thousand separator (if any) is inserted separating thousand groups. + * + * By default, "," is expected as the thousand separator, and "." is expected as the decimal separator. + * + * Locale-specific characters are always used in the formatted output when inserting + * thousand and decimal separators. These can be set using the {@link #thousandSeparator} and + * {@link #decimalSeparator} options. + * + * The format string must specify separator characters according to US/UK conventions ("," as the + * thousand separator, and "." as the decimal separator) + * + * To allow specification of format strings according to local conventions for separator characters, add + * the string `/i` to the end of the format string. This format depends on the {@link #thousandSeparator} and + * {@link #decimalSeparator} options. For example, if using European style separators, then the format string + * can be specified as `'0.000,00'`. This would be equivalent to using `'0,000.00'` when using US style formatting. + * + * Examples (123456.789): + * + * - `0` - (123457) show only digits, no precision + * - `0.00` - (123456.79) show only digits, 2 precision + * - `0.0000` - (123456.7890) show only digits, 4 precision + * - `0,000` - (123,457) show comma and digits, no precision + * - `0,000.00` - (123,456.79) show comma and digits, 2 precision + * - `0,0.00` - (123,456.79) shortcut method, show comma and digits, 2 precision + * - `0.####` - (123,456.789) Allow maximum 4 decimal places, but do not right pad with zeroes + * - `0.00##` - (123456.789) Show at least 2 decimal places, maximum 4, but do not right pad with zeroes + * + * @param {Number} v The number to format. + * @param {String} formatString The way you would like to format this text. + * @return {String} The formatted number. + */ + number: function(v, formatString) { + if (!formatString) { + return v; + } + if (isNaN(v)) { + return ''; + } + var formatFn = me.formatFns[formatString]; + // Generate formatting function to be cached and reused keyed by the format string. + // This results in a 100% performance increase over analyzing the format string each invocation. + if (!formatFn) { + var originalFormatString = formatString, + comma = me.thousandSeparator, + decimalSeparator = me.decimalSeparator, + precision = 0, + trimPart = '', + hasComma, splitFormat, extraChars, trimTrailingZeroes, code, len; + // The "/i" suffix allows caller to use a locale-specific formatting string. + // Clean the format string by removing all but numerals and the decimal separator. + // Then split the format string into pre and post decimal segments according to *what* the + // decimal separator is. If they are specifying "/i", they are using the local convention in the format string. + if (formatString.substr(formatString.length - 2) === '/i') { + // In a vast majority of cases, the separator will never change over the lifetime of the application. + // So we'll only regenerate this if we really need to + if (!me.I18NFormatCleanRe || me.lastDecimalSeparator !== decimalSeparator) { + me.I18NFormatCleanRe = new RegExp('[^\\d\\' + decimalSeparator + '#]', 'g'); + me.lastDecimalSeparator = decimalSeparator; + } + formatString = formatString.substr(0, formatString.length - 2); + hasComma = formatString.indexOf(comma) !== -1; + splitFormat = formatString.replace(me.I18NFormatCleanRe, '').split(decimalSeparator); + } else { + hasComma = formatString.indexOf(',') !== -1; + splitFormat = formatString.replace(me.formatCleanRe, '').split('.'); + } + extraChars = formatString.replace(me.formatPattern, ''); + if (splitFormat.length > 2) { + Ext.raise({ + sourceClass: "Ext.util.Format", + sourceMethod: "number", + value: v, + formatString: formatString, + msg: "Invalid number format, should have no more than 1 decimal" + }); + } else if (splitFormat.length === 2) { + precision = splitFormat[1].length; + // Formatting ending in .##### means maximum 5 trailing significant digits + trimTrailingZeroes = splitFormat[1].match(me.hashRe); + if (trimTrailingZeroes) { + len = trimTrailingZeroes[0].length; + // Need to escape, since this will be '.' by default + trimPart = 'trailingZeroes=new RegExp(Ext.String.escapeRegex(utilFormat.decimalSeparator) + "*0{0,' + len + '}$")'; + } + } + // The function we create is called immediately and returns a closure which has access to vars and some fixed values; RegExes and the format string. + code = [ + 'var utilFormat=Ext.util.Format,extNumber=Ext.Number,neg,absVal,fnum,parts' + (hasComma ? ',thousandSeparator,thousands=[],j,n,i' : '') + (extraChars ? ',formatString="' + formatString + '",formatPattern=/[\\d,\\.#]+/' : '') + ',trailingZeroes;' + 'return function(v){' + 'if(typeof v!=="number"&&isNaN(v=extNumber.from(v,NaN)))return"";' + 'neg=v<0;', + 'absVal=Math.abs(v);', + 'fnum=Ext.Number.toFixed(absVal, ' + precision + ');', + trimPart, + ';' + ]; + if (hasComma) { + // If we have to insert commas... + // split the string up into whole and decimal parts if there are decimals + if (precision) { + code[code.length] = 'parts=fnum.split(".");'; + code[code.length] = 'fnum=parts[0];'; + } + code[code.length] = 'if(absVal>=1000) {'; + code[code.length] = 'thousandSeparator=utilFormat.thousandSeparator;' + 'thousands.length=0;' + 'j=fnum.length;' + 'n=fnum.length%3||3;' + 'for(i=0;i` + * + * @param {String} v The string value to format. + * @return {String} The string with embedded `
` tags in place of newlines. + */ + nl2br: function(v) { + return Ext.isEmpty(v) ? '' : v.replace(me.nl2brRe, '
'); + }, + /** + * @method capitalize + * @inheritdoc Ext.String#method-capitalize + * Alias for {@link Ext.String#capitalize}. + */ + capitalize: Ext.String.capitalize, + /** + * @method uncapitalize + * @inheritdoc Ext.String#method-uncapitalize + * Alias for {@link Ext.String#uncapitalize}. + */ + uncapitalize: Ext.String.uncapitalize, + /** + * @method ellipsis + * @inheritdoc Ext.String#method-ellipsis + * Alias for {@link Ext.String#ellipsis}. + */ + ellipsis: Ext.String.ellipsis, + /** + * @method escape + * @inheritdoc Ext.String#method-escape + * Alias for {@link Ext.String#escape}. + */ + escape: Ext.String.escape, + /** + * @method escapeRegex + * @inheritdoc Ext.String#method-escapeRegex + * Alias for {@link Ext.String#escapeRegex}. + */ + escapeRegex: Ext.String.escapeRegex, + /** + * @method htmlDecode + * @inheritdoc Ext.String#method-htmlDecode + * Alias for {@link Ext.String#htmlDecode}. + */ + htmlDecode: Ext.String.htmlDecode, + /** + * @method htmlEncode + * @inheritdoc Ext.String#method-htmlEncode + * Alias for {@link Ext.String#htmlEncode}. + */ + htmlEncode: Ext.String.htmlEncode, + /** + * @method leftPad + * @inheritdoc Ext.String#method-leftPad + * Alias for {@link Ext.String#leftPad}. + */ + leftPad: Ext.String.leftPad, + /** + * @method toggle + * @inheritdoc Ext.String#method-toggle + * Alias for {@link Ext.String#toggle}. + */ + toggle: Ext.String.toggle, + /** + * @method trim + * @inheritdoc Ext.String#method-trim + * Alias for {@link Ext.String#trim}. + */ + trim: Ext.String.trim, + /** + * Parses a number or string representing margin sizes into an object. + * Supports CSS-style margin declarations (e.g. 10, "10", "10 10", "10 10 10" and + * "10 10 10 10" are all valid options and would return the same result). + * + * @param {Number/String} box The encoded margins + * @return {Object} An object with margin sizes for top, right, bottom and left + */ + parseBox: function(box) { + box = box || 0; + if (typeof box === 'number') { + return { + top: box, + right: box, + bottom: box, + left: box + }; + } + var parts = box.split(' '), + ln = parts.length; + if (ln === 1) { + parts[1] = parts[2] = parts[3] = parts[0]; + } else if (ln === 2) { + parts[2] = parts[0]; + parts[3] = parts[1]; + } else if (ln === 3) { + parts[3] = parts[1]; + } + return { + top: parseInt(parts[0], 10) || 0, + right: parseInt(parts[1], 10) || 0, + bottom: parseInt(parts[2], 10) || 0, + left: parseInt(parts[3], 10) || 0 + }; + }, + /** + * Resolves the specified resource `url` with an optional `prefix`. This resolution + * is based on {@link Ext#resolveResource}. The prefix is intended to be used for + * a package or resource pool identifier. + * + * @param {String} url The resource url to resolve + * @param {String} [prefix] A prefix/identifier to include in the resolution. + * @return {String} + */ + resource: function(url, prefix) { + prefix = prefix || ''; + return Ext.resolveResource(prefix + url); + }, + /** + * Formats the given value using `encodeURI`. + * @param {String} value The value to encode. + * @returns {string} + * @since 6.2.0 + */ + uri: function(value) { + return encodeURI(value); + }, + /** + * Formats the given value using `encodeURIComponent`. + * @param {String} value The value to encode. + * @returns {string} + * @since 6.2.0 + */ + uriCmp: function(value) { + return encodeURIComponent(value); + }, + wordBreakRe: /[\W\s]+/, + /** + * Returns the word at the given `index`. Spaces and punctuation are considered + * as word separators by default. For example: + * + * console.log(Ext.util.Format.word('Hello, my name is Bob.', 2); + * // == 'name' + * + * @param {String} value The sentence to break into words. + * @param {Number} index The 0-based word index. + * @param {String/RegExp} [sep="[\W\s]+"] The pattern by which to separate words. + * @return {String} The requested word or empty string. + */ + word: function(value, index, sep) { + var re = sep ? (typeof sep === 'string' ? new RegExp(sep) : sep) : me.wordBreakRe, + parts = (value || '').split(re); + return parts[index || 0] || ''; + } + }; +}); + +/** + * Represents an HTML fragment template. Templates may be {@link #compile precompiled} for greater performance. + * + * An instance of this class may be created by passing to the constructor either a single argument, or multiple + * arguments: + * + * # Single argument: String/Array + * + * The single argument may be either a String or an Array: + * + * - String: + * + * var t = new Ext.Template("
Hello {0}.
"); + * t.append('some-element', ['foo']); + * + * - Array: + * + * An Array will be combined with `join('')`. + * + * var t = new Ext.Template([ + * '
', + * '{name:trim} {value:ellipsis(10)}', + * '
', + * ]); + * t.compile(); + * t.append('some-element', {id: 'myid', cls: 'myclass', name: 'foo', value: 'bar'}); + * + * # Multiple arguments: String, Object, Array, ... + * + * Multiple arguments will be combined with `join('')`. + * + * var t = new Ext.Template( + * '
', + * '{name} {value}', + * '
', + * // a configuration object: + * { + * compiled: true, // {@link #compile} immediately + * } + * ); + * + * # Notes + * + * - For a list of available format functions, see {@link Ext.util.Format}. + * - `disableFormats` reduces `{@link #apply}` time when no formatting is required. + */ +Ext.define('Ext.Template', { + // @define Ext.String.format + // @define Ext.util.Format.format + requires: [ + //'Ext.dom.Helper', + 'Ext.util.Format' + ], + inheritableStatics: { + /** + * Creates a template from the passed element's value (_display:none_ textarea, preferred) or innerHTML. + * @param {String/HTMLElement} el A DOM element or its id + * @param {Object} config (optional) Config object + * @return {Ext.Template} The created template + * @static + * @inheritable + */ + from: function(el, config) { + el = Ext.getDom(el); + return new this(el.value || el.innerHTML, config || ''); + } + }, + // Chrome really likes "new Function" to realize the code block (as in it is + // 2x-3x faster to call it than using eval), but Firefox chokes on it badly. + // IE and Opera are also fine with the "new Function" technique. + useEval: Ext.isGecko, + /* End Definitions */ + /** + * Creates new template. + * + * @param {String...} html List of strings to be concatenated into template. + * Alternatively an array of strings can be given, but then no config object may be passed. + * @param {Object} [config] A config object to apply to this instance. + */ + constructor: function(html) { + var me = this, + args = arguments, + buffer = [], + length = args.length, + i, value; + me.initialConfig = {}; + // Allow an array to be passed here so we can + // pass an array of strings and an object + // at the end + if (length === 1 && Ext.isArray(html)) { + args = html; + length = args.length; + } + if (length > 1) { + for (i = 0; i < length; i++) { + value = args[i]; + if (typeof value === 'object') { + Ext.apply(me.initialConfig, value); + Ext.apply(me, value); + } else { + buffer.push(value); + } + } + } else { + buffer.push(html); + } + me.html = buffer.join(''); + }, + /** + * @property {Boolean} isTemplate + * `true` in this class to identify an object as an instantiated Template, or subclass thereof. + */ + isTemplate: true, + /** + * @cfg {Boolean} compiled + * True to immediately compile the template. Defaults to false. + */ + /** + * @cfg {Boolean} disableFormats + * True to disable format functions in the template. If the template doesn't contain + * format functions, setting disableFormats to true will reduce apply time. Defaults to false. + */ + disableFormats: false, + /** + * @property {RegExp} tokenRe + * Regular expression used to extract tokens. + * + * Finds the following expressions within a format string + * + * {AND?} + * / \ + * / \ + * / \ + * / \ + * OR AND? + * / \ / \ + * / \ / \ + * / \ / \ + * (\d+) ([a-z_][\w\-]*) / \ + * index name / \ + * / \ + * / \ + * \:([a-z_\.]*) (?:\((.*?)?\))? + * formatFn args + * + * Numeric index or (name followed by optional formatting function and args) + * @private + */ + tokenRe: /\{(?:(?:(\d+)|([a-z_][\w\-]*))(?::([a-z_\.]+)(?:\(([^\)]*?)?\))?)?)\}/gi, + /** + * Returns an HTML fragment of this template with the specified values applied. + * + * @param {Object/Array} values The template values. Can be an array if your params are numeric: + * + * var tpl = new Ext.Template('Name: {0}, Age: {1}'); + * tpl.apply(['John', 25]); + * + * or an object: + * + * var tpl = new Ext.Template('Name: {name}, Age: {age}'); + * tpl.apply({name: 'John', age: 25}); + * + * @return {String} The HTML fragment + */ + apply: function(values) { + var me = this; + if (me.compiled) { + if (!me.fn) { + me.compile(); + } + return me.fn(values).join(''); + } + return me.evaluate(values); + }, + /** + * @private + * Do not create the substitution closure on every apply call + */ + evaluate: function(values) { + var me = this, + useFormat = !me.disableFormats, + fm = Ext.util.Format, + tpl = me; + function fn(match, index, name, formatFn, args) { + // Calculate the correct name extracted from the {} + // Certain browser pass unmatched parameters as undefined, some as an empty string. + if (name == null || name === '') { + name = index; + } + if (formatFn && useFormat) { + if (args) { + args = [ + values[name] + ].concat(Ext.functionFactory('return [' + args + '];')()); + } else { + args = [ + values[name] + ]; + } + // Caller used '{0:this.bold}'. Create a call to tpl member function + if (formatFn.substr(0, 5) === "this.") { + return tpl[formatFn.substr(5)].apply(tpl, args); + } + // Caller used '{0:number("0.00")}'. Create a call to Ext.util.Format function + else if (fm[formatFn]) { + return fm[formatFn].apply(fm, args); + } else // Caller used '{0:someRandomText}'. We must return it unchanged + { + return match; + } + } else { + return values[name] !== undefined ? values[name] : ""; + } + } + return me.html.replace(me.tokenRe, fn); + }, + /** + * Appends the result of this template to the provided output array. + * @param {Object/Array} values The template values. See {@link #apply}. + * @param {Array} out The array to which output is pushed. + * @return {Array} The given out array. + */ + applyOut: function(values, out) { + var me = this; + if (me.compiled) { + if (!me.fn) { + me.compile(); + } + out.push.apply(out, me.fn(values)); + } else { + out.push(me.apply(values)); + } + return out; + }, + /** + * @method applyTemplate + * @member Ext.Template + * Alias for {@link #apply}. + * @inheritdoc Ext.Template#apply + */ + applyTemplate: function() { + return this.apply.apply(this, arguments); + }, + /** + * Sets the HTML used as the template and optionally compiles it. + * @param {String} html + * @param {Boolean} compile (optional) True to compile the template. + * @return {Ext.Template} this + */ + set: function(html, compile) { + var me = this; + me.html = html; + me.compiled = !!compile; + me.fn = null; + return me; + }, + compileARe: /\\/g, + compileBRe: /(\r\n|\n)/g, + compileCRe: /'/g, + /** + * Compiles the template into an internal function, eliminating the RegEx overhead. + * @return {Ext.Template} this + */ + compile: function() { + var me = this, + code; + code = me.html.replace(me.compileARe, '\\\\').replace(me.compileBRe, '\\n').replace(me.compileCRe, "\\'").replace(me.tokenRe, me.regexReplaceFn.bind(me)); + code = (this.disableFormats !== true ? 'var fm=Ext.util.Format;' : '') + (me.useEval ? '$=' : 'return') + " function(v){return ['" + code + "'];};"; + me.fn = me.useEval ? me.evalCompiled(code) : (new Function('Ext', code))(Ext); + // jshint ignore:line + me.compiled = true; + return me; + }, + /** + * @private + */ + evalCompiled: function($) { + // We have to use eval to realize the code block and capture the inner func we also + // don't want a deep scope chain. We only do this in Firefox and it is also unhappy + // with eval containing a return statement, so instead we assign to "$" and return + // that. Because we use "eval", we are automatically sandboxed properly. + eval($); + // jshint ignore:line + return $; + }, + regexReplaceFn: function(match, index, name, formatFn, args) { + // Calculate the correct expression to use to index into the values object/array + // index may be a numeric string, or a quoted alphanumeric string. + // Certain browser pass unmatched parameters as undefined, some as an empty string. + if (index == null || index === '') { + index = '"' + name + '"'; + } + // If we are being used as a formatter for Ext.String.format, we must skip the string itself in the argument list. + // Doing this enables String.format to omit the Array slice call. + else if (this.stringFormat) { + index = parseInt(index) + 1; + } + if (formatFn && this.disableFormats !== true) { + args = args ? ',' + args : ""; + // Caller used '{0:this.bold}'. Create a call to member function + if (formatFn.substr(0, 5) === "this.") { + formatFn = formatFn + '('; + } + // Caller used '{0:number("0.00")}'. Create a call to Ext.util.Format function + else if (Ext.util.Format[formatFn]) { + formatFn = "fm." + formatFn + '('; + } else // Caller used '{0:someRandomText}'. We must pass it through unchanged + { + return match; + } + return "'," + formatFn + "v[" + index + "]" + args + "),'"; + } else { + return "',v[" + index + "] == undefined ? '' : v[" + index + "],'"; + } + }, + /** + * Applies the supplied values to the template and inserts the new node(s) as the first child of el. + * + * @param {String/HTMLElement/Ext.dom.Element} el The context element + * @param {Object/Array} values The template values. See {@link #applyTemplate} for details. + * @param {Boolean} returnElement (optional) true to return a Ext.Element. + * @return {HTMLElement/Ext.dom.Element} The new node or Element + */ + insertFirst: function(el, values, returnElement) { + return this.doInsert('afterBegin', el, values, returnElement); + }, + /** + * Applies the supplied values to the template and inserts the new node(s) before el. + * + * @param {String/HTMLElement/Ext.dom.Element} el The context element + * @param {Object/Array} values The template values. See {@link #applyTemplate} for details. + * @param {Boolean} returnElement (optional) true to return a Ext.Element. + * @return {HTMLElement/Ext.dom.Element} The new node or Element + */ + insertBefore: function(el, values, returnElement) { + return this.doInsert('beforeBegin', el, values, returnElement); + }, + /** + * Applies the supplied values to the template and inserts the new node(s) after el. + * + * @param {String/HTMLElement/Ext.dom.Element} el The context element + * @param {Object/Array} values The template values. See {@link #applyTemplate} for details. + * @param {Boolean} returnElement (optional) true to return a Ext.Element. + * @return {HTMLElement/Ext.dom.Element} The new node or Element + */ + insertAfter: function(el, values, returnElement) { + return this.doInsert('afterEnd', el, values, returnElement); + }, + /** + * Applies the supplied `values` to the template and appends the new node(s) to the specified `el`. + * + * For example usage see {@link Ext.Template Ext.Template class docs}. + * + * @param {String/HTMLElement/Ext.dom.Element} el The context element + * @param {Object/Array} values The template values. See {@link #applyTemplate} for details. + * @param {Boolean} returnElement (optional) true to return an Ext.Element. + * @return {HTMLElement/Ext.dom.Element} The new node or Element + */ + append: function(el, values, returnElement) { + return this.doInsert('beforeEnd', el, values, returnElement); + }, + doInsert: function(where, el, values, returnElement) { + var newNode = Ext.DomHelper.insertHtml(where, Ext.getDom(el), this.apply(values)); + return returnElement ? Ext.get(newNode) : newNode; + }, + /** + * Applies the supplied values to the template and overwrites the content of el with the new node(s). + * + * @param {String/HTMLElement/Ext.dom.Element} el The context element + * @param {Object/Array} values The template values. See {@link #applyTemplate} for details. + * @param {Boolean} returnElement (optional) true to return a Ext.Element. + * @return {HTMLElement/Ext.dom.Element} The new node or Element + */ + overwrite: function(el, values, returnElement) { + var newNode = Ext.DomHelper.overwrite(Ext.getDom(el), this.apply(values)); + return returnElement ? Ext.get(newNode) : newNode; + } +}, function(Template) { + var formatRe = /\{\d+\}/, + generateFormatFn = function(format) { + // Generate a function which substitutes value tokens + if (formatRe.test(format)) { + format = new Template(format, formatTplConfig); + return function() { + return format.apply(arguments); + }; + } else // No value tokens + { + return function() { + return format; + }; + } + }, + // Flags for the template compile process. + // stringFormat means that token 0 consumes argument 1 etc. + // So that String.format does not have to slice the argument list. + formatTplConfig = { + useFormat: false, + compiled: true, + stringFormat: true + }, + formatFns = {}; + /** + * @method format + * @inheritdoc Ext.String#method-format + * @member Ext.util.Format + * Alias for {@link Ext.String#format}. + */ + /** + * Allows you to define a tokenized string and pass an arbitrary number of arguments to replace the tokens. Each + * token must be unique, and must increment in the format {0}, {1}, etc. Example usage: + * + * var cls = 'my-class', + * text = 'Some text'; + * var s = Ext.String.format('
{1}
', cls, text); + * // s now contains the string: '
Some text
' + * + * @param {String} format The tokenized string to be formatted. + * @param {Mixed...} values The values to replace tokens `{0}`, `{1}`, etc in order. + * @return {String} The formatted string. + * @member Ext.String + */ + Ext.String.format = Ext.util.Format.format = function(format) { + var formatFn = formatFns[format] || (formatFns[format] = generateFormatFn(format)); + return formatFn.apply(this, arguments); + }; + Ext.String.formatEncode = function() { + return Ext.String.htmlEncode(Ext.String.format.apply(this, arguments)); + }; +}); + +/** + * This class parses the XTemplate syntax and calls abstract methods to process the parts. + * @private + */ +Ext.define('Ext.util.XTemplateParser', { + requires: [ + 'Ext.String' + ], + constructor: function(config) { + Ext.apply(this, config); + }, + /** + * @property {Number} level The 'for' or 'foreach' loop context level. This is adjusted + * up by one prior to calling {@link #doFor} or {@link #doForEach} and down by one after + * calling the corresponding {@link #doEnd} that closes the loop. This will be 1 on the + * first {@link #doFor} or {@link #doForEach} call. + */ + /** + * This method is called to process a piece of raw text from the tpl. + * @param {String} text + * @method doText + */ + // doText: function (text) + /** + * This method is called to process expressions (like `{[expr]}`). + * @param {String} expr The body of the expression (inside "{[" and "]}"). + * @method doExpr + */ + // doExpr: function (expr) + /** + * This method is called to process simple tags (like `{tag}`). + * @method doTag + */ + // doTag: function (tag) + /** + * This method is called to process ``. + * @method doElse + */ + // doElse: function () + /** + * This method is called to process `{% text %}`. + * @param {String} text + * @method doEval + */ + // doEval: function (text) + /** + * This method is called to process ``. If there are other attributes, + * these are passed in the actions object. + * @param {String} action + * @param {Object} actions Other actions keyed by the attribute name (such as 'exec'). + * @method doIf + */ + // doIf: function (action, actions) + /** + * This method is called to process ``. If there are other attributes, + * these are passed in the actions object. + * @param {String} action + * @param {Object} actions Other actions keyed by the attribute name (such as 'exec'). + * @method doElseIf + */ + // doElseIf: function (action, actions) + /** + * This method is called to process ``. If there are other attributes, + * these are passed in the actions object. + * @param {String} action + * @param {Object} actions Other actions keyed by the attribute name (such as 'exec'). + * @method doSwitch + */ + // doSwitch: function (action, actions) + /** + * This method is called to process ``. If there are other attributes, + * these are passed in the actions object. + * @param {String} action + * @param {Object} actions Other actions keyed by the attribute name (such as 'exec'). + * @method doCase + */ + // doCase: function (action, actions) + /** + * This method is called to process ``. + * @method doDefault + */ + // doDefault: function () + /** + * This method is called to process ``. It is given the action type that started + * the tpl and the set of additional actions. + * @param {String} type The type of action that is being ended. + * @param {Object} actions The other actions keyed by the attribute name (such as 'exec'). + * @method doEnd + */ + // doEnd: function (type, actions) + /** + * This method is called to process ``. If there are other attributes, + * these are passed in the actions object. + * @param {String} action + * @param {Object} actions Other actions keyed by the attribute name (such as 'exec'). + * @method doFor + */ + // doFor: function (action, actions) + /** + * This method is called to process ``. If there are other + * attributes, these are passed in the actions object. + * @param {String} action + * @param {Object} actions Other actions keyed by the attribute name (such as 'exec'). + * @method doForEach + */ + // doForEach: function (action, actions) + /** + * This method is called to process ``. If there are other attributes, + * these are passed in the actions object. + * @param {String} action + * @param {Object} actions Other actions keyed by the attribute name. + * @method doExec + */ + // doExec: function (action, actions) + /** + * This method is called to process an empty ``. This is unlikely to need to be + * implemented, so a default (do nothing) version is provided. + * @method + */ + doTpl: Ext.emptyFn, + parse: function(str) { + var me = this, + len = str.length, + aliases = { + elseif: 'elif' + }, + topRe = me.topRe, + actionsRe = me.actionsRe, + index, stack, s, m, t, prev, frame, subMatch, begin, end, actions, prop, expectTplNext; + me.level = 0; + me.stack = stack = []; + for (index = 0; index < len; index = end) { + topRe.lastIndex = index; + m = topRe.exec(str); + if (!m) { + me.doText(str.substring(index, len)); + break; + } + begin = m.index; + end = topRe.lastIndex; + if (index < begin) { + // In the case of a switch statement, we expect a tpl for each case. + // However, if we have spaces they will get matched as plaintext, so + // we want to skip over them here. + s = str.substring(index, begin); + if (!(expectTplNext && Ext.String.trim(s) === '')) { + me.doText(s); + } + } + expectTplNext = false; + if (m[1]) { + end = str.indexOf('%}', begin + 2); + me.doEval(str.substring(begin + 2, end)); + end += 2; + } else if (m[2]) { + end = str.indexOf(']}', begin + 2); + me.doExpr(str.substring(begin + 2, end)); + end += 2; + } else if (m[3]) { + // if ('{' token) + me.doTag(m[3]); + } else if (m[4]) { + // content of a tag + actions = null; + while ((subMatch = actionsRe.exec(m[4])) !== null) { + s = subMatch[2] || subMatch[3]; + if (s) { + s = Ext.String.htmlDecode(s); + // decode attr value + t = subMatch[1]; + t = aliases[t] || t; + actions = actions || {}; + prev = actions[t]; + if (typeof prev == 'string') { + actions[t] = [ + prev, + s + ]; + } else if (prev) { + actions[t].push(s); + } else { + actions[t] = s; + } + } + } + if (!actions) { + if (me.elseRe.test(m[4])) { + me.doElse(); + } else if (me.defaultRe.test(m[4])) { + me.doDefault(); + } else { + me.doTpl(); + stack.push({ + type: 'tpl' + }); + } + } else if (actions['if']) { + me.doIf(actions['if'], actions); + stack.push({ + type: 'if' + }); + } else if (actions['switch']) { + me.doSwitch(actions['switch'], actions); + stack.push({ + type: 'switch' + }); + expectTplNext = true; + } else if (actions['case']) { + me.doCase(actions['case'], actions); + } else if (actions['elif']) { + me.doElseIf(actions['elif'], actions); + } else if (actions['for']) { + ++me.level; + // Extract property name to use from indexed item + if (prop = me.propRe.exec(m[4])) { + actions.propName = prop[1] || prop[2]; + } + me.doFor(actions['for'], actions); + stack.push({ + type: 'for', + actions: actions + }); + } else if (actions['foreach']) { + ++me.level; + // Extract property name to use from indexed item + if (prop = me.propRe.exec(m[4])) { + actions.propName = prop[1] || prop[2]; + } + me.doForEach(actions['foreach'], actions); + stack.push({ + type: 'foreach', + actions: actions + }); + } else if (actions.exec) { + me.doExec(actions.exec, actions); + stack.push({ + type: 'exec', + actions: actions + }); + } + } + /* + else { + // todo - error + } + */ + else if (m[0].length === 5) { + // if the length of m[0] is 5, assume that we're dealing with an opening tpl tag with no attributes (e.g. ...) + // in this case no action is needed other than pushing it on to the stack + stack.push({ + type: 'tpl' + }); + } else { + frame = stack.pop(); + me.doEnd(frame.type, frame.actions); + if (frame.type == 'for' || frame.type == 'foreach') { + --me.level; + } + } + } + }, + // Internal regexes + topRe: /(?:(\{\%)|(\{\[)|\{([^{}]+)\})|(?:]*)\>)|(?:<\/tpl>)/g, + actionsRe: /\s*(elif|elseif|if|for|foreach|exec|switch|case|eval|between)\s*\=\s*(?:(?:"([^"]*)")|(?:'([^']*)'))\s*/g, + propRe: /prop=(?:(?:"([^"]*)")|(?:'([^']*)'))/, + defaultRe: /^\s*default\s*$/, + elseRe: /^\s*else\s*$/ +}); + +/** + * This class compiles the XTemplate syntax into a function object. The function is used + * like so: + * + * function (out, values, parent, xindex, xcount) { + * // out is the output array to store results + * // values, parent, xindex and xcount have their historical meaning + * } + * + * @private + */ +Ext.define('Ext.util.XTemplateCompiler', { + extend: 'Ext.util.XTemplateParser', + // Chrome really likes "new Function" to realize the code block (as in it is + // 2x-3x faster to call it than using eval), but Firefox chokes on it badly. + // IE and Opera are also fine with the "new Function" technique. + useEval: Ext.isGecko, + // See http://jsperf.com/nige-array-append for quickest way to append to an array of unknown length + // (Due to arbitrary code execution inside a template, we cannot easily track the length in var) + // On IE8 and earlier, myArray[myArray.length]='foo' is better. On other browsers myArray.push('foo') is better. + useIndex: Ext.isIE8m, + useFormat: true, + propNameRe: /^[\w\d\$]*$/, + compile: function(tpl) { + var me = this, + code = me.generate(tpl); + // When using "new Function", we have to pass our "Ext" variable to it in order to + // support sandboxing. If we did not, the generated function would use the global + // "Ext", not the "Ext" from our sandbox (scope chain). + // + return me.useEval ? me.evalTpl(code) : (new Function('Ext', code))(Ext); + }, + generate: function(tpl) { + var me = this, + // note: Ext here is properly sandboxed + definitions = 'var fm=Ext.util.Format,ts=Object.prototype.toString;', + code; + // Track how many levels we use, so that we only "var" each level's variables once + me.maxLevel = 0; + me.body = [ + 'var c0=values, a0=' + me.createArrayTest(0) + ', p0=parent, n0=xcount, i0=xindex, k0, v;\n' + ]; + if (me.definitions) { + if (typeof me.definitions === 'string') { + me.definitions = [ + me.definitions, + definitions + ]; + } else { + me.definitions.push(definitions); + } + } else { + me.definitions = [ + definitions + ]; + } + me.switches = []; + me.parse(tpl); + me.definitions.push((me.useEval ? '$=' : 'return') + ' function (' + me.fnArgs + ') {', me.body.join(''), '}'); + code = me.definitions.join('\n'); + // Free up the arrays. + me.definitions.length = me.body.length = me.switches.length = 0; + me.definitions = me.body = me.switches = 0; + return code; + }, + //----------------------------------- + // XTemplateParser callouts + doText: function(text) { + var me = this, + out = me.body; + text = text.replace(me.aposRe, "\\'").replace(me.newLineRe, '\\n'); + if (me.useIndex) { + out.push('out[out.length]=\'', text, '\'\n'); + } else { + out.push('out.push(\'', text, '\')\n'); + } + }, + doExpr: function(expr) { + var out = this.body; + out.push('if ((v=' + expr + ') != null) out'); + // Do not coerce individual values in the buffer. + // The final Array#join('') will coerce to strings. + if (this.useIndex) { + out.push('[out.length]=v\n'); + } else { + out.push('.push(v)\n'); + } + }, + doTag: function(tag) { + var expr = this.parseTag(tag); + if (expr) { + this.doExpr(expr); + } else { + // if we cannot match on tagRe handle as plain text + this.doText('{' + tag + '}'); + } + }, + doElse: function() { + this.body.push('} else {\n'); + }, + doEval: function(text) { + this.body.push(text, '\n'); + }, + doIf: function(action, actions) { + var me = this; + // If it's just a propName, use it directly in the if + if (action === '.') { + me.body.push('if (values) {\n'); + } else if (me.propNameRe.test(action)) { + me.body.push('if (', me.parseTag(action), ') {\n'); + } else // Otherwise, it must be an expression, and needs to be returned from an fn which uses with(values) + { + me.body.push('if (', me.addFn(action), me.callFn, ') {\n'); + } + if (actions.exec) { + me.doExec(actions.exec); + } + }, + doElseIf: function(action, actions) { + var me = this; + // If it's just a propName, use it directly in the else if + if (action === '.') { + me.body.push('else if (values) {\n'); + } else if (me.propNameRe.test(action)) { + me.body.push('} else if (', me.parseTag(action), ') {\n'); + } else // Otherwise, it must be an expression, and needs to be returned from an fn which uses with(values) + { + me.body.push('} else if (', me.addFn(action), me.callFn, ') {\n'); + } + if (actions.exec) { + me.doExec(actions.exec); + } + }, + doSwitch: function(action) { + var me = this, + key; + // If it's just a propName, use it directly in the switch + if (action === '.' || action === '#') { + key = action === '.' ? 'values' : 'xindex'; + me.body.push('switch (', key, ') {\n'); + } else if (me.propNameRe.test(action)) { + me.body.push('switch (', me.parseTag(action), ') {\n'); + } else // Otherwise, it must be an expression, and needs to be returned from an fn which uses with(values) + { + me.body.push('switch (', me.addFn(action), me.callFn, ') {\n'); + } + me.switches.push(0); + }, + doCase: function(action) { + var me = this, + cases = Ext.isArray(action) ? action : [ + action + ], + n = me.switches.length - 1, + match, i; + if (me.switches[n]) { + me.body.push('break;\n'); + } else { + me.switches[n]++; + } + for (i = 0 , n = cases.length; i < n; ++i) { + match = me.intRe.exec(cases[i]); + cases[i] = match ? match[1] : ("'" + cases[i].replace(me.aposRe, "\\'") + "'"); + } + me.body.push('case ', cases.join(': case '), ':\n'); + }, + doDefault: function() { + var me = this, + n = me.switches.length - 1; + if (me.switches[n]) { + me.body.push('break;\n'); + } else { + me.switches[n]++; + } + me.body.push('default:\n'); + }, + doEnd: function(type, actions) { + var me = this, + L = me.level - 1; + if (type == 'for' || type == 'foreach') { + /* + To exit a for or foreach loop we must restore the outer loop's context. The + code looks like this (which goes with that produced by doFor or doForEach): + + for (...) { // the part generated by doFor or doForEach + ... // the body of the for loop + + // ... any tpl for exec statement goes here... + } + parent = p1; + values = r2; + xcount = n1; + xindex = i1 + */ + if (actions.exec) { + me.doExec(actions.exec); + } + me.body.push('}\n'); + me.body.push('parent=p', L, ';values=r', L + 1, ';xcount=n' + L + ';xindex=i', L, '+1;xkey=k', L, ';\n'); + } else if (type == 'if' || type == 'switch') { + me.body.push('}\n'); + } + }, + doFor: function(action, actions) { + var me = this, + s, + L = me.level, + up = L - 1, + parentAssignment; + // If it's just a propName, use it directly in the switch + if (action === '.') { + s = 'values'; + } else if (me.propNameRe.test(action)) { + s = me.parseTag(action); + } else // Otherwise, it must be an expression, and needs to be returned from an fn which uses with(values) + { + s = me.addFn(action) + me.callFn; + } + /* + We are trying to produce a block of code that looks like below. We use the nesting + level to uniquely name the control variables. + + // Omit "var " if we have already been through level 2 + var i2 = 0, + n2 = 0, + c2 = values['propName'], + // c2 is the context object for the for loop + a2 = Array.isArray(c2); + r2 = values, + // r2 is the values object + p2, // p2 is the parent context (of the outer for loop) + k2; // object key - not used by for loop but doEnd needs this to be declared + + // If iterating over the current data, the parent is always set to c2 + p2 = parent = c2; + // If iterating over a property in an object, set the parent to the object + p2 = parent = a1 ? c1[i1] : c1 // set parent + if (c2) { + if (a2) { + n2 = c2.length; + } else if (c2.isMixedCollection) { + c2 = c2.items; + n2 = c2.length; + } else if (c2.isStore) { + c2 = c2.data.items; + n2 = c2.length; + } else { + c2 = [ c2 ]; + n2 = 1; + } + } + // i2 is the loop index and n2 is the number (xcount) of this for loop + for (xcount = n2; i2 < n2; ++i2) { + values = c2[i2] // adjust special vars to inner scope + xindex = i2 + 1 // xindex is 1-based + + The body of the loop is whatever comes between the tpl and /tpl statements (which + is handled by doEnd). + */ + // Declare the vars for a particular level only if we have not already declared them. + if (me.maxLevel < L) { + me.maxLevel = L; + me.body.push('var '); + } + if (action == '.') { + parentAssignment = 'c' + L; + } else { + parentAssignment = 'a' + up + '?c' + up + '[i' + up + ']:c' + up; + } + me.body.push('i', L, '=0,n', L, '=0,c', L, '=', s, ',a', L, '=', me.createArrayTest(L), ',r', L, '=values,p', L, ',k', L, ';\n', 'p', L, '=parent=', parentAssignment, '\n', 'if (c', L, '){if(a', L, '){n', L, '=c', L, '.length;}else if (c', L, '.isMixedCollection){c', L, '=c', L, '.items;n', L, '=c', L, '.length;}else if(c', L, '.isStore){c', L, '=c', L, '.data.items;n', L, '=c', L, '.length;}else{c', L, '=[c', L, '];n', L, '=1;}}\n', 'for (xcount=n', L, ';i', L, '1){ out.push("', actions.between, '"); } \n'); + } + }, + doForEach: function(action, actions) { + var me = this, + s, + L = me.level, + up = L - 1, + parentAssignment; + // If it's just a propName, use it directly in the switch + if (action === '.') { + s = 'values'; + } else if (me.propNameRe.test(action)) { + s = me.parseTag(action); + } else // Otherwise, it must be an expression, and needs to be returned from an fn which uses with(values) + { + s = me.addFn(action) + me.callFn; + } + /* + We are trying to produce a block of code that looks like below. We use the nesting + level to uniquely name the control variables. + + // Omit "var " if we have already been through level 2 + var i2 = -1, + n2 = 0, + c2 = values['propName'], // c2 is the context object for the for loop + a2 = Array.isArray(c2); + r2 = values, // r2 is the values object + p2, // p2 is the parent context (of the outer for loop) + k2; // k2 is the object key while looping + + // If iterating over the current data, the parent is always set to c2 + p2 = parent = c2; + // If iterating over a property in an object, set the parent to the object + p2 = parent = a1 ? c1[i1] : c1 // set parent + + for(k2 in c2){ + xindex = ++i + 1; // xindex is 1-based + xkey = k2; + values = c2[k2]; // values is the property value + + + The body of the loop is whatever comes between the tpl and /tpl statements (which + is handled by doEnd). + */ + // Declare the vars for a particular level only if we have not already declared them. + if (me.maxLevel < L) { + me.maxLevel = L; + me.body.push('var '); + } + if (action == '.') { + parentAssignment = 'c' + L; + } else { + parentAssignment = 'a' + up + '?c' + up + '[i' + up + ']:c' + up; + } + me.body.push('i', L, '=-1,n', L, '=0,c', L, '=', s, ',a', L, '=', me.createArrayTest(L), ',r', L, '=values,p', L, ',k', L, ';\n', 'p', L, '=parent=', parentAssignment, '\n', 'for(k', L, ' in c', L, '){\n', 'xindex=++i', L, '+1;\n', 'xkey=k', L, ';\n', 'values=c', L, '[k', L, '];'); + if (actions.propName) { + me.body.push('.', actions.propName); + } + if (actions.between) { + me.body.push('if(xindex>1){ out.push("', actions.between, '"); } \n'); + } + }, + createArrayTest: ('isArray' in Array) ? function(L) { + return 'Array.isArray(c' + L + ')'; + } : function(L) { + return 'ts.call(c' + L + ')==="[object Array]"'; + }, + doExec: function(action, actions) { + var me = this, + name = 'f' + me.definitions.length, + guards = me.guards[me.strict ? 0 : 1]; + me.definitions.push('function ' + name + '(' + me.fnArgs + ') {', guards.doTry, ' var $v = values; with($v) {', ' ' + action, ' }', guards.doCatch, '}'); + me.body.push(name + me.callFn + '\n'); + }, + //----------------------------------- + // Internal + guards: [ + { + doTry: '', + doCatch: '' + }, + { + doTry: 'try { ', + doCatch: ' } catch(e) {\n' + 'Ext.log.warn("XTemplate evaluation exception: " + e.message);\n' + '}' + } + ], + addFn: function(body) { + var me = this, + name = 'f' + me.definitions.length, + guards = me.guards[me.strict ? 0 : 1]; + if (body === '.') { + me.definitions.push('function ' + name + '(' + me.fnArgs + ') {', ' return values', '}'); + } else if (body === '..') { + me.definitions.push('function ' + name + '(' + me.fnArgs + ') {', ' return parent', '}'); + } else { + me.definitions.push('function ' + name + '(' + me.fnArgs + ') {', guards.doTry, ' var $v = values; with($v) {', ' return(' + body + ')', ' }', guards.doCatch, '}'); + } + return name; + }, + parseTag: function(tag) { + var me = this, + m = me.tagRe.exec(tag), + name, format, args, math, v; + if (!m) { + return null; + } + name = m[1]; + format = m[2]; + args = m[3]; + math = m[4]; + // name = "." - Just use the values object. + if (name == '.') { + // filter to not include arrays/objects/nulls + if (!me.validTypes) { + me.definitions.push('var validTypes={string:1,number:1,boolean:1};'); + me.validTypes = true; + } + v = 'validTypes[typeof values] || ts.call(values) === "[object Date]" ? values : ""'; + } + // name = "#" - Use the xindex + else if (name == '#') { + v = 'xindex'; + } + // name = "$" - Use the xkey + else if (name == '$') { + v = 'xkey'; + } else if (name.substr(0, 7) == "parent.") { + v = name; + } + // compound Javascript property name (e.g., "foo.bar") + else if (isNaN(name) && name.indexOf('-') == -1 && name.indexOf('.') != -1) { + v = "values." + name; + } else // number or a '-' in it or a single word (maybe a keyword): use array notation + // (http://jsperf.com/string-property-access/4) + { + v = "values['" + name + "']"; + } + if (math) { + v = '(' + v + math + ')'; + } + if (format && me.useFormat) { + args = args ? ',' + args : ""; + if (format.substr(0, 5) != "this.") { + format = "fm." + format + '('; + } else { + format += '('; + } + } else { + return v; + } + return format + v + args + ')'; + }, + /** + * @private + */ + evalTpl: function($) { + // We have to use eval to realize the code block and capture the inner func we also + // don't want a deep scope chain. We only do this in Firefox and it is also unhappy + // with eval containing a return statement, so instead we assign to "$" and return + // that. Because we use "eval", we are automatically sandboxed properly. + eval($); + return $; + }, + newLineRe: /\r\n|\r|\n/g, + aposRe: /[']/g, + intRe: /^\s*(\d+)\s*$/, + tagRe: /^([\w-\.\#\$]+)(?:\:([\w\.]*)(?:\((.*?)?\))?)?(\s?[\+\-\*\/]\s?[\d\.\+\-\*\/\(\)]+)?$/ +}, function() { + var proto = this.prototype; + proto.fnArgs = 'out,values,parent,xindex,xcount,xkey'; + proto.callFn = '.call(this,' + proto.fnArgs + ')'; +}); + +/** + * A template class that supports advanced functionality like: + * + * - Auto-filling arrays using templates and sub-templates + * - Conditional processing with basic comparison operators + * - Basic math function support + * - Execute arbitrary inline code with special built-in template variables + * - Custom member functions + * - Many special tags and built-in operators that aren't defined as part of the API, but are supported in the templates that can be created + * + * XTemplate provides the templating mechanism built into {@link Ext.view.View}. + * + * The {@link Ext.Template} describes the acceptable parameters to pass to the constructor. The following examples + * demonstrate all of the supported features. + * + * # Sample Data + * + * This is the data object used for reference in each code example: + * + * var data = { + * name: 'Don Griffin', + * title: 'Senior Technomage', + * company: 'Sencha Inc.', + * drinks: ['Coffee', 'Water', 'More Coffee'], + * kids: [ + * { name: 'Aubrey', age: 17 }, + * { name: 'Joshua', age: 13 }, + * { name: 'Cale', age: 10 }, + * { name: 'Nikol', age: 5 }, + * { name: 'Solomon', age: 0 } + * ] + * }; + * + * # Auto filling of arrays + * + * The **tpl** tag and the **for** operator are used to process the provided data object: + * + * - If the value specified in for is an array, it will auto-fill, repeating the template block inside the tpl + * tag for each item in the array. + * - If for="." is specified, the data object provided is examined. + * - If between="..." is specified, the provided value will be inserted between the items. + * This is also supported in the "foreach" looping template. + * - While processing an array, the special variable {#} will provide the current array index + 1 (starts at 1, not 0). + * + * Examples: + * + * ... // loop through array at root node + * ... // loop through array at foo node + * ... // loop through array at foo.bar node + * ... // loop through array at root node and insert ',' between each item + * + * Using the sample data above: + * + * var tpl = new Ext.XTemplate( + * '

Kids: ', + * '', // process the data.kids node + * '

{#}. {name}

', // use current array index to autonumber + * '

' + * ); + * tpl.overwrite(panel.body, data.kids); // pass the kids property of the data object + * + * An example illustrating how the **for** property can be leveraged to access specified members of the provided data + * object to populate the template: + * + * var tpl = new Ext.XTemplate( + * '

Name: {name}

', + * '

Title: {title}

', + * '

Company: {company}

', + * '

Kids: ', + * '', // interrogate the kids property within the data + * '

{name}

', + * '

' + * ); + * tpl.overwrite(panel.body, data); // pass the root node of the data object + * + * Flat arrays that contain values (and not objects) can be auto-rendered using the special **`{.}`** variable inside a + * loop. This variable will represent the value of the array at the current index: + * + * var tpl = new Ext.XTemplate( + * '

{name}\'s favorite beverages:

', + * '', + * '
- {.}
', + * '
' + * ); + * tpl.overwrite(panel.body, data); + * + * When processing a sub-template, for example while looping through a child array, you can access the parent object's + * members via the **parent** object: + * + * var tpl = new Ext.XTemplate( + * '

Name: {name}

', + * '

Kids: ', + * '', + * '', + * '

{name}

', + * '

Dad: {parent.name}

', + * '
', + * '

' + * ); + * tpl.overwrite(panel.body, data); + * + * The **foreach** operator is used to loop over an object's properties. The following + * example demonstrates looping over the main data object's properties: + * + * var tpl = new Ext.XTemplate( + * '
', + * '', + * '
{$}
', // the special **`{$}`** variable contains the property name + * '
{.}
', // within the loop, the **`{.}`** variable is set to the property value + * '
', + * '
' + * ); + * tpl.overwrite(panel.body, data); + * + * # Conditional processing with basic comparison operators + * + * The **tpl** tag and the **if** operator are used to provide conditional checks for deciding whether or not to render + * specific parts of the template. + * + * Using the sample data above: + * + * var tpl = new Ext.XTemplate( + * '

Name: {name}

', + * '

Kids: ', + * '', + * '', + * '

{name}

', + * '
', + * '

' + * ); + * tpl.overwrite(panel.body, data); + * + * More advanced conditionals are also supported: + * + * var tpl = new Ext.XTemplate( + * '

Name: {name}

', + * '

Kids: ', + * '', + * '

{name} is a ', + * '', + * '

teenager

', + * '', + * '

kid

', + * '', + * '

baby

', + * '
', + * '

' + * ); + * + * var tpl = new Ext.XTemplate( + * '

Name: {name}

', + * '

Kids: ', + * '', + * '

{name} is a ', + * '', + * '', + * '

girl

', + * '', + * '

boy

', + * '
', + * '

' + * ); + * + * A `break` is implied between each case and default, however, multiple cases can be listed + * in a single <tpl> tag. + * + * # Using double quotes + * + * Examples: + * + * var tpl = new Ext.XTemplate( + * "Child", + * "Teenager", + * "...", + * '...', + * "", + * "Hello" + * ); + * + * # Basic math support + * + * The following basic math operators may be applied directly on numeric data values: + * + * + - * / + * + * For example: + * + * var tpl = new Ext.XTemplate( + * '

Name: {name}

', + * '

Kids: ', + * '', + * '', // <-- Note that the > is encoded + * '

{#}: {name}

', // <-- Auto-number each item + * '

In 5 Years: {age+5}

', // <-- Basic math + * '

Dad: {parent.name}

', + * '
', + * '

' + * ); + * tpl.overwrite(panel.body, data); + * + * # Execute arbitrary inline code with special built-in template variables + * + * Anything between `{[ ... ]}` is considered code to be executed in the scope of the template. + * The expression is evaluated and the result is included in the generated result. There are + * some special variables available in that code: + * + * - **out**: The output array into which the template is being appended (using `push` to later + * `join`). + * - **values**: The values in the current scope. If you are using scope changing sub-templates, + * you can change what values is. + * - **parent**: The scope (values) of the ancestor template. + * - **xindex**: If you are in a "for" or "foreach" looping template, the index of the loop you are in (1-based). + * - **xcount**: If you are in a "for" looping template, the total length of the array you are looping. + * - **xkey**: If you are in a "foreach" looping template, the key of the current property + * being examined. + * + * This example demonstrates basic row striping using an inline code block and the xindex variable: + * + * var tpl = new Ext.XTemplate( + * '

Name: {name}

', + * '

Company: {[values.company.toUpperCase() + ", " + values.title]}

', + * '

Kids: ', + * '', + * '

', + * '{name}', + * '
', + * '

' + * ); + * + * Any code contained in "verbatim" blocks (using "{% ... %}") will be inserted directly in + * the generated code for the template. These blocks are not included in the output. This + * can be used for simple things like break/continue in a loop, or control structures or + * method calls (when they don't produce output). The `this` references the template instance. + * + * var tpl = new Ext.XTemplate( + * '

Name: {name}

', + * '

Company: {[values.company.toUpperCase() + ", " + values.title]}

', + * '

Kids: ', + * '', + * '{% if (xindex % 2 === 0) continue; %}', + * '{name}', + * '{% if (xindex > 100) break; %}', + * '', + * '

' + * ); + * + * # Template member functions + * + * One or more member functions can be specified in a configuration object passed into the XTemplate constructor for + * more complex processing: + * + * var tpl = new Ext.XTemplate( + * '

Name: {name}

', + * '

Kids: ', + * '', + * '', + * '

Girl: {name} - {age}

', + * '', + * '

Boy: {name} - {age}

', + * '
', + * '', + * '

{name} is a baby!

', + * '
', + * '

', + * { + * // XTemplate configuration: + * disableFormats: true, + * // member functions: + * isGirl: function(name){ + * return name == 'Aubrey' || name == 'Nikol'; + * }, + * isBaby: function(age){ + * return age < 1; + * } + * } + * ); + * tpl.overwrite(panel.body, data); + */ +Ext.define('Ext.XTemplate', { + extend: 'Ext.Template', + requires: [ + 'Ext.util.XTemplateCompiler' + ], + isXTemplate: true, + /** + * @private + */ + emptyObj: {}, + /** + * @cfg {Boolean} compiled + * Only applies to {@link Ext.Template}, XTemplates are compiled automatically on the + * first call to {@link #apply} or {@link #applyOut}. + * @hide + */ + /** + * @cfg {String/Array} definitions + * Optional. A statement, or array of statements which set up `var`s which may then + * be accessed within the scope of the generated function. + * + * var data = { + * name: 'Don Griffin', + * isWizard: true, + * title: 'Senior Technomage', + * company: 'Sencha Inc.' + * }; + * + * var tpl = new Ext.XTemplate('{[values.isWizard ? wizard : notSoWizard]}' + + * ' {name}', { + * definitions: 'var wizard = "Wizard", notSoWizard = "Townsperson";' + * }); + * + * console.log(tpl.apply(data)); + * // LOGS: Wizard Don Griffin + */ + /** + * @property {Function} fn + * The function that applies this template. This is created on first use of the + * template (calls to `apply` or `applyOut`). + * @private + * @readonly + */ + fn: null, + /** + * @cfg {Boolean} [strict=false] + * Expressions in templates that traverse "dot paths" and fail (due to `null` at some + * stage) have always been expanded as empty strings. This is convenient in most cases + * but doing so can also mask errors in the template. Setting this to `true` changes + * this default so that any expression errors will be thrown as exceptions. + */ + strict: false, + apply: function(values, parent, xindex, xcount) { + var buffer = this.applyOut(values, [], parent, xindex, xcount); + // If only one token, return it as its uncoerced data type. + // This will allow things like ObjectTemplate to use + // formatters on non-string values. + return buffer.length === 1 ? buffer[0] : buffer.join(''); + }, + applyOut: function(values, out, parent, xindex, xcount) { + var me = this, + compiler; + if (!me.fn) { + compiler = new Ext.util.XTemplateCompiler({ + useFormat: me.disableFormats !== true, + definitions: me.definitions, + strict: me.strict + }); + me.fn = compiler.compile(me.html); + } + // xindex is 1-based, so 0 is impossible + xindex = xindex || 1; + // likewise, this tpl exists in the parent, so xcount==0 is not possible + xcount = xcount || 1; + if (me.strict) { + me.fn(out, values, parent || me.emptyObj, xindex, xcount); + } else { + try { + me.fn(out, values, parent || me.emptyObj, xindex, xcount); + } catch (e) { + Ext.log.warn('XTemplate evaluation exception: ' + e.message); + } + } + return out; + }, + /** + * Does nothing. XTemplates are compiled automatically, so this function simply returns this. + * @return {Ext.XTemplate} this + */ + compile: function() { + return this; + }, + statics: { + get: function(config, source, defaultTpl) { + var ret = config; + if (config == null) { + if (source && defaultTpl) { + ret = this.getTpl(source, defaultTpl); + } + } else if ((config || config === '') && !config.isTemplate) { + ret = new this(config); + } + return ret; + }, + /** + * Gets an `XTemplate` from an object (an instance of an {@link Ext#define}'d class). + * Many times, templates are configured high in the class hierarchy and are to be + * shared by all classes that derive from that base. To further complicate matters, + * these templates are seldom actual instances but are rather configurations. For + * example: + * + * Ext.define('MyApp.Class', { + * extraCls: 'extra-class', + * + * someTpl: [ + * '
', + * { + * // Member fn - outputs the owing class's extra CSS class + * emitClass: function(out) { + * out.push(this.owner.extraCls); + * } + * }] + * }); + * + * The goal being to share that template definition with all instances and even + * instances of derived classes, until `someTpl` is overridden. This method will + * "upgrade" these configurations to be real `XTemplate` instances *in place* (to + * avoid creating one instance per object). + * + * The resulting XTemplate will have an `owner` reference injected which refers back + * to the owning object whether that is an object which has an *own instance*, or a + * class prototype. Through this link, XTemplate member functions will be able to access + * prototype properties of its owning class. + * + * @param {Object} instance The object from which to get the `XTemplate` (must be + * an instance of an {@link Ext#define}'d class). + * @param {String} name The name of the property by which to get the `XTemplate`. + * @return {Ext.XTemplate} The `XTemplate` instance or null if not found. + * @protected + * @static + */ + getTpl: function(instance, name) { + var tpl = instance[name], + // go for it! 99% of the time we will get it! + owner; + if (tpl) { + // tpl is just a configuration (not an instance) + if (!tpl.isTemplate) { + // create the template instance from the configuration: + tpl = Ext.XTemplate.get(tpl); + } + if (!tpl.owner) { + // and replace the reference with the new instance: + if (instance.hasOwnProperty(name)) { + // the tpl is on the instance + owner = instance; + } else { + // must be somewhere in the prototype chain + for (owner = instance.self.prototype; owner && !owner.hasOwnProperty(name); owner = owner.superclass) {} + } + owner[name] = tpl; + tpl.owner = owner; + } + } + // else !tpl (no such tpl) or the tpl is an instance already... either way, tpl + // is ready to return + return tpl || null; + } + } +}); + +/** + * This class is a base class for an event domain. In the context of MVC, an "event domain" + * is one or more base classes that fire events to which a Controller wants to listen. A + * controller listens to events by describing the selectors for events of interest to it. + * + * Matching selectors to the firer of an event is one key aspect that defines an event + * domain. All event domain instances must provide a `match` method that tests selectors + * against the event firer. + * + * When an event domain instance is created (typically as a `singleton`), its `type` + * property is used to catalog the domain in the + * {@link Ext.app.EventDomain#instances Ext.app.EventDomain.instances} map. + * + * There are five event domains provided by default: + * + * - {@link Ext.app.domain.Component Component domain}. This is the primary event domain that + * has been available since Ext JS MVC was introduced. This domain is defined as any class that + * extends {@link Ext.Component}, where the selectors use + * {@link Ext.ComponentQuery#query Ext.ComponentQuery}. + * - {@link Ext.app.domain.Global Global domain}. This domain provides Controllers with access + * to events fired from {@link Ext.GlobalEvents} Observable instance. These events represent + * the state of the application as a whole, and are always anonymous. Because of this, Global + * domain does not provide selectors at all. + * - {@link Ext.app.domain.Controller Controller domain}. This domain includes all classes + * that extend {@link Ext.app.Controller}. Events fired by Controllers will be available + * within this domain; selectors are either Controller's {@link Ext.app.Controller#id id} or + * '*' wildcard for any Controller. + * - {@link Ext.app.domain.Store Store domain}. This domain is for classes extending + * {@link Ext.data.AbstractStore}. Selectors are either Store's + * {@link Ext.data.AbstractStore#storeId storeId} or '*' wildcard for any Store. + * - {@link Ext.app.domain.Direct Direct domain}. This domain includes all classes that extend + * {@link Ext.direct.Provider}. Selectors are either Provider's {@link Ext.direct.Provider#id id} + * or '*' wildcard for any Provider. This domain is optional and will be loaded only if + * {@link Ext.direct.Manager} singleton is required in your application. + */ +Ext.define('Ext.app.EventDomain', { + requires: [ + 'Ext.util.Event' + ], + statics: { + /** + * An object map containing `Ext.app.EventDomain` instances keyed by the value + * of their `type` property. + */ + instances: {} + }, + /** + * @cfg {String} idProperty Name of the identifier property for this event domain. + */ + isEventDomain: true, + isInstance: false, + constructor: function() { + var me = this; + if (!me.isInstance) { + Ext.app.EventDomain.instances[me.type] = me; + } + me.bus = {}; + me.monitoredClasses = []; + }, + /** + * This method dispatches an event fired by an object monitored by this domain. This + * is not called directly but is called by interceptors injected by the `monitor` method. + * + * @param {Object} target The firer of the event. + * @param {String} ev The event being fired. + * @param {Array} args The arguments for the event. This array **does not** include the event name. + * That has already been sliced off because this class intercepts the {@link Ext.util.Observable#fireEventArgs fireEventArgs} + * method which takes an array as the event's argument list. + * + * @return {Boolean} `false` if any listener returned `false`, otherwise `true`. + * + * @private + */ + dispatch: function(target, ev, args) { + ev = Ext.canonicalEventName(ev); + var me = this, + bus = me.bus, + selectors = bus[ev], + selector, controllers, id, info, events, len, i, event; + if (!selectors) { + return true; + } + // Loop over all the selectors that are bound to this event + for (selector in selectors) { + // Check if the target matches the selector, note that we will only have + // me.controller when we're an instance of a domain.View attached to a view controller. + if (selectors.hasOwnProperty(selector) && me.match(target, selector, me.controller)) { + // Loop over all the controllers that are bound to this selector + controllers = selectors[selector]; + for (id in controllers) { + if (controllers.hasOwnProperty(id)) { + info = controllers[id]; + if (info.controller.isActive()) { + // Loop over all the events that are bound to this selector + // on the current controller + events = info.list; + len = events.length; + for (i = 0; i < len; i++) { + event = events[i]; + // Fire the event! + if (event.fire.apply(event, args) === false) { + return false; + } + } + } + } + } + } + } + return true; + }, + /** + * This method adds listeners on behalf of a controller. This method is passed an + * object that is keyed by selectors. The value of these is also an object but now + * keyed by event name. For example: + * + * domain.listen({ + * 'some[selector]': { + * click: function() { ... } + * }, + * + * 'other selector': { + * change: { + * fn: function() { ... }, + * delay: 10 + * } + * } + * + * }, controller); + * + * @param {Object} selectors Config object containing selectors and listeners. + * @param {Ext.app.BaseController} [controller] (private) + * @private + */ + listen: function(selectors, controller) { + var me = this, + bus = me.bus, + idProperty = me.idProperty, + monitoredClasses = me.monitoredClasses, + monitoredClassesCount = monitoredClasses.length, + controllerId = controller.getId(), + isComponentDomain = (me.type === 'component'), + refMap = isComponentDomain ? controller.getRefMap() : null, + i, tree, info, selector, options, listener, scope, event, listeners, ev, classHasListeners; + for (selector in selectors) { + listeners = selectors[selector]; + if (isComponentDomain) { + // This allows ref names to be used as selectors, e.g. + // refs: { + // nav: '#navigationList + // }, + // control: { + // nav: { + // itemclick: 'onNavClick' + // } + // } + // + // We process this here instead of in the controller so that we don't + // have to do multiple loops over the selectors + selector = refMap[selector] || selector; + } + if (listeners) { + if (idProperty) { + if (!/^[*#]/.test(selector)) { + Ext.raise('Selectors containing id should begin with #'); + } + selector = selector === '*' ? selector : selector.substring(1); + } + for (ev in listeners) { + options = null; + listener = listeners[ev]; + scope = controller; + ev = Ext.canonicalEventName(ev); + event = new Ext.util.Event(controller, ev); + // Normalize the listener + if (Ext.isObject(listener)) { + options = listener; + listener = options.fn; + scope = options.scope || controller; + delete options.fn; + delete options.scope; + } + if ((!options || !options.scope) && typeof listener === 'string') { + // Allow this lookup to be dynamic in debug mode. + // Super useful for testing! + if (!scope[listener]) { + Ext.raise('Cannot resolve "' + listener + '" on controller.'); + } + scope = null; + } else if (typeof listener === 'string') { + listener = scope[listener]; + } + event.addListener(listener, scope, options); + for (i = 0; i < monitoredClassesCount; ++i) { + classHasListeners = monitoredClasses[i].hasListeners; + if (classHasListeners) { + // Ext.mixin.Observable doesn't have hasListeners at class level + classHasListeners._incr_(ev); + } + } + // Create the bus tree if it is not there yet + tree = bus[ev] || (bus[ev] = {}); + tree = tree[selector] || (tree[selector] = {}); + info = tree[controllerId] || (tree[controllerId] = { + controller: controller, + list: [] + }); + // Push our listener in our bus + info.list.push(event); + } + } + } + }, + /** + * This method matches the firer of the event (the `target`) to the given `selector`. + * Default matching is very simple: a match is true when selector equals target's + * {@link #cfg-idProperty idProperty}, or when selector is '*' wildcard to match any + * target. + * + * @param {Object} target The firer of the event. + * @param {String} selector The selector to which to match the `target`. + * + * @return {Boolean} `true` if the `target` matches the `selector`. + * + * @protected + */ + match: function(target, selector) { + var idProperty = this.idProperty; + if (idProperty) { + return selector === '*' || target[idProperty] === selector; + } + return false; + }, + /** + * This method is called by the derived class to monitor `fireEvent` calls. Any call + * to `fireEvent` on the target Observable will be intercepted and dispatched to any + * listening Controllers. Assuming the original `fireEvent` method does not return + * `false`, the event is passed to the `dispatch` method of this object. + * + * This is typically called in the `constructor` of derived classes. + * + * @param {Ext.Class} observable The Observable to monitor for events. + * + * @protected + */ + monitor: function(observable) { + var domain = this, + prototype = observable.isInstance ? observable : observable.prototype, + doFireEvent = prototype.doFireEvent; + domain.monitoredClasses.push(observable); + prototype.doFireEvent = function(ev, args) { + var me = this, + ret; + ret = doFireEvent.apply(me, arguments); + // Observable can be destroyed in the event handler above, + // in which case we can't proceed with dispatching domain event. + if (ret !== false && !me.destroyed && !me.isSuspended(ev)) { + ret = domain.dispatch(me, ev, args); + } + return ret; + }; + }, + /** + * Removes all of a controller's attached listeners. + * + * @param {String} controllerId The id of the controller. + * + * @private + */ + unlisten: function(controllerId) { + var bus = this.bus, + id = controllerId, + monitoredClasses = this.monitoredClasses, + monitoredClassesCount = monitoredClasses.length, + controllers, ev, events, len, item, selector, selectors, i, j, info, classHasListeners; + if (controllerId.isController) { + id = controllerId.getId(); + } + for (ev in bus) { + ev = Ext.canonicalEventName(ev); + if (bus.hasOwnProperty(ev) && (selectors = bus[ev])) { + for (selector in selectors) { + controllers = selectors[selector]; + info = controllers[id]; + if (info) { + events = info.list; + if (events) { + for (i = 0 , len = events.length; i < len; ++i) { + item = events[i]; + item.clearListeners(); + for (j = 0; j < monitoredClassesCount; ++j) { + classHasListeners = monitoredClasses[j].hasListeners; + if (classHasListeners) { + // Ext.mixin.Observable doesn't have hasListeners + // at class level + classHasListeners._decr_(item.name); + } + } + } + delete controllers[id]; + } + } + } + } + } + }, + destroy: function() { + this.monitoredClasses = this.bus = null; + this.callParent(); + } +}); + +/** + * This class implements the component event domain. All classes extending from + * {@link Ext.Component} are included in this domain. The matching criteria uses + * {@link Ext.ComponentQuery}. + * + * @private + */ +Ext.define('Ext.app.domain.Component', { + extend: 'Ext.app.EventDomain', + singleton: true, + requires: [ + 'Ext.Widget' + ], + type: 'component', + constructor: function() { + this.callParent(); + this.monitor(Ext.Widget); + }, + dispatch: function(target, ev, args) { + var controller = target.lookupController(false), + // don't skip target + domain, view; + while (controller) { + domain = controller.compDomain; + if (domain) { + if (domain.dispatch(target, ev, args) === false) { + return false; + } + } + view = controller.getView(); + controller = view ? view.lookupController(true) : null; + } + return this.callParent([ + target, + ev, + args + ]); + }, + match: function(target, selector) { + return target.is(selector); + } +}); + +/* + * The dirty implementation in this class is quite naive. The reasoning for this is that the dirty state + * will only be used in very specific circumstances, specifically, after the render process has begun but + * the component is not yet rendered to the DOM. As such, we want it to perform as quickly as possible + * so it's not as fully featured as you may expect. + */ +/** + * Manages certain element-like data prior to rendering. These values are passed + * on to the render process. This is currently used to manage the "class" and "style" attributes + * of a component's primary el as well as the bodyEl of panels. This allows things like + * addBodyCls in Panel to share logic with addCls in Component. + * @private + */ +Ext.define('Ext.util.ProtoElement', function() { + var splitWords = Ext.String.splitWords, + toMap = Ext.Array.toMap; + return { + isProtoEl: true, + /** + * The property name for the className on the data object passed to {@link #writeTo}. + */ + clsProp: 'cls', + /** + * The property name for the style on the data object passed to {@link #writeTo}. + */ + styleProp: 'style', + /** + * The property name for the removed classes on the data object passed to {@link #writeTo}. + */ + removedProp: 'removed', + /** + * True if the style must be converted to text during {@link #writeTo}. When used to + * populate tpl data, this will be true. When used to populate {@link Ext.dom.Helper} + * specs, this will be false (the default). + */ + styleIsText: false, + constructor: function(config) { + var me = this, + cls, style; + if (config) { + Ext.apply(me, config); + cls = me.cls; + style = me.style; + delete me.cls; + } + me.classList = cls ? splitWords(cls) : []; + me.classMap = cls ? toMap(me.classList) : {}; + if (style) { + if (typeof style === 'string') { + me.style = Ext.Element.parseStyles(style); + } else if (Ext.isFunction(style)) { + me.styleFn = style; + delete me.style; + } else { + me.style = Ext.apply({}, style); + } + } + }, + // don't edit the given object + /** + * Indicates that the current state of the object has been flushed to the DOM, so we need + * to track any subsequent changes + */ + flush: function() { + this.flushClassList = []; + this.removedClasses = {}; + // clear the style, it will be recreated if we add anything new + delete this.style; + delete this.unselectableAttr; + }, + /** + * Adds class to the element. + * @param {String} cls One or more classnames separated with spaces. + * @return {Ext.util.ProtoElement} this + */ + addCls: function(cls) { + if (!cls) { + return this; + } + var me = this, + add = (typeof cls === 'string') ? splitWords(cls) : cls, + length = add.length, + list = me.classList, + map = me.classMap, + flushList = me.flushClassList, + i = 0, + c; + for (; i < length; ++i) { + c = add[i]; + if (!map[c]) { + map[c] = true; + list.push(c); + if (flushList) { + flushList.push(c); + delete me.removedClasses[c]; + } + } + } + return me; + }, + /** + * True if the element has given class. + * @param {String} cls + * @return {Boolean} + */ + hasCls: function(cls) { + return cls in this.classMap; + }, + /** + * Removes class from the element. + * @param {String} cls One or more classnames separated with spaces. + * @return {Ext.util.ProtoElement} this + */ + removeCls: function(cls) { + var me = this, + list = me.classList, + newList = (me.classList = []), + remove = toMap(splitWords(cls)), + length = list.length, + map = me.classMap, + removedClasses = me.removedClasses, + i, c; + for (i = 0; i < length; ++i) { + c = list[i]; + if (remove[c]) { + if (removedClasses) { + if (map[c]) { + removedClasses[c] = true; + Ext.Array.remove(me.flushClassList, c); + } + } + delete map[c]; + } else { + newList.push(c); + } + } + return me; + }, + /** + * @method setStyle + * @inheritdoc Ext.dom.Element#method-setStyle + * @return {Ext.util.ProtoElement} this + */ + setStyle: function(prop, value) { + var me = this, + style = me.style || (me.style = {}); + if (typeof prop === 'string') { + if (arguments.length === 1) { + me.setStyle(Ext.Element.parseStyles(prop)); + } else { + style[prop] = value; + } + } else { + Ext.apply(style, prop); + } + return me; + }, + unselectable: function() { + // See Ext.dom.Element.unselectable for an explanation of what is required to make an element unselectable + this.addCls(Ext.dom.Element.unselectableCls); + if (Ext.isOpera) { + this.unselectableAttr = true; + } + }, + /** + * Writes style and class properties to given object. + * Styles will be written to {@link #styleProp} and class names to {@link #clsProp}. + * @param {Object} to + * @return {Object} to + */ + writeTo: function(to) { + var me = this, + classList = me.flushClassList || me.classList, + removedClasses = me.removedClasses, + style; + if (me.styleFn) { + style = Ext.apply({}, me.styleFn()); + Ext.apply(style, me.style); + } else { + style = me.style; + } + to[me.clsProp] = classList.join(' '); + if (style) { + to[me.styleProp] = me.styleIsText ? Ext.DomHelper.generateStyles(style, null, true) : style; + } + if (removedClasses) { + removedClasses = Ext.Object.getKeys(removedClasses); + if (removedClasses.length) { + to[me.removedProp] = removedClasses.join(' '); + } + } + if (me.unselectableAttr) { + to.unselectable = 'on'; + } + return to; + } + }; +}); + +/** + * This class encapsulates a _collection_ of DOM elements, providing methods to filter members, or to perform collective + * actions upon the whole set. + * + * Although they are not listed, this class supports all of the methods of {@link Ext.dom.Element}. The methods from + * these classes will be performed on all the elements in this collection. + * + * All methods return _this_ and can be chained. + * + * Usage: + * + * var els = Ext.select("#some-el div.some-class", true); + * // or select directly from an existing element + * var el = Ext.get('some-el'); + * el.select('div.some-class', true); + * + * els.setWidth(100); // all elements become 100 width + * els.hide(true); // all elements fade out and hide + * // or + * els.setWidth(100).hide(true); + */ +Ext.define('Ext.dom.CompositeElement', { + alternateClassName: 'Ext.CompositeElement', + extend: 'Ext.dom.CompositeElementLite', + isLite: false, + /** + * @private + */ + getElement: function(el) { + // In this case just return it, since we already have a reference to it + return el; + }, + /** + * @private + */ + transformElement: function(el) { + return Ext.get(el); + } +}); + +/** + * Creates plugin instances. + * + * A plugin may be specified simply as a *config object* as long as the correct `ptype` is specified: + * + * { + * ptype: 'gridviewdragdrop', + * dragText: 'Drag and drop to reorganize' + * } + * + * Or just use the ptype on its own: + * + * 'gridviewdragdrop' + * + * Alternatively you can instantiate the plugin with Ext.create: + * + * Ext.create('Ext.grid.plugin.DragDrop', { + * dragText: 'Drag and drop to reorganize' + * }) + * @private + */ +Ext.define('Ext.plugin.Manager', { + alternateClassName: [ + 'Ext.PluginManager', + 'Ext.PluginMgr' + ], + singleton: true, + typeName: 'ptype', + /** + * Creates a new Plugin from the specified config object using the config object's ptype to determine the class to + * instantiate. + * @param {Object} config A configuration object for the Plugin you wish to create. + * @param {Function} defaultType (optional) The constructor to provide the default Plugin type if the config object does not + * contain a `ptype`. (Optional if the config contains a `ptype`). + * @param {String} host + * @return {Ext.Component} The newly instantiated Plugin. + */ + create: function(config, defaultType, host) { + var result, type; + if (config.init) { + result = config; + } else { + // Inject the host into the config is we know the host + if (host) { + config = Ext.apply({}, config); + // copy since we are going to modify + config.cmp = host; + } else // Grab the host ref if it was configured in + { + host = config.cmp; + } + if (config.xclass) { + result = Ext.create(config); + } else { + // Lookup the class from the ptype and instantiate unless its a singleton + type = 'plugin.' + (config.ptype || defaultType); + result = Ext.ClassManager.instantiateByAlias(type, config); + } + } + // If we come out with a non-null plugin, ensure that any setCmp is called once. + if (result && host && result.setCmp && !result.setCmpCalled) { + result.setCmp(host); + result.setCmpCalled = true; + } + return result; + } +}); + +/** + * Utility class for manipulating CSS rules + * @singleton + */ +Ext.define('Ext.util.CSS', function() { + var CSS, + rules = null, + doc = document, + camelRe = /(-[a-z])/gi, + camelFn = function(m, a) { + return a.charAt(1).toUpperCase(); + }; + return { + singleton: true, + rules: rules, + initialized: false, + /** + * @private + */ + constructor: function() { + // Cache a reference to the singleton + CSS = this; + }, + /** + * Creates a stylesheet from a text blob of rules. + * These rules will be wrapped in a STYLE tag and appended to the HEAD of the document. + * @param {String} cssText The text containing the css rules + * @param {String} id An id to add to the stylesheet for later removal + * @return {CSSStyleSheet} + */ + createStyleSheet: function(cssText, id) { + var ss, + head = doc.getElementsByTagName('head')[0], + styleEl = doc.createElement('style'); + styleEl.setAttribute('type', 'text/css'); + if (id) { + styleEl.setAttribute('id', id); + } + // Feature detect old IE + ss = styleEl.styleSheet; + if (ss) { + head.appendChild(styleEl); + ss.cssText = cssText; + } else { + styleEl.appendChild(doc.createTextNode(cssText)); + head.appendChild(styleEl); + ss = styleEl.sheet; + } + CSS.cacheStyleSheet(ss); + return ss; + }, + /** + * Removes a style or link tag by id + * @param {String/CSSStyleSheet} stylesheet The id of the style tag, or the CSSStyleSheet + * reference to remove + */ + removeStyleSheet: function(stylesheet) { + var styleEl = (typeof stylesheet === 'string') ? doc.getElementById(stylesheet) : stylesheet.ownerNode; + if (styleEl) { + styleEl.parentNode.removeChild(styleEl); + } + }, + /** + * Dynamically swaps an existing stylesheet reference for a new one + * @param {String} id The id of an existing link tag to remove + * @param {String} url The href of the new stylesheet to include + */ + swapStyleSheet: function(id, url) { + var ss; + CSS.removeStyleSheet(id); + ss = doc.createElement("link"); + ss.setAttribute("rel", "stylesheet"); + ss.setAttribute("type", "text/css"); + ss.setAttribute("id", id); + ss.setAttribute("href", url); + doc.getElementsByTagName("head")[0].appendChild(ss); + }, + /** + * @private + */ + cacheStyleSheet: function(ss) { + if (!rules) { + rules = CSS.rules = {}; + } + try { + // try catch for cross domain access issue + var ssRules = ss.cssRules || ss.rules, + i = ssRules.length - 1, + imports = ss.imports, + len = imports ? imports.length : 0, + rule, j; + // Old IE has a different way of handling imports + for (j = 0; j < len; ++j) { + CSS.cacheStyleSheet(imports[j]); + } + for (; i >= 0; --i) { + rule = ssRules[i]; + // If it's an @import rule, import its stylesheet + if (rule.styleSheet) { + CSS.cacheStyleSheet(rule.styleSheet); + } + CSS.cacheRule(rule, ss); + } + } catch (e) {} + }, + cacheRule: function(cssRule, styleSheet) { + // If it's an @import rule, import its stylesheet + if (cssRule.styleSheet) { + return CSS.cacheStyleSheet(cssRule.styleSheet); + } + var selectorText = cssRule.selectorText, + selectorCount, j; + if (selectorText) { + // Split in case there are multiple, comma-delimited selectors + selectorText = selectorText.split(','); + selectorCount = selectorText.length; + for (j = 0; j < selectorCount; j++) { + // IE<8 does not keep a reference to parentStyleSheet in the rule, so we + // must cache an object like this until IE<8 is deprecated. + rules[Ext.String.trim(selectorText[j]).toLowerCase()] = { + parentStyleSheet: styleSheet, + cssRule: cssRule + }; + } + } + }, + /** + * Gets all css rules for the document + * @param {Boolean} refreshCache true to refresh the internal cache + * @return {Object} An object (hash) of rules indexed by selector + */ + getRules: function(refreshCache) { + var result = {}, + selector; + if (rules === null || refreshCache) { + CSS.refreshCache(); + } + for (selector in rules) { + result[selector] = rules[selector].cssRule; + } + return result; + }, + /** + * Refresh the rule cache if you have dynamically added stylesheets + * @return {Object} An object (hash) of rules indexed by selector + */ + refreshCache: function() { + var ds = doc.styleSheets, + i = 0, + len = ds.length; + rules = CSS.rules = {}; + for (; i < len; i++) { + try { + if (!ds[i].disabled) { + CSS.cacheStyleSheet(ds[i]); + } + } catch (e) {} + } + }, + /** + * Gets an an individual CSS rule by selector(s) + * @param {String/String[]} selector The CSS selector or an array of selectors to try. The first selector that is found is returned. + * @param {Boolean} refreshCache true to refresh the internal cache if you have recently updated any rules or added styles dynamically + * @param rawCache The CSS rule or null if one is not found + */ + getRule: function(selector, refreshCache, rawCache) { + var i, result; + if (!rules || refreshCache) { + CSS.refreshCache(); + } + if (!Ext.isArray(selector)) { + result = rules[selector.toLowerCase()]; + if (result && !rawCache) { + result = result.cssRule; + } + return result || null; + } + for (i = 0; i < selector.length; i++) { + if (rules[selector[i]]) { + return rawCache ? rules[selector[i].toLowerCase()] : rules[selector[i].toLowerCase()].cssRule; + } + } + return null; + }, + /** + * Creates a rule. + * @param {CSSStyleSheet} styleSheet The StyleSheet to create the rule in as returned from {@link #createStyleSheet}. + * @param {String} selector The selector to target the rule. + * @param {String} cssText The cssText specification eg `"color:red;font-weight:bold;text-decoration:underline"` + * @return {CSSStyleRule} The created rule + */ + createRule: function(styleSheet, selector, cssText) { + var result, + ruleSet = styleSheet.cssRules || styleSheet.rules, + index = ruleSet.length; + if (styleSheet.insertRule) { + styleSheet.insertRule(selector + ' {' + cssText + '}', index); + } else { + styleSheet.addRule(selector, cssText || ' '); + } + CSS.cacheRule(result = ruleSet[index], styleSheet); + return result; + }, + /** + * Updates a rule property + * @param {String/String[]} selector If it's an array it tries each selector until it finds one. Stops immediately once one is found. + * @param {String} property The css property or a cssText specification eg `"color:red;font-weight:bold;text-decoration:underline"` + * @param {String} value The new value for the property + * @return {Boolean} true If a rule was found and updated + */ + updateRule: function(selector, property, value) { + var rule, i, styles; + if (!Ext.isArray(selector)) { + rule = CSS.getRule(selector); + if (rule) { + // 2 arg form means cssText sent, so parse it and update each style + if (arguments.length === 2) { + styles = Ext.Element.parseStyles(property); + for (property in styles) { + rule.style[property.replace(camelRe, camelFn)] = styles[property]; + } + } else { + rule.style[property.replace(camelRe, camelFn)] = value; + } + return true; + } + } else { + for (i = 0; i < selector.length; i++) { + if (CSS.updateRule(selector[i], property, value)) { + return true; + } + } + } + return false; + }, + deleteRule: function(selector) { + var rule = CSS.getRule(selector, false, true), + styleSheet, index; + if (rule) { + styleSheet = rule.parentStyleSheet; + index = Ext.Array.indexOf(styleSheet.cssRules || styleSheet.rules, rule.cssRule); + if (styleSheet.deleteRule) { + styleSheet.deleteRule(index); + } else { + styleSheet.removeRule(index); + } + delete rules[selector]; + } + } + }; +}); + +/** + * @private + */ +Ext.define('Ext.fx.easing.Abstract', { + config: { + startTime: 0, + startValue: 0 + }, + isEasing: true, + isEnded: false, + constructor: function(config) { + this.initConfig(config); + return this; + }, + applyStartTime: function(startTime) { + if (!startTime) { + startTime = Ext.Date.now(); + } + return startTime; + }, + updateStartTime: function(startTime) { + this.reset(); + }, + reset: function() { + this.isEnded = false; + }, + getValue: Ext.emptyFn +}); + +/** + * @private + */ +Ext.define('Ext.fx.easing.Linear', { + extend: 'Ext.fx.easing.Abstract', + alias: 'easing.linear', + config: { + duration: 0, + endValue: 0 + }, + updateStartValue: function(startValue) { + this.distance = this.getEndValue() - startValue; + }, + updateEndValue: function(endValue) { + this.distance = endValue - this.getStartValue(); + }, + getValue: function() { + var deltaTime = Ext.Date.now() - this.getStartTime(), + duration = this.getDuration(); + if (deltaTime > duration) { + this.isEnded = true; + return this.getEndValue(); + } else { + return this.getStartValue() + ((deltaTime / duration) * this.distance); + } + } +}); + +/** + * @private + * + * The abstract class. Sub-classes are expected, at the very least, to implement translation logics inside + * the 'translate' method + */ +Ext.define('Ext.util.translatable.Abstract', { + extend: 'Ext.Evented', + mixins: [ + 'Ext.mixin.Factoryable' + ], + factoryConfig: { + type: 'translatable', + defaultType: 'csstransform' + }, + requires: [ + 'Ext.fx.easing.Linear' + ], + config: { + easing: null, + easingX: { + duration: 300 + }, + easingY: { + duration: 300 + } + }, + /** + * @event animationstart + * Fires whenever the animation is started + * @param {Ext.util.translatable.Abstract} this + * @param {Number} x The current translation on the x axis + * @param {Number} y The current translation on the y axis + */ + /** + * @event animationframe + * Fires for each animation frame + * @param {Ext.util.translatable.Abstract} this + * @param {Number} x The new translation on the x axis + * @param {Number} y The new translation on the y axis + */ + /** + * @event animationend + * Fires whenever the animation is ended + * @param {Ext.util.translatable.Abstract} this + * @param {Number} x The current translation on the x axis + * @param {Number} y The current translation on the y axis + */ + /** + * @property {Number} x + * @private + * The last translated x value + */ + x: 0, + /** + * @property {Number} y + * @private + * The last translated y value + */ + y: 0, + activeEasingX: null, + activeEasingY: null, + isAnimating: false, + isTranslatable: true, + constructor: function(config) { + this.callParent([ + config + ]); + // this.position is simply an internal reusable object for GC purposes and should + // not be accessed directly as it's values are not kept in sync. always use + // getPosition() to get the position + this.position = { + x: 0, + y: 0 + }; + }, + factoryEasing: function(easing) { + return Ext.factory(easing, Ext.fx.easing.Linear, null, 'easing'); + }, + applyEasing: function(easing) { + if (!this.getEasingX()) { + this.setEasingX(this.factoryEasing(easing)); + } + if (!this.getEasingY()) { + this.setEasingY(this.factoryEasing(easing)); + } + }, + applyEasingX: function(easing) { + return this.factoryEasing(easing); + }, + applyEasingY: function(easing) { + return this.factoryEasing(easing); + }, + doTranslate: function(x, y) { + if (this.hasListeners.translate) { + this.fireEvent('translate', this, x, y); + } + }, + translate: function(x, y, animation) { + if (animation) { + return this.translateAnimated(x, y, animation); + } + if (this.isAnimating) { + this.stopAnimation(); + } + if (!isNaN(x) && typeof x === 'number') { + this.x = x; + } + if (!isNaN(y) && typeof y === 'number') { + this.y = y; + } + this.doTranslate(x, y); + }, + translateAxis: function(axis, value, animation) { + var x, y; + if (axis === 'x') { + x = value; + } else { + y = value; + } + return this.translate(x, y, animation); + }, + /** + * Returns the translatable object's current position. + * @return {Object} position An object with x and y properties + */ + getPosition: function() { + var me = this, + position = me.position; + position.x = -me.x; + position.y = -me.y; + return position; + }, + animate: function(easingX, easingY) { + var me = this; + me.activeEasingX = easingX; + me.activeEasingY = easingY; + me.isAnimating = true; + if (me.ownerCmp) { + me.ownerCmp.isTranslating = true; + } + me.lastX = null; + me.lastY = null; + Ext.AnimationQueue.start(me.doAnimationFrame, me); + me.fireEvent('animationstart', me, me.x, me.y); + return me; + }, + translateAnimated: function(x, y, animation) { + var me = this, + now, easing, easingX, easingY; + if (!Ext.isObject(animation)) { + animation = {}; + } + if (me.isAnimating) { + me.stopAnimation(); + } + // Callback must be called in stopAnimation + me.callback = animation.callback; + me.callbackScope = animation.scope; + now = Ext.Date.now(); + easing = animation.easing; + easingX = (typeof x === 'number') ? (animation.easingX || easing || me.getEasingX() || true) : null; + easingY = (typeof y === 'number') ? (animation.easingY || easing || me.getEasingY() || true) : null; + if (easingX) { + easingX = me.factoryEasing(easingX); + easingX.setStartTime(now); + easingX.setStartValue(me.x); + easingX.setEndValue(x); + if ('duration' in animation) { + easingX.setDuration(animation.duration); + } + } + if (easingY) { + easingY = me.factoryEasing(easingY); + easingY.setStartTime(now); + easingY.setStartValue(me.y); + easingY.setEndValue(y); + if ('duration' in animation) { + easingY.setDuration(animation.duration); + } + } + return me.animate(easingX, easingY); + }, + doAnimationFrame: function() { + var me = this, + easingX = me.activeEasingX, + easingY = me.activeEasingY, + now = Date.now(), + x, y; + if (!me.isAnimating) { + return; + } + me.lastRun = now; + if (easingX === null && easingY === null) { + me.stopAnimation(); + return; + } + if (easingX !== null) { + me.x = x = Math.round(easingX.getValue()); + if (easingX.isEnded) { + me.activeEasingX = null; + me.fireEvent('axisanimationend', me, 'x', x); + } + } else { + x = me.x; + } + if (easingY !== null) { + me.y = y = Math.round(easingY.getValue()); + if (easingY.isEnded) { + me.activeEasingY = null; + me.fireEvent('axisanimationend', me, 'y', y); + } + } else { + y = me.y; + } + if (me.lastX !== x || me.lastY !== y) { + me.doTranslate(x, y); + me.lastX = x; + me.lastY = y; + } + me.fireEvent('animationframe', me, x, y); + }, + stopAnimation: function() { + var me = this; + if (!me.isAnimating) { + return; + } + me.activeEasingX = null; + me.activeEasingY = null; + me.isAnimating = false; + if (me.ownerCmp) { + me.ownerCmp.isTranslating = false; + } + Ext.AnimationQueue.stop(me.doAnimationFrame, me); + me.fireEvent('animationend', me, me.x, me.y); + if (me.callback) { + me.callback.call(me.callbackScope); + me.callback = null; + } + }, + refresh: function() { + this.translate(this.x, this.y); + }, + resolveListenerScope: function() { + var ownerCmp = this.ownerCmp, + a = arguments; + if (ownerCmp) { + return ownerCmp.resolveListenerScope.apply(ownerCmp, a); + } + return this.callParent(a); + }, + destroy: function() { + var me = this; + me.destroying = true; + if (me.isAnimating) { + me.stopAnimation(); + } + me.callParent(); + me.destroying = false; + me.destroyed = true; + } +}); + +/** + * @private + */ +Ext.define('Ext.util.translatable.Dom', { + extend: 'Ext.util.translatable.Abstract', + alias: 'translatable.dom', + // also configures Factoryable + config: { + element: null + }, + applyElement: function(element) { + if (!element) { + return; + } + return Ext.get(element); + }, + updateElement: function() { + this.refresh(); + } +}); + +/** + * @private + * + * Scroll position implementation + */ +Ext.define('Ext.util.translatable.ScrollPosition', { + extend: 'Ext.util.translatable.Dom', + alias: 'translatable.scrollposition', + // also configures Factoryable + constructor: function(config) { + if (config && config.element) { + this.x = config.element.getScrollLeft(); + this.y = config.element.getScrollTop(); + } + this.callParent([ + config + ]); + }, + translateAnimated: function() { + var element = this.getElement(); + this.x = element.getScrollLeft(); + this.y = element.getScrollTop(); + this.callParent(arguments); + }, + doTranslate: function(x, y) { + var element = this.getElement(); + element.setScrollLeft(Math.round(x)); + element.setScrollTop(Math.round(y)); + }, + getPosition: function() { + var me = this, + position = me.position, + element = me.getElement(); + position.x = element.getScrollLeft(); + position.y = element.getScrollTop(); + return position; + } +}); + +/** + * Ext.scroll.Scroller allows any element to have scrollable content, both on desktop and + * touch-screen devices, and defines a set of useful methods for manipulating the scroll + * position and controlling the scrolling behavior. + */ +Ext.define('Ext.scroll.Scroller', { + extend: 'Ext.Evented', + alias: 'scroller.scroller', + mixins: [ + 'Ext.mixin.Factoryable', + 'Ext.mixin.Bufferable' + ], + requires: [ + 'Ext.util.CSS', + 'Ext.util.translatable.ScrollPosition', + 'Ext.Deferred' + ], + factoryConfig: { + defaultType: 'scroller' + }, + bufferableMethods: { + onDomScrollEnd: 100 + }, + isScroller: true, + /** + * @event refresh + * Fires whenever the Scroller is refreshed. + * @param {Ext.scroll.Scroller} this + */ + /** + * @event scrollstart + * Fires whenever the scrolling is started. + * @param {Ext.scroll.Scroller} this + * @param {Number} x The current x position. + * @param {Number} y The current y position. + */ + /** + * @event scrollend + * Fires whenever the scrolling is ended. + * @param {Ext.scroll.Scroller} this + * @param {Number} x The current x position. + * @param {Number} y The current y position. + * @param {Number} deltaX The change in x value. + * @param {Number} deltaY The change in y value. + */ + /** + * @event scroll + * Fires whenever the Scroller is scrolled. + * @param {Ext.scroll.Scroller} this + * @param {Number} x The new x position. + * @param {Number} y The new y position. + * @param {Number} deltaX The change in x value. + * @param {Number} deltaY The change in y value. + */ + config: { + /** + * @cfg {'auto'/'vertical'/'horizontal'/'both'} [direction='auto'] + * @deprecated 5.1.0 use {@link #x} and {@link #y} instead + */ + direction: undefined, + // undefined because we need the updater to always run + /** + * @cfg {String/HTMLElement/Ext.dom.Element} + * The element to make scrollable. + */ + element: undefined, + /** + * @cfg {Boolean} [scrollbars=true] + * `false` to hide scrollbars on browsers where it is possible via CSS, + * Currently Webkit, Chrome, and IE10+ + * @private + */ + scrollbars: null, + /** + * @cfg {String} A CSS selector that identifies items inside this scroller that + * should be snapped into position when user scrolling ends. By default the items + * top/left will be aligned with the top/left of the container. This alignment + * can be changed using {@link #snapOffset} + * + * This api is highly experimental as it is based on bleeding-edge CSS implementations + * that may change in the near future. Do not rely on it in your applications. + * + * @private + */ + snapSelector: null, + /** + * @cfg {Object} An object with x and y properties for offsetting the currently + * snapped item from the top/left of the container. + * + * This api is highly experimental as it is based on bleeding-edge CSS implementations + * that may change in the near future. Do not rely on it in your applications. + * + * @private + */ + snapOffset: null, + /** + * @cfg {Object} an object with x and y properties that specifies the size of the + * snap points on the x and y axes. For IE10+/Edge only, since those browsers do + * not support the newer CSS properties for snapping to element boundaries. + * + * This config is experimental and may be removed in a future version of the framework. + * + * @private + */ + msSnapInterval: null, + /** + * @cfg {Boolean/String} + * - `true` or `'auto'` to enable horizontal auto-scrolling. In auto-scrolling mode + * scrolling is only enabled when the {@link #element} has overflowing content. + * - `false` to disable horizontal scrolling + * - `'scroll'` to always enable horizontal scrolling regardless of content size. + */ + x: true, + /** + * @cfg {Boolean/String} + * - `true` or `'auto'` to enable vertical auto-scrolling. In auto-scrolling mode + * scrolling is only enabled when the {@link #element} has overflowing content. + * - `false` to disable vertical scrolling + * - `'scroll'` to always enable vertical scrolling regardless of content size. + */ + y: true, + /** + * @cfg {Ext.dom.Element} scrollElement + * The element to read the scrollTop/scrollLeft from. This is used to + * work around cross browser issues where WebKit/Blink require reading/writing + * scrollTop/scrollLeft on the document.body, even if the documentElement is + * the thing overflowing. In future this can be removed once document.scrollingElement + * becomes a standard across all supported browsers. + * + * Note that scroll(Width/Height) and other dimensions can be read from the + * documentElement without issue. + * @private + */ + scrollElement: null, + /** + * @cfg {Object} + * The size of the scrollable content expressed as an object with x and y properties + * @private + * @readonly + */ + size: null, + spacerXY: null, + /** + * @cfg {Object} touchAction for the scroller's {@link #element}. + * + * For more details see {@link Ext.dom.Element#setTouchAction} + */ + touchAction: null + }, + snappableCls: Ext.baseCSSPrefix + 'scroller-snappable', + elementCls: Ext.baseCSSPrefix + 'scroller', + spacerCls: Ext.baseCSSPrefix + 'scroller-spacer', + noScrollbarsCls: Ext.baseCSSPrefix + 'no-scrollbars', + statics: { + /** + * Creates and returns an appropriate Scroller instance for the current device. + * @param {Object} config Configuration options for the Scroller + * @param type + * @return {Ext.scroll.Scroller} + */ + create: function(config, type) { + return Ext.Factory.scroller(config, type); + }, + /** + * Get the scrolling element for the document based on feature detection. + * See: https://dev.opera.com/articles/fixing-the-scrolltop-bug/ + * + * @return {HTMLElement} + * + * @private + */ + getScrollingElement: function() { + var doc = document, + standard = this.$standardScrollElement, + el = doc.scrollingElement, + iframe, frameDoc; + // Normalize the scrollElement we need to read/write from + // First attempt to detect the newer standard for viewport + // scrolling + if (el) { + return el; + } + // The newer standard doesn't exist, let the scroller + // decide via feature detection. + if (standard === undefined) { + iframe = document.createElement('iframe'); + iframe.style.height = '1px'; + document.body.appendChild(iframe); + frameDoc = iframe.contentWindow.document; + frameDoc.write('
x
'); + frameDoc.close(); + standard = frameDoc.documentElement.scrollHeight > frameDoc.body.scrollHeight; + iframe.parentNode.removeChild(iframe); + this.$standardScrollElement = standard; + } + return standard ? doc.documentElement : doc.body; + }, + /** + * @private + */ + initViewportScroller: function() { + var scroller = Ext.getViewportScroller(); + if (!scroller.getElement()) { + // if the viewport component has already claimed the viewport scroller + // it will have already set its overflow element as the scroller element, + // otherwise, the element is always the body. + scroller.setElement(Ext.getBody()); + } + } + }, + constructor: function(config) { + var me = this; + me.position = { + x: 0, + y: 0 + }; + me.callParent([ + config + ]); + }, + destroy: function() { + var me = this, + partners = me._partners, + key; + Ext.undefer(me.restoreTimer); + // Clear any overflow styles + me.setX(Ext.emptyString); + me.setY(Ext.emptyString); + if (me._spacer) { + me._spacer.destroy(); + } + if (me.scrollListener) { + me.scrollListener.destroy(); + } + if (partners) { + for (key in partners) { + me.removePartner(partners[key].scroller); + } + } + // Remove element listeners, this will cause scrollElement to + // be cleared also. + me.setElement(null); + me._partners = me.component = null; + if (me.translatable) { + me.translatable.destroy(); + me.translatable = null; + } + me.removeSnapStylesheet(); + me.callParent(); + }, + /** + * Adds a "partner" scroller. Partner scrollers reflect each other's scroll position + * at all times - if either scroller is scrolled, the scroll position of its partner + * will be be automatically synchronized. + * + * A scroller may have multiple partners. + * + * @param {Ext.scroll.Scroller} partner + * @param {String} [axis='both'] The axis to synchronize (`'x'`, '`y`', or '`both`') + */ + addPartner: function(partner, axis) { + var me = this, + partners = me._partners || (me._partners = {}), + otherPartners = partner._partners || (partner._partners = {}); + // Translate to boolean flags. {x:,y:} + axis = me.axisConfigs[axis || 'both']; + partners[partner.getId()] = { + scroller: partner, + axes: axis + }; + otherPartners[me.getId()] = { + scroller: me, + axes: axis + }; + }, + applyElement: function(element, oldElement) { + var me = this; + if (oldElement && me.scrollListener) { + me.scrollListener.destroy(); + } + if (element) { + if (typeof element === 'string' && !Ext.get(element)) { + Ext.raise("Cannot create Ext.scroll.Scroller instance. " + "Element with id '" + element + "' not found."); + } + element = Ext.get(element); + } + return element; + }, + applySize: function(size, oldSize) { + var x, y; + if (size === null || typeof size === 'number') { + x = y = size; + } else if (size) { + x = size.x; + y = size.y; + } + if (x === null) { + x = 0; + } else if (x === undefined) { + x = (oldSize ? oldSize.x : 0); + } + if (y === null) { + y = 0; + } else if (y === undefined) { + y = (oldSize ? oldSize.y : 0); + } + if (!oldSize || x !== oldSize.x || y !== oldSize.y) { + return { + x: x, + y: y + }; + } + }, + /** + * Gets the `clientWidth` and `clientHeight` of the {@link #element} for this scroller. + * @return {Object} An object with `x` and `y` properties. + */ + getClientSize: function() { + var dom = this.getElement().dom; + return { + x: dom.clientWidth, + y: dom.clientHeight + }; + }, + /** + * Returns the amount of space consumed by scrollbars in the DOM + * @return {Object} size An object containing the scrollbar sizes. + * @return {Number} return.width The width of the vertical scrollbar. + * @return {Number} return.height The height of the horizontal scrollbar. + */ + getScrollbarSize: function() { + var me = this, + width = 0, + height = 0, + element = me.getElement(), + dom, x, y, hasXScroll, hasYScroll, scrollbarSize; + if (element && !element.destroyed) { + x = me.getX(); + y = me.getY(); + dom = element.dom; + if (x || y) { + scrollbarSize = Ext.getScrollbarSize(); + } + if (x === 'scroll') { + hasXScroll = true; + } else if (x) { + hasXScroll = dom.scrollWidth > dom.clientWidth; + } + if (y === 'scroll') { + hasYScroll = true; + } else if (y) { + hasYScroll = dom.scrollHeight > dom.clientHeight; + } + if (hasXScroll) { + height = scrollbarSize.height; + } + if (hasYScroll) { + width = scrollbarSize.width; + } + } + return { + width: width, + height: height + }; + }, + /** + * @method getPosition + * Returns the current scroll position + * @return {Object} An object with `x` and `y` properties. + */ + getPosition: function() { + var me = this; + if (me.positionDirty) { + me.updateDomScrollPosition(); + } + return me.position; + }, + /** + * @method getSize + * Returns the size of the scrollable content + * @return {Object} size + * @return {Number} return.x The width of the scrollable content + * @return {Number} return.y The height of the scrollable content + */ + getSize: function() { + var element = this.getElement(), + size, dom; + if (element && !element.destroyed) { + dom = element.dom; + size = { + x: dom.scrollWidth, + y: dom.scrollHeight + }; + } else { + size = { + x: 0, + y: 0 + }; + } + return size; + }, + /** + * @method getMaxPosition + * Returns the maximum scroll position for this scroller + * @return {Object} position + * @return {Number} return.x The maximum scroll position on the x axis + * @return {Number} return.y The maximum scroll position on the y axis + */ + getMaxPosition: function() { + var element = this.getElement(), + x = 0, + y = 0, + dom; + if (element && !element.destroyed) { + dom = element.dom; + x = dom.scrollWidth - dom.clientWidth; + y = dom.scrollHeight - dom.clientHeight; + } + return { + x: x, + y: y + }; + }, + /** + * @method getMaxUserPosition + * Returns the maximum scroll position for this scroller for scrolling that is initiated + * by the user via mouse or touch. This differs from getMaxPosition in that getMaxPosition + * returns the true maximum scroll position regardless of which axes are enabled for + * user scrolling. + * @return {Object} position + * @return {Number} return.x The maximum scroll position on the x axis + * @return {Number} return.y The maximum scroll position on the y axis + */ + getMaxUserPosition: function() { + var me = this, + element = me.getElement(), + x = 0, + y = 0, + dom; + if (element && !element.destroyed) { + dom = element.dom; + if (me.getX()) { + x = dom.scrollWidth - dom.clientWidth; + } + if (me.getY()) { + y = dom.scrollHeight - dom.clientHeight; + } + } + return { + x: x, + y: y + }; + }, + /** + * Refreshes the scroller size and maxPosition. + * @param {Boolean} immediate `true` to refresh immediately. By default refreshes + * are deferred until the next {@link Ext.GlobalEvents#event-idle idle} event to + * ensure any pending writes have been flushed to the dom and any reflows have + * taken place. + * @return {Ext.scroll.Scroller} this + * @chainable + */ + refresh: function() { + // Element size has changed. + // Our position property may need refreshing from the DOM + this.positionDirty = true; + this.fireEvent('refresh', this); + return this; + }, + /** + * Removes a partnership that was created via {@link #addPartner} + * @param {Ext.scroll.Scroller} partner + * @private + */ + removePartner: function(partner) { + var partners = this._partners, + otherPartners = partner._partners; + if (partners) { + delete partners[partner.getId()]; + } + if (otherPartners) { + delete (otherPartners[this.getId()]); + } + }, + /** + * Scrolls by the passed delta values, optionally animating. + * + * All of the following are equivalent: + * + * scroller.scrollBy(10, 10, true); + * scroller.scrollBy([10, 10], true); + * scroller.scrollBy({ x: 10, y: 10 }, true); + * + * A null value for either `x` or `y` will result in no scrolling on the given axis, + * for example: + * + * scroller.scrollBy(null, 10); + * + * will scroll by 10 on the y axis and leave the x axis at its current scroll position + * + * @param {Number/Number[]/Object} deltaX Either the x delta, an Array specifying x + * and y deltas or an object with "x" and "y" properties. + * @param {Number/Boolean/Object} deltaY Either the y delta, or an animate flag or + * config object. + * @param {Boolean/Object} animate Animate flag/config object if the delta values were + * passed separately. + * @return {Ext.Promise} A promise for when the scroll completes. + */ + scrollBy: function(deltaX, deltaY, animate) { + var position = this.getPosition(); + if (deltaX) { + if (deltaX.length) { + // array + animate = deltaY; + deltaY = deltaX[1]; + deltaX = deltaX[0]; + } else if (typeof deltaX !== 'number') { + // object + animate = deltaY; + deltaY = deltaX.y; + deltaX = deltaX.x; + } + } + deltaX = (typeof deltaX === 'number') ? deltaX + position.x : null; + deltaY = (typeof deltaY === 'number') ? deltaY + position.y : null; + return this.doScrollTo(deltaX, deltaY, animate); + }, + /** + * Ensures a descendant element of the scroller is visible by scrolling to it. + * + * @param {String/HTMLElement/Ext.dom.Element/Object} el + * The descendant element to scroll into view. May also be the options object with + * the `element` key defining the descendant element. + * + * @param {Object} [options] An object containing options to modify the operation. + * + * @param {Object} [options.align] The alignment for the scroll. + * @param {'start'/'center'/'end'} [options.align.x] The alignment of the x scroll. If not + * specified, the minimum will be done to make the element visible. The behavior is `undefined` + * if the request cannot be honored. If the alignment is suffixed with a `?`, the alignment will + * only take place if the item is not already in the visible area. + * @param {'start'/'center'/'end'} [options.align.y] The alignment of the y scroll. If not + * specified, the minimum will be done to make the element visible. The behavior is `undefined` + * if the request cannot be honored. If the alignment is suffixed with a `?`, the alignment will + * only take place if the item is not already in the visible area. + * + * @param {Boolean} [options.animation] Pass `true` to animate the row into view. + * + * @param {Boolean} [options.highlight=false] Pass `true` to highlight the row with a glow + * animation when it is in view. Can also be a hex color to use for highlighting + * (defaults to yellow = '#ffff9c'). + * + * @param {Boolean} [options.x=true] `false` to disable horizontal scroll. + * @param {Boolean} [options.y=true] `false` to disable vertical scroll. + * + * @return {Ext.Promise} A promise for when the scroll completes. + * @since 6.5.1 + */ + ensureVisible: function(el, options) { + var me = this, + position = me.getPosition(), + highlight, newPosition, ret; + // Might get called before Component#onBoxReady which is when the Scroller is set up with elements. + if (el) { + if (el && el.element && !el.isElement) { + options = el; + el = options.element; + } + options = options || {}; + highlight = options.highlight; + newPosition = me.getEnsureVisibleXY(el, options); + // Only attempt to scroll if it's needed. + if (newPosition.y !== position.y || newPosition.x !== position.x) { + if (highlight) { + me.on({ + scrollend: 'doHighlight', + scope: me, + single: true, + args: [ + el, + highlight + ] + }); + } + ret = me.doScrollTo(newPosition.x, newPosition.y, options.animation); + } else { + // No scrolling needed, but still honor highlight request + if (highlight) { + me.doHighlight(el, highlight); + } + // Resolve straight away + ret = Ext.Deferred.getCachedResolved(); + } + } else { + // Can't scroll + ret = Ext.Deferred.getCachedRejected(); + } + return ret; + }, + /** + * Scrolls a descendant element of the scroller into view. + * @param {String/HTMLElement/Ext.dom.Element} el the descendant to scroll into view + * @param {Boolean} [hscroll=true] False to disable horizontal scroll. + * @param {Boolean/Object} [animate] true for the default animation or a standard Element + * animation config object + * @param {Boolean/String} [highlight=false] true to + * {@link Ext.dom.Element#highlight} the element when it is in view. Can also be a + * hex color to use for highlighting (defaults to yellow = '#ffff9c'). + * + * @deprecated 6.5.1 Use {@link #ensureVisible} instead. + * @return {Ext.Promise} A promise for when the scroll completes. + */ + scrollIntoView: function(el, hscroll, animate, highlight) { + return this.ensureVisible(el, { + animation: animate, + highlight: highlight, + x: hscroll + }); + }, + /** + * Determines if the passed element is within the visible x and y scroll viewport. + * @param {String/HTMLElement/Ext.dom.Element} el The dom node, Ext.dom.Element, or + * id (string) of the dom element that is to be verified to be in view + * @return {Object} Which ranges the element is in. + * @return {Boolean} return.x `true` if the passed element is within the x visible range. + * @return {Boolean} return.y `true` if the passed element is within the y visible range. + */ + isInView: function(el) { + return this.doIsInView(el); + }, + /** + * Scrolls to the given position. + * + * All of the following are equivalent: + * + * scroller.scrollTo(10, 10, true); + * scroller.scrollTo([10, 10], true); + * scroller.scrollTo({ x: 10, y: 10 }, true); + * + * A null value for either `x` or `y` will result in no scrolling on the given axis, + * for example: + * + * scroller.scrollTo(null, 10); + * + * will scroll to 10 on the y axis and leave the x axis at its current scroll position + * + * A negative value for either `x` or `y` represents an offset from the maximum scroll + * position on the given axis: + * + * // scrolls to 10px from the maximum x scroll position and 20px from maximum y + * scroller.scrollTo(-10, -20); + * + * A value of Infinity on either axis will scroll to the maximum scroll position on + * that axis: + * + * // scrolls to the maximum position on both axes + * scroller.scrollTo(Infinity, Infinity); + * + * @param {Number} x The scroll position on the x axis. + * @param {Number} y The scroll position on the y axis. + * @param {Boolean/Object} [animation] Whether or not to animate the scrolling to the new position. + * + * @return {Ext.Promise} A promise for when the scroll completes. + */ + scrollTo: function(x, y, animation) { + var maxPosition; + if (x) { + if (x.length) { + // array + animation = y; + y = x[1]; + x = x[0]; + } else if (typeof x !== 'number') { + // object + animation = y; + y = x.y; + x = x.x; + } + } + if (x < 0 || y < 0) { + maxPosition = this.getMaxPosition(); + if (x < 0) { + x += maxPosition.x; + } + if (y < 0) { + y += maxPosition.y; + } + } + return this.doScrollTo(x, y, animation); + }, + updateDirection: function(direction) { + var me = this, + x, y; + if (!direction) { + // if no direction was configured we set its value based on the values of + // x and y. This ensures getDirection() always returns something useful + // for backward compatibility. + x = me.getX(); + y = me.getY(); + if (x && y) { + direction = (y === 'scroll' && x === 'scroll') ? 'both' : 'auto'; + } else if (y) { + direction = 'vertical'; + } else if (x) { + direction = 'horizontal'; + } + // set the _direction property directly to avoid the updater being called + // and triggering setX/setY calls + me._direction = direction; + } else { + if (direction === 'auto') { + x = true; + y = true; + } else if (direction === 'vertical') { + x = false; + y = true; + } else if (direction === 'horizontal') { + x = true; + y = false; + } else if (direction === 'both') { + x = 'scroll'; + y = 'scroll'; + } + me.setX(x); + me.setY(y); + } + }, + updateScrollbars: function(scrollbars, oldScrollbars) { + this.syncScrollbarCls(); + }, + updateSize: function(size) { + var me = this, + element = me.getElement(), + x = size.x, + y = size.y, + spacer; + if (element) { + me.positionDirty = true; + spacer = me.getSpacer(); + // Typically a dom scroller simply assumes the scroll size dictated by its content. + // In some cases, however, it is necessary to be able to manipulate this scroll size + // (infinite lists for example). This method positions a 1x1 px spacer element + // within the scroller element to set a specific scroll size. + if (!x && !y) { + spacer.hide(); + } else { + // Subtract spacer size from coordinates (spacer is always 1x1 px in size) + if (x > 0) { + x -= 1; + } + if (y > 0) { + y -= 1; + } + me.setSpacerXY({ + x: x, + y: y + }); + spacer.show(); + } + } + }, + updateMsSnapInterval: function() { + this.initMsSnapInterval(); + }, + updateSnapSelector: function() { + this.initSnap(); + }, + updateSnapOffset: function() { + this.initSnap(); + }, + updateTouchAction: function(touchAction) { + var element = this.getElement(); + if (element) { + element.setTouchAction(touchAction); + } + }, + updateElement: function(element, oldElement) { + var me = this, + touchAction = me.getTouchAction(), + scrollListener = me.scrollListener, + elementCls = me.elementCls, + eventSource, scrollEl; + // If we have a scrollListener, we also have a scrollElement + if (scrollListener) { + scrollListener.destroy(); + me.scrollListener = null; + me.setScrollElement(null); + } + if (oldElement && !oldElement.destroyed) { + // TODO: might be nice to have x-scroller-foo classes to map overflow styling + oldElement.setStyle('overflow', 'hidden'); + oldElement.removeCls(elementCls); + } + if (element) { + if (element.dom === document.documentElement || element.dom === document.body) { + // When the documentElement or body is scrolled, its scroll events are + // fired via the window object + eventSource = Ext.getWin(); + scrollEl = Ext.scroll.Scroller.getScrollingElement(); + } else { + scrollEl = eventSource = element; + } + me.setScrollElement(Ext.get(scrollEl)); + me.scrollListener = eventSource.on({ + scroll: me.onDomScroll, + scope: me, + destroyable: true + }); + if (touchAction) { + element.setTouchAction(touchAction); + } + me.initXStyle(); + me.initYStyle(); + element.addCls(elementCls); + me.initSnap(); + me.initMsSnapInterval(); + me.syncScrollbarCls(); + } + }, + updateX: function(x) { + this.initXStyle(); + }, + updateY: function(y) { + this.initYStyle(); + }, + deprecated: { + '5': { + methods: { + /** + * @method getScroller + * Returns this scroller. + * + * In Sencha Touch 2, access to a Component's Scroller was provided via + * a Ext.scroll.View class that was returned from the Component's getScrollable() + * method: + * + * component.getScrollable().getScroller(); + * + * in 5.0 all the functionality of Ext.scroll.View has been rolled into + * Ext.scroll.Scroller, and Ext.scroll.View has been removed. Component's + * getScrollable() method now returns a Ext.scroll.Scroller. This method is + * provided for compatibility. + * @deprecated 5.0 This method is deprecated. Please use Ext.scroll.Scroller's + * getScrollable() method instead. + */ + getScroller: function() { + return this; + } + } + }, + '5.1.0': { + methods: { + /** + * @method scrollToTop + * Scrolls to 0 on both axes + * @param {Boolean/Object} animate + * @private + * @return {Ext.scroll.Scroller} this + * @chainable + * @deprecated 5.1.0 Use scrollTo instead + */ + scrollToTop: function(animate) { + return this.scrollTo(0, 0, animate); + }, + /** + * @method scrollToEnd + * Scrolls to the maximum position on both axes + * @param {Boolean/Object} animate + * @private + * @return {Ext.scroll.Scroller} this + * @chainable + * @deprecated 5.1.0 Use scrollTo instead + */ + scrollToEnd: function(animate) { + return this.scrollTo(Infinity, Infinity, animate); + } + } + } + }, + privates: { + axisConfigs: { + x: { + x: true + }, + y: { + y: true + }, + both: { + x: true, + y: true + } + }, + /** + * @private + * Gets the x/y coordinates to ensure the element is scrolled into view. + * + * @param {String/HTMLElement/Ext.dom.Element/Object} el + * The descendant element to scroll into view. May also be the options object with + * the `element` key defining the descendant element. + * + * @param {Object} [options] An object containing options to modify the operation. + * + * @param {Object/String} [options.align] The alignment for the scroll. If a string, this value + * will be used for both `x` and `y` alignments. + * @param {'start'/'center'/'end'} [options.align.x] The alignment of the x scroll. If not + * specified, the minimum will be done to make the element visible. The behavior is `undefined` + * if the request cannot be honored. If the alignment is suffixed with a `?`, the alignment will + * only take place if the item is not already in the visible area. + * @param {'start'/'center'/'end'} [options.align.y] The alignment of the y scroll. If not + * specified, the minimum will be done to make the element visible. The behavior is `undefined` + * if the request cannot be honored. If the alignment is suffixed with a `?`, the alignment will + * only take place if the item is not already in the visible area. + * + * @param {Boolean} [options.x=true] `false` to disable horizontal scroll and `x` align option. + * @param {Boolean} [options.y=true] `false` to disable vertical scroll and `y` align option. + * @return {Object} The new position that will be used to scroll the element into view. + * @since 6.5.1 + */ + getEnsureVisibleXY: function(el, options) { + var position = this.getPosition(), + viewport = this.component ? this.component.getScrollableClientRegion() : this.getElement(), + newPosition, align; + if (el && el.element && !el.isElement) { + options = el; + el = options.element; + } + options = options || {}; + align = options.align; + if (align) { + if (Ext.isString(align)) { + align = { + x: options.x === false ? null : align, + y: options.y === false ? null : align + }; + } else if (Ext.isObject(align)) { + if (align.x && options.x === false) { + align.x = null; + } + if (align.y && options.y === false) { + align.y = null; + } + } + } + newPosition = Ext.fly(el).getScrollIntoViewXY(viewport, position.x, position.y, align); + newPosition.x = options.x === false ? position.x : newPosition.x; + newPosition.y = options.y === false ? position.y : newPosition.y; + return newPosition; + }, + getSpacer: function() { + var me = this, + spacer = me._spacer, + element; + // In some cases (e.g. infinite lists) we need to be able to tell the scroller + // to have a specific size, regardless of its contents. This creates a spacer + // element which can then be absolutely positioned to affect the element's + // scroll size. Must be first element, so it is not translated due to being after + // the element contrainer el. + if (!spacer) { + element = me.getElement(); + spacer = me._spacer = element.createChild({ + cls: me.spacerCls, + role: 'presentation' + }, element.dom.firstChild); + spacer.setVisibilityMode(2); + // 'display' visibilityMode + spacer.hide(); + // make sure the element is positioned if it is not already. This ensures + // that the spacer's position will affect the element's scroll size + element.position(); + } + return spacer; + }, + applySpacerXY: function(pos, oldPos) { + // Opt out if we have the same value + if (oldPos && pos.x === oldPos.x && pos.y === oldPos.y) { + pos = undefined; + } + return pos; + }, + updateSpacerXY: function(pos) { + var me = this, + spacer = me.getSpacer(), + sStyle = spacer.dom.style, + scrollHeight = pos.y, + shortfall; + sStyle.marginTop = ''; + me.translateSpacer(pos.x, me.constrainScrollRange(scrollHeight)); + // Force a synchronous layout to update the scrollHeight. + // This flip-flops between 0px and 1px + sStyle.lineHeight = Number(!parseInt(sStyle.lineHeight, 10)) + 'px'; + // See if we can get any more scrollHeight from a margin-top + if (scrollHeight > 1000000) { + shortfall = scrollHeight - me.getElement().dom.scrollHeight; + if (shortfall > 0) { + sStyle.marginTop = Math.min(shortfall, me.maxSpacerMargin || 0) + 'px'; + } + } + }, + // rtl hook - rtl version sets right style + translateSpacer: function(x, y) { + this.getSpacer().translate(x, y); + }, + doIsInView: function(el, skipCheck) { + var me = this, + c = me.component, + result = { + x: false, + y: false + }, + elRegion, + myEl = me.getElement(), + myElRegion; + if (el && (skipCheck || (myEl.contains(el) || (c && c.owns(el))))) { + myElRegion = myEl.getRegion(); + elRegion = Ext.fly(el).getRegion(); + result.x = elRegion.right > myElRegion.left && elRegion.left < myElRegion.right; + result.y = elRegion.bottom > myElRegion.top && elRegion.top < myElRegion.bottom; + } + return result; + }, + // Checks if the scroller contains a component by searching up the element hierarchy + // using components. It uses component navigation as opposed to elements because we + // want logical ownership. + contains: function(component) { + var el = this.getElement(), + owner = component; + while (owner && owner !== Ext.Viewport) { + if (el.contains(owner.el)) { + return true; + } + owner = owner.getRefOwner(); + } + return false; + }, + constrainScrollRange: function(scrollRange) { + // Only do the expensive search for the browser limit if they + // want more than a million pixels. + if (scrollRange < 1000000) { + return scrollRange; + } + if (!this.maxSpacerTranslate) { + // + // Find max scroll height which transform: translateY(npx) will support. + // IE11 appears to have 21,474,834 + // Chrome and Safari have 16,777,216, but additional margin-top of 16777215px allows a scrollHeight of 33,554,431 + // Firefox has 17,895,698 + // IE9-10 1,534,000 + // + var maxScrollHeight = Math.pow(2, 32), + tooHigh = maxScrollHeight, + tooLow = 500, + scrollTest = Ext.getBody().createChild({ + style: { + position: 'absolute', + left: '-10000px', + top: '0', + width: '500px', + height: '500px' + }, + cn: { + cls: this.spacerCls + } + }, null, true), + stretcher = Ext.get(scrollTest.firstChild), + sStyle = stretcher.dom.style; + stretcher.translate(0, maxScrollHeight - 1); + sStyle.lineHeight = Number(!parseInt(sStyle.lineHeight, 10)) + 'px'; + // See what the max translateY is which still stretches the scrollHeight + while (tooHigh !== tooLow + 1) { + stretcher.translate(0, (maxScrollHeight = tooLow + Math.floor((tooHigh - tooLow) / 2))); + // Force a synchronous layout to update the scrollHeight. + // This flip-flops between 0px and 1px + sStyle.lineHeight = Number(!parseInt(sStyle.lineHeight, 10)) + 'px'; + if (scrollTest.scrollHeight < maxScrollHeight) { + tooHigh = maxScrollHeight; + } else { + tooLow = maxScrollHeight; + } + } + stretcher.translate(0, Ext.scroll.Scroller.prototype.maxSpacerTranslate = tooLow); + // Go through the same steps seeing how far we can push it with margin-top + tooHigh = tooLow * 2; + while (tooHigh !== tooLow + 1) { + stretcher.dom.style.marginTop = ((maxScrollHeight = tooLow + Math.floor((tooHigh - tooLow) / 2))) + 'px'; + // Force a synchronous layout to update the scrollHeight. + // This flip-flops between 0px and 1px + sStyle.lineHeight = Number(!parseInt(sStyle.lineHeight, 10)) + 'px'; + if (scrollTest.scrollHeight < maxScrollHeight) { + tooHigh = maxScrollHeight; + } else { + tooLow = maxScrollHeight; + } + } + Ext.fly(scrollTest).destroy(); + Ext.scroll.Scroller.prototype.maxSpacerMargin = tooLow - Ext.scroll.Scroller.prototype.maxSpacerTranslate; + } + // The maximum a translateY transform can be pushed to stretch the scrollHeight before + // it collapses back to offsetHeight + return Math.min(scrollRange, this.maxSpacerTranslate); + }, + // hook for rtl mode to convert an x coordinate to RTL space. + convertX: function(x) { + return x; + }, + // highlights an element after it has been scrolled into view + doHighlight: function(el, highlight) { + if (highlight !== true) { + // handle hex color + Ext.fly(el).highlight(highlight); + } else { + Ext.fly(el).highlight(); + } + }, + doScrollTo: function(x, y, animate) { + // There is an IE8 override of this method; when making changes here + // don't forget to update the override as well + var me = this, + element = me.getScrollElement(), + maxPosition, dom, xInf, yInf, ret, translatable, deferred; + if (element && !element.destroyed) { + dom = element.dom; + xInf = (x === Infinity); + yInf = (y === Infinity); + if (xInf || yInf) { + maxPosition = me.getMaxPosition(); + if (xInf) { + x = maxPosition.x; + } + if (yInf) { + y = maxPosition.y; + } + } + if (x !== null) { + x = me.convertX(x); + } + if (animate) { + translatable = me.translatable; + if (!translatable) { + me.translatable = translatable = new Ext.util.translatable.ScrollPosition({ + element: element + }); + } + deferred = new Ext.Deferred(); + // Use onFrame here to let the scroll complete and animations to fire. + translatable.on('animationend', function() { + // Check destroyed vs destroying since we're onFrame here + if (me.destroyed) { + deferred.reject(); + } else { + deferred.resolve(); + } + }, Ext.global, { + single: true, + onFrame: true + }); + translatable.translate(x, y, animate); + ret = deferred.promise; + } else { + if (y != null) { + dom.scrollTop = y; + } + if (x != null) { + dom.scrollLeft = x; + } + ret = Ext.Deferred.getCachedResolved(); + } + // Our position object will need refreshing before returning. + me.positionDirty = true; + } else { + ret = Ext.Deferred.getCachedRejected(); + } + return ret; + }, + fireScrollStart: function(x, y, xDelta, yDelta) { + var me = this, + component = me.component; + me.invokePartners('onPartnerScrollStart', x, y, xDelta, yDelta); + me.startX = x - xDelta; + me.startY = y - yDelta; + if (me.hasListeners.scrollstart) { + me.fireEvent('scrollstart', me, x, y); + } + if (component && component.onScrollStart) { + component.onScrollStart(x, y); + } + Ext.GlobalEvents.fireEvent('scrollstart', me, x, y); + }, + fireScroll: function(x, y, xDelta, yDelta) { + var me = this, + component = me.component; + me.invokePartners('onPartnerScroll', x, y, xDelta, yDelta); + if (me.hasListeners.scroll) { + me.fireEvent('scroll', me, x, y, xDelta, yDelta); + } + if (component && component.onScrollMove) { + component.onScrollMove(x, y); + } + Ext.GlobalEvents.fireEvent('scroll', me, x, y, xDelta, yDelta); + }, + fireScrollEnd: function(x, y, xDelta, yDelta) { + var me = this, + component = me.component, + dx = x - me.startX, + dy = y - me.startY; + me.startX = me.startY = null; + me.invokePartners('onPartnerScrollEnd', x, y, xDelta, yDelta); + if (me.hasListeners.scrollend) { + me.fireEvent('scrollend', me, x, y, dx, dy); + } + if (component && component.onScrollEnd) { + component.onScrollEnd(x, y); + } + Ext.GlobalEvents.fireEvent('scrollend', me, x, y, dx, dy); + }, + // rtl hook + getElementScroll: function(element) { + return element.getScroll(); + }, + initSnap: function() { + var me = this, + snapOffset = me.getSnapOffset(), + snapSelector = me.getSnapSelector(), + element = me.getElement(), + offsetX, offsetY, snapCoordinate; + if (element && snapSelector) { + element.addCls(me.snappableCls); + me.removeSnapStylesheet(); + if (snapOffset) { + offsetX = snapOffset.x || 0; + offsetY = snapOffset.y || 0; + if (offsetX) { + offsetX = -offsetX + 'px'; + } + if (offsetY) { + offsetY = -offsetY + 'px'; + } + } + snapCoordinate = offsetX + ' ' + offsetY + ';'; + me.snapStylesheet = Ext.util.CSS.createStyleSheet('#' + element.id + ' ' + snapSelector + '{-webkit-scroll-snap-coordinate:' + snapCoordinate + 'scroll-snap-coordinate:' + snapCoordinate + '}'); + } + }, + initMsSnapInterval: function() { + var element = this.getElement(), + interval, x, y, style; + if (element) { + interval = this.getMsSnapInterval(); + if (interval) { + x = interval.x; + y = interval.y; + style = element.dom.style; + if (x) { + style['-ms-scroll-snap-points-x'] = 'snapInterval(0px, ' + x + 'px)'; + } + if (y) { + style['-ms-scroll-snap-points-y'] = 'snapInterval(0px, ' + y + 'px)'; + } + } + } + }, + initXStyle: function() { + var element = this.getElement(), + x = this.getX(); + // Check that element exists and is not destroyed + if (element && element.dom) { + if (!x) { + x = 'hidden'; + } else if (x === true) { + x = 'auto'; + } + element.setStyle('overflow-x', x); + } + }, + initYStyle: function() { + var element = this.getElement(), + y = this.getY(); + // Check that element exists and is not destroyed + if (element && element.dom) { + if (!y) { + y = 'hidden'; + } else if (y === true) { + y = 'auto'; + } + element.setStyle('overflow-y', y); + } + }, + invokePartners: function(method, x, y, xDelta, yDelta) { + var me = this, + partners = me._partners, + partner, id, axes; + if (!me.suspendSync) { + me.invokingPartners = true; + for (id in partners) { + axes = partners[id].axes; + partner = partners[id].scroller; + // Only pass the scroll on to partners if we are are configured to pass on the scrolled dimension + if (!partner.invokingPartners && (xDelta && axes.x || yDelta && axes.y)) { + partner[method](me, axes.x ? x : null, axes.y ? y : null, xDelta, yDelta); + } + } + me.invokingPartners = false; + } + }, + suspendPartnerSync: function() { + this.suspendSync = (this.suspendSync || 0) + 1; + }, + resumePartnerSync: function(syncNow) { + var me = this, + position; + if (me.suspendSync) { + me.suspendSync--; + } + if (!me.suspendSync && syncNow) { + position = me.getPosition(); + me.invokePartners('onPartnerScroll', position.x, position.y); + me.invokePartners('onPartnerScrollEnd', position.x, position.y); + } + }, + readPosition: function(position) { + var me = this, + element = me.getScrollElement(), + elScroll; + position = position || {}; + if (element && !element.destroyed) { + elScroll = me.getElementScroll(element); + position.x = elScroll.left; + position.y = elScroll.top; + } + return position; + }, + updateDomScrollPosition: function(silent) { + var me = this, + position = me.position, + oldX = position.x, + oldY = position.y, + x, y, xDelta, yDelta; + me.readPosition(position); + x = position.x; + y = position.y; + me.positionDirty = false; + if (!silent) { + xDelta = x - oldX; + yDelta = y - oldY; + // If we already know about the position. then we've been coerced there by a partner + // and that will have been firing our event sequence synchronously, so they do not + // not need to be fire in response to the ensuing scroll event. + if (xDelta || yDelta) { + if (!me.isScrolling) { + me.isScrolling = Ext.isScrolling = true; + me.fireScrollStart(x, y, xDelta, yDelta); + } + me.fireScroll(x, y, xDelta, yDelta); + me.onDomScrollEnd(x, y, xDelta, yDelta); + } + } + return position; + }, + /** + * @private + * May be called when a Component is rendererd AFTER some scrolling partner has begun its lifecycle to sync + * this scroller with partners which may be scrolled anywhere by now. + */ + syncWithPartners: function() { + var me = this, + partners = me._partners, + id, partner, position; + me.suspendPartnerSync(); + for (id in partners) { + partner = partners[id].scroller; + position = partner.getPosition(); + me.onPartnerScroll(partner, position.x, position.y); + } + me.resumePartnerSync(); + }, + syncScrollbarCls: function() { + var element = this.getElement(); + if (element) { + element.toggleCls(this.noScrollbarsCls, this.getScrollbars() === false); + } + }, + onDomScroll: function() { + var hasTimer = !!this.restoreTimer; + this.updateDomScrollPosition(hasTimer); + if (hasTimer) { + Ext.undefer(this.onDomScrollEnd.timer); + return; + } + }, + doOnDomScrollEnd: function(x, y, xDelta, yDelta) { + var me = this; + // Could be destroyed by this time + if (me.destroying || me.destroyed) { + return; + } + me.isScrolling = Ext.isScrolling = false; + // if this is being flushed we only need to set the scrolling status to false + if (x === undefined) { + return; + } + me.trackingScrollLeft = x; + me.trackingScrollTop = y; + me.fireScrollEnd(x, y, xDelta, yDelta); + }, + onPartnerScrollStart: function(partner, x, y, xDelta, yDelta) { + // Pass the signal on immediately to all partners. + this.isScrolling = true; + this.fireScrollStart(x, y, xDelta, yDelta); + }, + onPartnerScroll: function(partner, x, y, xDelta, yDelta) { + this.doScrollTo(x, y, false); + // Update the known scroll position so that when it reacts to its DOM, + // it will not register a change and so will not invoke partners. + // All scroll intentions are propagated synchronously. + // The ensuing multiple scroll events are then ignored. + this.updateDomScrollPosition(true); + // Pass the signal on immediately to all partners. + this.fireScroll(x, y, xDelta, yDelta); + }, + onPartnerScrollEnd: function(partner, x, y, xDelta, yDelta) { + // manually clearing the buffer queue before calling the method without buffering + this.cancelOnDomScrollEnd(); + // Pass the signal on immediately to all partners. + // We are called by the onDomScrollEnd of our controller + // so we must not add another delay and call doOnScrollEnd directly. + this.doOnDomScrollEnd(x, y, xDelta, yDelta); + }, + removeSnapStylesheet: function() { + var stylesheet = this.snapStylesheet; + if (stylesheet) { + Ext.util.CSS.removeStyleSheet(stylesheet); + this.snapStylesheet = null; + } + }, + restoreState: function() { + var me = this, + el = me.getScrollElement(); + if (el) { + // Only restore state if has been previously captured! For example, + // floaters probably have not been hidden before initially shown. + if (me.trackingScrollTop !== undefined) { + // If we're restoring the scroll position, we don't want to publish + // scroll events since the scroll position should not have changed + // at all as far as the user is concerned, so just do it silently + // while ensuring we maintain the correct internal state. 50ms is + // enough to capture the async scroll events, anything after that + // we re-enable. + if (!me.restoreTimer) { + me.restoreTimer = Ext.defer(function() { + me.restoreTimer = null; + }, 50); + } + me.doScrollTo(me.trackingScrollLeft, me.trackingScrollTop, false); + } + } + } + } +}, // Do not discard the state. +// It may need to be restored again. +function(Scroller) { + /** + * @private + * @return {Ext.scroll.Scroller} + */ + Ext.getViewportScroller = function() { + // This method creates the global viewport scroller. This scroller instance must + // always exist regardless of whether or not there is a Viewport component in use + // so that global scroll events will still fire. Menus and some other floating + // things use these scroll events to hide themselves. + var scroller = Scroller.viewport; + if (!scroller) { + Scroller.viewport = scroller = new Scroller(); + Scroller.initViewportScroller(); + } + return scroller; + }; + /** + * @private + * @param {Ext.scroll.Scroller} scroller + */ + Ext.setViewportScroller = function(scroller) { + if (Scroller.viewport !== scroller) { + Ext.destroy(Scroller.viewport); + if (scroller && !scroller.isScroller) { + scroller = new Scroller(scroller); + } + Scroller.viewport = scroller; + } + }; + Ext.onReady(function() { + // The viewport scroller must always exist, but it is deferred so that the + // viewport component has a chance to call Ext.setViewportScroller() with + // its own scroller first. + // We assign the timer to a property to cancel the call while setting up + // for unit tests. We will call initViewportScroller without waiting for the + // Viewport to initialize. + Scroller.initViewportScrollerTimer = Ext.defer(Scroller.initViewportScroller, 100); + }); +}); + +/** + * A mixin to add floating capability to a Component. + */ +Ext.define('Ext.util.Floating', { + mixinId: 'floating', + uses: [ + 'Ext.ZIndexManager' + ], + /** + * @cfg {Boolean} focusOnToFront + * Specifies whether the floated component should be automatically {@link Ext.Component#method-focus focused} when + * it is {@link #toFront brought to the front}. + */ + focusOnToFront: true, + /** + * @cfg {Boolean} [modal=false] + * True to make the floated component modal and mask everything behind it when displayed, false to display it without + * restricting access to other UI elements. + */ + /** + * @cfg {String/Boolean} shadow + * Specifies whether the floating component should be given a shadow. Set to true to automatically create an + * {@link Ext.Shadow}, or a string indicating the shadow's display {@link Ext.Shadow#mode}. Set to false to + * disable the shadow. + */ + shadow: 'sides', + /** + * @cfg {Boolean} [animateShadow=false] + * `true` to animate the shadow along with the component while the component is animating. + * By default the shadow is hidden while the component is animating + */ + animateShadow: false, + /** + * @cfg {Boolean} constrain + * True to constrain this Components within its containing element, false to allow it to fall outside of its containing + * element. By default this Component will be rendered to `document.body`. To render and constrain this Component within + * another element specify {@link Ext.Component#renderTo renderTo}. + */ + constrain: false, + /** + * @cfg {Boolean} [alignOnScroll=true] + * By default, when the {@link Ext.Component#alignTo alignTo} method is called, a floating component will + * scroll to keep aligned with the anchoring element if the anchoring element is part of the scroll. + * + * If this is not necessary, and the `alignTo` is a one-off operation then set this config to `false`. + */ + alignOnScroll: true, + /** + * @cfg {Boolean} [fixed=false] + * Configure as `true` to have this Component fixed at its `X, Y` coordinates in the browser viewport, immune + * to scrolling the document. + */ + /** + * @cfg {Number} shadowOffset + * Number of pixels to offset the shadow. + */ + /** + * @cfg {Boolean} shim `true` to enable an iframe shim for this Component to keep + * windowed objects from showing through. + */ + /** + * @property {Boolean} floating + * The value `true` indicates that this Component is floating. + * @private + * @readonly + */ + /** + * @property {Ext.ZIndexManager} zIndexManager + * Only present for {@link Ext.Component#cfg-floating floating} Components after + * they have been rendered. + * + * A reference to the ZIndexManager which is managing this Component's z-index. + * + * The {@link Ext.ZIndexManager ZIndexManager} maintains a stack of floating Component z-indices, and also provides + * a single modal mask which is insert just beneath the topmost visible modal floating Component. + * + * Floating Components may be {@link Ext.Component#toFront brought to the front} or {@link Ext.Component#toBack sent to the back} of the + * z-index stack. + * + * This defaults to the global {@link Ext.WindowManager ZIndexManager} for floating Components that are + * programatically {@link Ext.Component#method-render rendered}. + * + * For {@link Ext.Component#cfg-floating floating} Components that are added to a + * Container, the ZIndexManager is acquired from the first ancestor Container found + * that is floating. If no floating ancestor is found, the global + * {@link Ext.WindowManager ZIndexManager} is used. + * + * See {@link Ext.Component#cfg-floating} and {@link #zIndexParent} + * @readonly + */ + /** + * @property {Ext.Container} zIndexParent + * Only present for {@link Ext.Component#cfg-floating} Components which were + * inserted as child items of Containers, and which have a floating Container in + * their containment ancestry. + * + * For {@link Ext.Component#cfg-floating} Components which are child items of a + * Container, the zIndexParent will be a floating ancestor Container which is + * responsible for the base z-index value of all its floating descendants. It + * provides a {@link Ext.ZIndexManager ZIndexManager} which provides z-indexing + * services for all its descendant floating Components. + * + * Floating Components that are programmatically {@link Ext.Component#method-render rendered} will not have a `zIndexParent` + * property. + * + * For example, the dropdown {@link Ext.view.BoundList BoundList} of a ComboBox which is in a Window will have the + * Window as its `zIndexParent`, and will always show above that Window, wherever the Window is placed in the z-index stack. + * + * See {@link Ext.Component#cfg-floating} and {@link #zIndexManager} + * @readonly + */ + config: { + /** + * @private + * @cfg {Number} activeCounter An incrementing numeric counter indicating activation index for use by the {@link #zIndexManager} + * to sort its stack. + */ + activeCounter: 0, + /** + * @cfg {Boolean/Number} [alwaysOnTop=false] A flag indicating that this component should be on the top of the z-index stack for use by the {@link #zIndexManager} + * to sort its stack. + * + * This may be a positive number to prioritize the ordering of multiple visible always on top components. + * + * This may be set to a *negative* number to prioritize a component to the *bottom* of the z-index stack. + */ + alwaysOnTop: false + }, + preventDefaultAlign: false, + _visModeMap: { + visibility: 1, + display: 2, + offsets: 3 + }, + constructor: function() { + var me = this, + el = me.el, + shadow = me.shadow, + shadowOffset, shadowConfig; + if (shadow) { + shadowConfig = { + mode: (shadow === true) ? 'sides' : shadow + }; + shadowOffset = me.shadowOffset; + if (shadowOffset) { + shadowConfig.offset = shadowOffset; + } + shadowConfig.animate = me.animateShadow; + shadowConfig.fixed = me.fixed; + el.enableShadow(shadowConfig, false); + } + if (me.shim || Ext.useShims) { + el.enableShim({ + fixed: me.fixed + }, false); + } + el.setVisibilityMode(me._visModeMap[me.hideMode]); + // mousedown brings to front + // Use capture to see the event first before any contained DD instance stop the event. + me.el.on({ + mousedown: me.onMouseDown, + scope: me, + capture: true + }); + // Register with the configured ownerCt. + // With this we acquire a floatParent for relative positioning, and a zIndexParent which is an + // ancestor floater which provides zIndex management. + me.registerWithOwnerCt(); + me.initHierarchyEvents(); + }, + alignTo: function(alignTarget, position, offsets, animate, monitorScroll) { + var me = this, + alignEl, destroyed, dom, myXY, anchorXY, listeners; + // We may be aligned to a Component, an Ext.Element, or an HtmlElement + // In the latter case we can't create Ext.Element because that might leave + // orphan Element instances so we use our internal Fly instance instead. + if (alignTarget.isComponent) { + alignEl = alignTarget.el; + destroyed = alignTarget.destroyed; + } else { + me.alignTargetFly = me.alignTargetFly || new Ext.dom.Fly(); + alignEl = alignTarget = me.alignTargetFly.attach(alignTarget); + dom = alignEl.dom; + destroyed = !dom || Ext.isGarbage(dom); + } + if (destroyed) { + me._lastAlignTarget = null; + if (me.alignListeners) { + me.alignListeners.destroy(); + } + return; + } + me.mixins.positionable.alignTo.call(me, alignEl, position, offsets, animate, monitorScroll !== false); + // Work out the vector to maintain our relative position as the alignTarget element moves + myXY = me.getXY(); + anchorXY = alignTarget.getXY(); + me.alignVector = [ + myXY[0] - anchorXY[0], + myXY[1] - anchorXY[1] + ]; + // Let's stash these on the component/element in case it's aligned to something else + // in its little lifetime. + me._lastAlignTarget = alignTarget; + me._lastAlignToPos = position; + me._lastAlignToOffsets = offsets; + // If we are aligned to a Component which is also either floating and aligned, or + // *inside* a floating which is aligned, find the topmost, static target which + // is anchoring the whole cascade. + // For example the column header trigger el at the top of a column menu set. + me._topAlignTarget = me.getTopAlignTarget(); + // Initially we have no clipping. + me.clearClip(); + // Since floaters May be rendered to the document.body, floaters could become marooned + // from its alignTarget if the alignTarget is inside an element that scrolls + // and then that element is scrolled. + // Only add the listeners once. + if (!me.alignListeners) { + // Always realign on window resize - the anchor element can move as a result. + // Buffer so that we execute after any viewport layout has finished. + listeners = { + resize: { + fn: me.alignOnResize, + buffer: 100 + }, + scope: me, + destroyable: true + }; + // If we are supposed to align on scroll aligned, then add global scroll listener + // so that we can follow the anchor element wherever it scrolls to. + // Do not need to do this the floater is rendered inside the element that they are aligned to. + // For example CellEditors within grid cells. + if (me.alignOnScroll && !alignEl.contains(me.el)) { + listeners.scroll = me.doRealign; + } + me.alignListeners = Ext.on(listeners); + } + }, + initFloatConstrain: function() { + var me = this, + floatParent = me.floatParent; + // If a floating Component is configured to be constrained, but has no configured + // constrainTo setting, set its constrainTo to be it's ownerCt before rendering. + if ((me.constrain || me.constrainHeader) && !me.constrainTo) { + me.constrainTo = floatParent ? floatParent.getTargetEl() : me.container; + } + }, + initHierarchyEvents: function() { + var me = this; + if (!me.hierarchyEventListeners) { + me.hierarchyEventListeners = Ext.on({ + hide: 'syncHidden', + collapse: 'syncHidden', + show: 'syncHidden', + expand: 'syncHidden', + added: 'syncHidden', + scope: me, + destroyable: true + }); + } + }, + registerWithOwnerCt: function() { + var me = this, + ownerCt = me.ownerCt, + zip = me.zIndexParent; + if (zip) { + zip.unregisterFloatingItem(me); + } + // Acquire a zIndexParent by traversing the ownerCt axis for the nearest floating ancestor. + // This is to find a base which can allocate relative z-index values + zip = me.zIndexParent = me.up('[floating]'); + // Set the floatParent to the ownertCt if one has been provided. + // Otherwise use the zIndexParent. + // Developers must only use ownerCt if there is really a containing relationship. + me.floatParent = ownerCt || zip; + me.initFloatConstrain(); + delete me.ownerCt; + if (zip) { + zip.registerFloatingItem(me); + } else { + Ext.WindowManager.register(me); + } + }, + /** + * @private + * Mousedown brings to front, and programmatically grabs focus + * unless the mousedown was on a focusable element + */ + onMouseDown: function(e) { + var me = this, + focusTask = me.focusTask, + owner = me.getRefOwner(), + // Do not autofocus the Component (which delegates onto the getFocusEl() descendant) + // for touch events. + preventFocus = e.pointerType === 'touch', + target, dom, skipFronting; + if (me.floating && (// get out of here if there is already a pending focus. This usually means + // that the handler for a mousedown on a child element set the focus on some + // other component, and we so not want to steal it back. See EXTJSIV-9458 + !focusTask || !focusTask.id)) { + // If focus is already within this floating hierarchy, then do not disturb it on mousedown. + if (me.owns(Ext.Element.getActiveElement())) { + // Indicate that we want the component to be + // considered as a focus target but no + preventFocus = { + ownsFocus: true + }; + } + target = e.target; + dom = me.el.dom; + // loop the target's ancestors to see if we clicked on a focusable element + // or a descendant of a focusable element, If so we don't want to focus + // this floating component. If we end up with no target, it probably means + // it's been removed from the DOM, so we should attempt to bring ourselves + // to front anyway + while (!preventFocus && target && target !== dom) { + if (Ext.fly(target).isFocusable()) { + preventFocus = { + ownsFocus: true + }; + } + target = target.parentNode; + } + // We can skip toFront() if we're already active and the click was + // within our element but not on something focusable. + skipFronting = Ext.WindowManager.getActive() === me && (target === dom || preventFocus); + // If what was mousedowned upon is going to claim focus anyway, pass + // preventFocus as true. + if (!skipFronting) { + me.toFront(preventFocus); + } + // If we have not hit a focusable element, and our owner + // contains focus, then prevent the default action of mousedown (focus movement) + if (!preventFocus && owner && owner.containsFocus) { + e.preventDefault(); + } + } + }, + onBeforeFloatLayout: function() { + this.el.preventSync = true; + }, + onAfterFloatLayout: function() { + var el = this.el; + if (el.shadow || el.shim) { + // An element's underlays (shadow and shim) are automatically synced in response + // to any calls to Ext.Element APIs that change the element's size or position + // (setXY, setWidth, etc). Since the layout system bypasses these APIs and + // sets the element's styles directly, we need to trigger a sync now. + el.setUnderlaysVisible(true); + el.syncUnderlays(); + } + }, + /** + * synchronizes the hidden state of this component with the state of its hierarchy + * @private + */ + syncHidden: function() { + var me = this, + hidden = me.hidden || !me.rendered, + hierarchicallyHidden = me.hierarchicallyHidden = me.isHierarchicallyHidden(), + pendingShow = me.pendingShow; + if (hidden !== hierarchicallyHidden) { + if (hierarchicallyHidden) { + me.hide(); + me.pendingShow = true; + } else if (pendingShow) { + delete me.pendingShow; + if (pendingShow.length) { + me.show.apply(me, pendingShow); + } else { + me.show(); + } + } + } + }, + /** + * @private + * z-index is managed by the zIndexManager and may be overwritten at any time. + * Returns the next z-index to be used. + * + * If this is a Container, then it will have rebased any managed floating Components, + * and so the next available z-index will be approximately 10000 above that. + */ + setZIndex: function(index) { + var me = this; + me.el.setZIndex(index); + // Next item goes 10 above; + index += 10; + // When a Container with floating descendants has its z-index set, it rebases any floating descendants it is managing. + // The returned value is a round number approximately 10000 above the last z-index used. + if (me.floatingDescendants) { + index = Math.floor(me.floatingDescendants.setBase(index) / 100) * 100 + 10000; + } + return index; + }, + /** + * Moves this floating Component into a constrain region. + * + * By default, this Component is constrained to be within the container it was added to, or the element it was + * rendered to. + * + * An alternative constraint may be passed. + * @param {String/HTMLElement/Ext.dom.Element/Ext.util.Region} [constrainTo] The Element or {@link Ext.util.Region Region} + * into which this Component is to be constrained. Defaults to the element into which this floating Component + * was rendered. + */ + doConstrain: function(constrainTo) { + var me = this, + // Calculate the constrained position. + // calculateConstrainedPosition will provide a default constraint + // region if there is no explicit constrainTo, *and* there is no floatParent owner Component. + xy = me.calculateConstrainedPosition(constrainTo, null, true); + // false is returned if no movement is needed + if (xy) { + me.setPosition(xy); + } + }, + updateActiveCounter: function(activeCounter) { + var me = this, + zim = me.zIndexParent; + // If we have a zIndexParent, it has to rebase its own zIndices + if (zim && zim !== zim.zIndexManager.front && me.bringParentToFront !== false) { + zim.setActiveCounter(++Ext.ZIndexManager.activeCounter); + } + // Rebase the local zIndices + zim = me.zIndexManager; + if (zim) { + zim.onComponentUpdate(me); + } + }, + updateAlwaysOnTop: function(alwaysOnTop) { + var z = this.zIndexManager; + // Rebase the local zIndices + if (z) { + z.onComponentUpdate(this); + } + }, + /** + * Brings this floating Component to the front of any other visible, floating Components managed by the same + * {@link Ext.ZIndexManager ZIndexManager} + * + * If this Component is modal, inserts the modal mask just below this Component in the z-index stack. + * + * @param {Boolean} [preventFocus=false] Specify `true` to prevent the Component from being focused. + * @return {Ext.Component} this + */ + toFront: function(preventFocus) { + var me = this; + // ZIndexManager#onCollectionSort will call setActive if this component ends up on the top. + // That will focus it if we have been requested to do so. + if (me.zIndexManager.bringToFront(me, preventFocus || !me.focusOnToFront)) { + if (me.hasListeners.tofront) { + me.fireEvent('tofront', me, me.el.getZIndex()); + } + } + return me; + }, + /** + * @private + * This method is called internally by {@link Ext.ZIndexManager} to signal that a floating Component has either been + * moved to the top of its zIndex stack, or pushed from the top of its zIndex stack. + * + * If a _Window_ is superceded by another Window, deactivating it hides its shadow. + * + * This method also fires the {@link Ext.Component#activate activate} or + * {@link Ext.Component#deactivate deactivate} event depending on which action occurred. + * + * @param {Boolean} [isTopMost=false] True to activate the Component, false to deactivate it. + */ + onZIndexChange: function(isTopMost) { + var me = this; + if (isTopMost) { + // Check the element's visible state. Might be clipped to hide but + // be accessible. Do not show a shadow. + if (me.el.shadow && me.el.getData().isVisible !== false && !me.maximized) { + me.el.enableShadow(null, true); + } + me.fireEvent('activate', me); + } else // Deactivate carries no operations. It may be that this component has just moved down and another + // component has been brought to the top, so that will automatically receive focus. + // If we have been hidden, Component#onHide handles reverting focus to the previousExternalFocus element. + { + me.fireEvent('deactivate', me); + } + }, + /** + * @private + * This method is called internally by {@link Ext.ZIndexManager} to signal that a + * focusable floating Component has become the topost focusable in its zIndex stack. + */ + onFocusTopmost: function() { + var activeCmp = Ext.ComponentManager.getActiveComponent(); + // Skip focusing if we already contain focused element + if (!activeCmp || !activeCmp.up(this)) { + this.focus(); + } + }, + /** + * Sends this Component to the back of (lower z-index than) any other visible windows + * @return {Ext.Component} this + */ + toBack: function() { + this.zIndexManager.sendToBack(this); + return this; + }, + /** + * Center this Component in its container. + * @return {Ext.Component} this + */ + center: function() { + var me = this, + parent = me.floatParent, + xy; + if (me.isVisible()) { + xy = me.getAlignToXY(parent ? parent.getTargetEl() : me.container, 'c-c'); + me.setPagePosition(xy); + } else { + me.needsCenter = true; + } + return me; + }, + onFloatShow: function() { + var me = this, + target = me._lastAlignTarget; + if (me.needsCenter) { + me.center(); + } else if (target) { + if (target.destroyed) { + me._lastAlignTarget = null; + } else { + // Anchor to the target. Do not track scroll if we are position:fixed + me.alignTo(target, me._lastAlignToPos, me._lastAlignToOffsets, false, !me.fixed); + } + } + me.needsCenter = false; + }, + /** + * @private + */ + fitContainer: function(animate) { + var me = this, + parent = me.floatParent, + container = parent ? parent.getTargetEl() : me.container, + newBox = container.getViewSize(), + newPosition = parent || (container.dom !== document.body) ? // If we are a contained floater, or rendered to a div, maximized position is (0,0) + [ + 0, + 0 + ] : // If no parent and rendered to body, align with origin of container el. + container.getXY(); + newBox.x = newPosition[0]; + newBox.y = newPosition[1]; + me.setBox(newBox, animate); + }, + privates: { + onFloatDestroy: function() { + var me = this, + fly = me.alignTargetFly; + if (me.hierarchyEventListeners) { + me.hierarchyEventListeners.destroy(); + me.hierarchyEventListeners = null; + } + me.clearAlignEl(); + if (fly) { + // We only want to destroy the instance, but leave the element intact + fly.detach(); + fly.destroy(); + } + }, + /** + * Gets the topmost *non floating* alignTo target if there are multiple aligns + * such as a menu stack hanging off a button or grid column header. + * @return {Ext.Element/Ext.Component} The topmost, *non floating* alignTo target. + * @private + */ + getTopAlignTarget: function() { + var next = this._lastAlignTarget, + result = next; + // Track up through aligned floaters until we hit a root element or non-floater. + while (next && (result = next) && next.isComponent) { + // If we hit a floater, try its alignTarget next + if (result.isFloating()) { + next = result._lastAlignTarget; + } else // If a static component, see if it's owned by a floater and try its alignTarget if so. + { + next = result.up('{isFloating()}'); + next = next && next._lastAlignTarget; + } + } + return result; + }, + clearAlignEl: function() { + var me = this; + if (me._lastAlignTarget) { + me.alignListeners = Ext.destroy(me.alignListeners); + Ext.un('scroll', me.doRealign, me); + me._lastAlignToPos = me._lastAlignTarget = me._lastAlignToOffsets = me._topAlignTarget = null; + } + }, + alignOnResize: function() { + this.doRealign(); + }, + doRealign: function(scroller) { + var me = this, + alignEl = me._lastAlignTarget.el, + destroyed, dom, anchorXY, myXY; + // Only react if we are visible. + // onFloatShow realigns upon show. + if (alignEl && me.isVisible()) { + // Ensure we always have an Ext.Element as our alignEl. + // We may be aligned to a Component, an Ext.Element, or an raw HtmlElement + if (alignEl.isComponent) { + destroyed = alignEl.destroyed; + } else { + dom = alignEl.dom; + destroyed = !dom || Ext.isGarbage(dom); + } + // If the Component/Element we were aligning to is destroyed, clear our alignment. + if (destroyed) { + me.clearAlignEl(); + } + // Realign only if + // the topmost align target is within the scrolling element (it has scrolled with the content) + // AND our element is NOT within the scrolled element (it would move with the scroll) + else if (!scroller || (scroller.getElement().contains(me._topAlignTarget.el) && !scroller.getElement().contains(me.el))) { + anchorXY = alignEl.getXY(); + myXY = [ + anchorXY[0] + me.alignVector[0], + anchorXY[1] + me.alignVector[1] + ]; + me.setXY(myXY); + // Clip to the boundaries of the scroller which is moving us + if (scroller) { + me.clipToScroller(scroller); + } + } + } + }, + /** + * Clips this floating element to the scrolling element in line with how + * its topmost anchoring element is clipped. + * @private + */ + clipToScroller: function(scroller) { + var me = this, + anchorBox = me._topAlignTarget.getBox(), + scrollerBox = scroller.getElement().getConstrainRegion(), + sides = 0; + // Clip this to match the clippig of the anchor target + if (anchorBox.top < scrollerBox.top) { + sides = 1; + } + if (anchorBox.right > scrollerBox.right) { + sides = sides | 2; + } + if (anchorBox.bottom > scrollerBox.bottom) { + sides = sides | 4; + } + if (anchorBox.left < scrollerBox.left) { + sides = sides | 8; + } + if (sides) { + me.clipTo(scrollerBox, sides); + } else { + me.clearClip(); + } + } + } +}); + +/** + * This mixin enables classes to declare relationships to child elements and provides the + * mechanics for acquiring the {@link Ext.dom.Element elements} and storing them on an object + * instance as properties. + * + * This class is used by {@link Ext.Component components} and {@link Ext.layout.container.Container container layouts} to + * manage their child elements. + * + * A typical component that uses these features might look something like this: + * + * Ext.define('Ext.ux.SomeComponent', { + * extend: 'Ext.Component', + * + * childEls: [ + * 'bodyEl' + * ], + * + * renderTpl: [ + * '
' + * ], + * + * // ... + * }); + * + * The `{@link #childEls}` config lists one or more relationships to child elements managed + * by the component. The items in this array can be objects that more fully specify the + * child. For example, the above could have used this instead to achieve the same result: + * + * childEls: [ + * { name: 'bodyEl', itemId: 'bodyEl' } + * ] + * + * + * Unlike a `renderTpl` where there is a single value for an instance, `childEls` are aggregated + * up the class hierarchy so that they are effectively inherited. In other words, if a + * class where to derive from `Ext.ux.SomeComponent` in the example above, it could also + * have a `childEls` property in the same way as `Ext.ux.SomeComponent`. + * + * Ext.define('Ext.ux.AnotherComponent', { + * extend: 'Ext.ux.SomeComponent', + * + * childEls: [ + * // 'bodyEl' is inherited + * 'innerEl' + * ], + * + * renderTpl: [ + * '
' + * '
' + * '
' + * ], + * + * // ... + * }); + * + * **IMPORTANT** + * The `renderTpl` contains both child elements and unites them in the desired markup, but + * the `childEls` only contains the new child element. The `data-ref` attribute must be + * rendered on to child elements that do not use `select` or `selectNode` options. This + * is done for performance reasons on IE8 where element lookup (even by id) is not very + * efficient. + * + * @private + */ +Ext.define('Ext.util.ElementContainer', { + mixinId: 'elementCt', + config: { + /** + * @cfg {Object/String[]/Object[]} childEls + * The canonical form of `childEls` is an object keyed by child's property name + * with values that are objects with the following properties. + * + * - `itemId` - The id to combine with the Component's id that is the id of the + * child element. + * - `id` - The id of the child element. + * - `leaf` - Set to `true` to ignore content when scanning for childEls. This + * should be set on things like the generated content for an `Ext.view.View`. + * - `select`: A selector that will be passed to {@link Ext.dom.Element#method-select}. + * - `selectNode`: A selector that will be passed to {@link Ext.dom.Element#method-selectNode}. + * + * For example: + * + * childEls: { + * button: true, + * buttonText: 'text', + * buttonImage: { + * itemId: 'image' + * } + * } + * + * The above is translated into the following complete form: + * + * childEls: { + * button: { + * name: 'button', + * itemId: 'button' + * }, + * buttonText: { + * name: 'buttonText', + * itemId: 'text' + * }, + * buttonImage: { + * name: 'buttonImage', + * itemId: 'image' + * } + * } + * + * The above can be provided as an array like so: + * + * childEls: [ + * 'button', + * { name: 'buttonText', itemId: 'text' }, + * { name: 'buttonImage', itemId: 'image' } + * } + * + * For example, a Component which renders a title and body text: + * + * @example + * Ext.create('Ext.Component', { + * renderTo: Ext.getBody(), + * renderTpl: [ + * '

{title}

', + * '

{msg}

', + * ], + * renderData: { + * title: "Error", + * msg: "Something went wrong" + * }, + * childEls: ["title"], + * listeners: { + * afterrender: function(cmp){ + * // After rendering the component will have a title property + * cmp.title.setStyle({color: "red"}); + * } + * } + * }); + * + * **Note:** `childEl`s in the {@link Ext.Component#cfg-renderTpl renderTpl} + * must be referenced in a **data-ref** attribute. Notice in the above example + * that the "title" `childEl` is set in the `renderTpl` using + * **data-ref="title"**. + * + * When using `select`, the property will be an instance of {@link Ext.CompositeElement}. + * In all other cases, the property will be an {@link Ext.dom.Element} or `null` + * if not found. + * + * Care should be taken when using `select` or `selectNode` to find child elements. + * The following issues should be considered: + * + * - Performance: using selectors can be 10x slower than id lookup. + * - Over-selecting: selectors are applied after the DOM elements for all children + * have been rendered, so selectors can match elements from child components + * (including nested versions of the same component) accidentally. + * + * This above issues are most important when using `select` since it returns multiple + * elements. + */ + childEls: { + $value: {}, + cached: true, + lazy: true, + merge: function(newValue, oldValue, target, mixinClass) { + var childEls = oldValue ? Ext.Object.chain(oldValue) : {}, + i, val; + // We'd use mergeSets except it assumes array elements are just names. + if (newValue instanceof Array) { + for (i = newValue.length; i--; ) { + val = newValue[i]; + if (!mixinClass || !(val in childEls)) { + if (typeof val === 'string') { + childEls[val] = { + name: val, + itemId: val + }; + } else { + childEls[val.name] = val; + } + } + } + } else if (newValue) { + if (newValue.constructor === Object) { + for (i in newValue) { + if (!mixinClass || !(i in childEls)) { + val = newValue[i]; + if (val === true) { + childEls[i] = { + itemId: i + }; + } else if (typeof val === 'string') { + childEls[i] = { + itemId: val + }; + } else { + childEls[i] = val; + if (!('itemId' in val)) { + val.itemId = i; + } + } + childEls[i].name = i; + } + } + } else { + if (!mixinClass || !(newValue in childEls)) { + childEls[newValue] = { + name: newValue, + itemId: newValue + }; + } + } + } + return childEls; + } + } + }, + destroy: function() { + var me = this, + childEls = me.getChildEls(), + child, childName; + for (childName in childEls) { + child = me[childName]; + if (child) { + if (child.destroy) { + child.component = null; + child.destroy(); + } + me[childName] = null; + } + } + }, + privates: { + /** + * Add a childEl specific to this instance. This must be called before render. + * @param childEl + * @private + * @since 6.0.0 + */ + addChildEl: function(childEl) { + var me = this, + childEls = me.getChildEls(); + if (!me.hasOwnProperty('childEls')) { + me.childEls = childEls = Ext.Object.chain(childEls); + } + if (typeof childEl === 'string') { + childEl = { + name: childEl, + itemId: childEl + }; + } + childEls[childEl.name] = childEl; + }, + /** + * Called after the mixin is applied. We need to see if `childEls` were used by + * the `targetClass` and apply them to the config. + * @param {Ext.Class} targetClass + * @private + */ + afterClassMixedIn: function(targetClass) { + // When we are mixed in the targetClass may already have specified childEls, + // so check the prototype for any... + var proto = targetClass.prototype, + childEls = proto.childEls; + if (childEls) { + delete proto.childEls; + targetClass.getConfigurator().add({ + childEls: childEls + }); + } + }, + /** + * Sets references to elements inside the component. + * @private + */ + attachChildEls: function(el, owner) { + var me = this, + childEls = me.getChildEls(), + comp = owner || me, + // fyi - we are also used by layouts + baseId = comp.id + '-', + unframed = !comp.frame, + childName, elements, entry, k, selector, value, id; + for (childName in childEls) { + // hasOwnProperty is a no-go here since we use prototype chains... + entry = childEls[childName]; + if (unframed && entry.frame) { + + continue; + } + selector = entry.select; + if (selector) { + value = el.select(selector, true); + } + // a CompositeElement + else if (!(selector = entry.selectNode)) { + if (!(id = entry.id)) { + // With a normal childEl we want to rely on data-ref to populate + // the cache and *not* use getById since that should never find + // anything we don't already know about. + id = baseId + entry.itemId; + value = Ext.cache[id]; + } else // || el.getById(id); + { + // With a specified id we may not be so lucky, so check the cache + // first but then fallback to getById. + value = Ext.cache[id] || el.getById(id); + } + } else { + value = el.selectNode(selector, false); + } + if (value) { + if (value.isElement) { + value.component = comp; + } else if (value.isComposite && !value.isLite) { + elements = value.elements; + for (k = elements.length; k--; ) { + elements[k].component = comp; + } + } + } + me[childName] = value || null; + } + } + } +}); + +/** + * Given a component hierarchy of this: + * + * { + * xtype: 'panel', + * id: 'ContainerA', + * layout: 'hbox', + * renderTo: Ext.getBody(), + * items: [ + * { + * id: 'ContainerB', + * xtype: 'container', + * items: [ + * { id: 'ComponentA' } + * ] + * } + * ] + * } + * + * The rendering of the above proceeds roughly like this: + * + * - ContainerA's initComponent calls #render passing the `renderTo` property as the + * container argument. + * - `render` calls the `getRenderTree` method to get a complete {@link Ext.dom.Helper} spec. + * - `getRenderTree` fires the "beforerender" event and calls the #beforeRender + * method. Its result is obtained by calling #getElConfig. + * - The #getElConfig method uses the `renderTpl` and its render data as the content + * of the `autoEl` described element. + * - The result of `getRenderTree` is passed to {@link Ext.dom.Helper#append}. + * - The `renderTpl` contains calls to render things like docked items, container items + * and raw markup (such as the `html` or `tpl` config properties). These calls are to + * methods added to the {@link Ext.XTemplate} instance by #setupRenderTpl. + * - The #setupRenderTpl method adds methods such as `renderItems`, `renderContent`, etc. + * to the template. These are directed to "doRenderItems", "doRenderContent" etc.. + * - The #setupRenderTpl calls traverse from components to their {@link Ext.layout.Layout} + * object. + * - When a container is rendered, it also has a `renderTpl`. This is processed when the + * `renderContainer` method is called in the component's `renderTpl`. This call goes to + * Ext.layout.container.Container#doRenderContainer. This method repeats this + * process for all components in the container. + * - After the top-most component's markup is generated and placed in to the DOM, the next + * step is to link elements to their components and finish calling the component methods + * `onRender` and `afterRender` as well as fire the corresponding events. + * - The first step in this is to call #finishRender. This method descends the + * component hierarchy and calls `onRender` and fires the `render` event. These calls + * are delivered top-down to approximate the timing of these calls/events from previous + * versions. + * - During the pass, the component's `el` is set. Likewise, the `renderSelectors` and + * `childEls` are applied to capture references to the component's elements. + * - These calls are also made on the {@link Ext.layout.container.Container} layout to + * capture its elements. Both of these classes use {@link Ext.util.ElementContainer} to + * handle `childEls` processing. + * + * @private + */ +Ext.define('Ext.util.Renderable', { + mixinId: 'renderable', + requires: [ + 'Ext.dom.Element' + ], + frameCls: Ext.baseCSSPrefix + 'frame', + frameIdRegex: /[\-]frame\d+[TMB][LCR]$/, + frameElNames: [ + 'TL', + 'TC', + 'TR', + 'ML', + 'MC', + 'MR', + 'BL', + 'BC', + 'BR', + 'Table' + ], + frameTpl: [ + '{% this.renderTabGuard(out, values, \'before\'); %}', + '', + '
{parent.baseCls}-{parent.ui}-{.}-tl{frameElCls}" role="presentation">', + '
{parent.baseCls}-{parent.ui}-{.}-tr{frameElCls}" role="presentation">', + '
{parent.baseCls}-{parent.ui}-{.}-tc{frameElCls}" role="presentation">
', + '
', + '
', + '
', + '
{parent.baseCls}-{parent.ui}-{.}-ml{frameElCls}" role="presentation">', + '
{parent.baseCls}-{parent.ui}-{.}-mr{frameElCls}" role="presentation">', + '
{parent.baseCls}-{parent.ui}-{.}-mc{frameElCls}" role="presentation">', + '{%this.applyRenderTpl(out, values)%}', + '
', + '
', + '
', + '', + '
{parent.baseCls}-{parent.ui}-{.}-bl{frameElCls}" role="presentation">', + '
{parent.baseCls}-{parent.ui}-{.}-br{frameElCls}" role="presentation">', + '
{parent.baseCls}-{parent.ui}-{.}-bc{frameElCls}" role="presentation">
', + '
', + '
', + '
', + '{% this.renderTabGuard(out, values, \'after\'); %}' + ], + frameTableTpl: [ + '{% this.renderTabGuard(out, values, \'before\'); %}', + '
', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '', + '{% this.renderTabGuard(out, values, \'after\'); %}' + ], + /** + * @property {Number} _renderState + * This property holds one of the following values during the render process: + * + * * **0** - The component is not rendered. + * * **1** - The component has fired beforerender and is about to call beforeRender. + * The component has just started rendering. + * * **2** - The component has finished the `beforeRender` process and is about to + * call `onRender`. This is when `rendering` is set to `true`. + * * **3** - The component has started `onRender`. This is when `rendered` is set + * to `true`. + * * **4** - The component has finished its afterrender process. + * + * @private + * @readonly + * @since 5.0.0 + */ + _renderState: 0, + _layerCls: Ext.baseCSSPrefix + 'layer', + _fixedLayerCls: Ext.baseCSSPrefix + 'fixed-layer', + // Some components will have such roles that do not actively participate + // in user interaction, and thus do not need their ARIA attributes updated + ariaStaticRoles: { + presentation: true, + article: true, + definition: true, + directory: true, + document: true, + img: true, + heading: true, + math: true, + note: true, + banner: true, + complementary: true, + contentinfo: true, + navigation: true, + search: true, + // When a role is not defined it is akin to static + 'undefined': true, + 'null': true + }, + statics: { + makeRenderSetter: function(cfg, renderState) { + var name = cfg.name; + return function(value) { + var me = this, + bucket = (me.renderConfigs || (me.renderConfigs = {})), + pending = bucket[renderState]; + if (me._renderState >= renderState) { + (cfg.setter || cfg.getSetter()).call(me, value); + } else { + if (!pending) { + bucket[renderState] = pending = {}; + } + if (!(name in pending)) { + pending[name] = me[name]; + } + me[name] = value; + } + return me; + }; + }, + processRenderConfig: function(source, configName, state) { + // Even though this is not inheritableState, our onClassExtended adds it to + // all derived classes so that our "this" pointer is the derived class. + var proto = this.prototype, + configurator = this.getConfigurator(), + Renderable = Ext.util.Renderable, + makeSetter = Renderable.makeRenderSetter, + renderConfig = source[configName], + cachedSetter, cfg, name, setterName; + for (name in renderConfig) { + cfg = Ext.Config.get(name); + if (!proto[setterName = cfg.names.set]) { + cachedSetter = (cfg.renderSetter || (cfg.renderSetter = {})); + proto[setterName] = cachedSetter[state] || (cachedSetter[state] = makeSetter(cfg, state)); + } + } + delete source[configName]; + configurator.add(renderConfig); + } + }, + onClassMixedIn: function(targetClass) { + var override = targetClass.override, + processRenderConfig = this.processRenderConfig, + processOverride = function(body) { + if (body.beforeRenderConfig) { + this.processRenderConfig(body, 'beforeRenderConfig', 1); + } + if (body.renderConfig) { + this.processRenderConfig(body, 'renderConfig', 3); + } + override.call(this, body); + }, + processClass = function(theClass, classBody) { + // We need to process overrides for renderConfig declarations: + theClass.override = processOverride; + // While we are here we add this method (an inheritableStatic basically) + theClass.processRenderConfig = processRenderConfig; + if (classBody.beforeRenderConfig) { + theClass.processRenderConfig(classBody, 'beforeRenderConfig', 1); + } + if (classBody.renderConfig) { + theClass.processRenderConfig(classBody, 'renderConfig', 3); + } + }; + // Process Component itself. + processClass(targetClass, targetClass.prototype); + // And apply to all Component-derived classes as well: + targetClass.onExtended(processClass); + }, + /** + * Allows additional behavior after rendering is complete. At this stage, the + * {@link Ext.Component Component's} {@link Ext.Component#getEl Element} will have + * been styled according to the configuration, will have had any configured CSS + * class names added, and will be in the configured visibility and configured enable + * state. + * + * **Note:** If the Component has a {@link Ext.Component#controller ViewController} + * and the controller has an {@link Ext.app.ViewController#afterRender afterRender} + * method it will be called passing the Component as the single param. + * + * @template + * @protected + */ + afterRender: function() { + var me = this, + data = {}, + protoEl = me.protoEl, + target = me.el, + controller, item, pre, hidden, contentEl; + me.finishRenderChildren(); + me._renderState = 4; + // We need to do the contentEl here because it depends on the layout items (inner/outerCt) + // to be rendered before we can put it in + if (me.contentEl) { + pre = Ext.baseCSSPrefix; + hidden = pre + 'hidden-'; + contentEl = me.contentEl = Ext.get(me.contentEl); + contentEl.component = me; + contentEl.removeCls([ + pre + 'hidden', + hidden + 'display', + hidden + 'offsets' + ]); + me.getContentTarget().appendChild(contentEl.dom); + } + protoEl.writeTo(data); + // Here we apply any styles that were set on the protoEl during the rendering phase + // A majority of times this will not happen, but we still need to handle it + item = data.removed; + if (item) { + target.removeCls(item); + } + item = data.cls; + if (item.length) { + target.addCls(item); + } + item = data.style; + if (data.style) { + target.setStyle(item); + } + me.protoEl = null; + // If this is the outermost Container, lay it out as soon as it is rendered. + // Some Components like Ext.LoadMask will lay out themselves and some like + // Ext.dd.StatusProxy will even render themselves to a detached document body, + // so we allow them to opt out of the Ext layouts. + if (!me.ownerCt && !me.skipLayout) { + me.updateLayout(); + } + if (!(me.x && me.y) && (me.pageX || me.pageY)) { + me.setPagePosition(me.pageX, me.pageY); + } + if (me.disableOnRender) { + me.onDisable(); + } + controller = me.controller; + if (controller && controller.afterRender) { + controller.afterRender(me); + } + if (me.focusableContainer && me.initFocusableContainer) { + me.initFocusableContainer(); + } + }, + afterFirstLayout: function(width, height) { + var me = this, + x = me.x, + y = me.y, + alignSpec = me.defaultAlign, + alignOffset = me.alignOffset, + controller, hasX, hasY, pos, xy; + // We only have to set absolute position here if there is no ownerlayout which should take responsibility. + // Consider the example of rendered components outside of a viewport - these might need their positions setting. + if (!me.ownerLayout) { + hasX = x !== undefined; + hasY = y !== undefined; + } + // For floaters, calculate x and y if they aren't defined by aligning + // the sized element to the center of either the container or the ownerCt + if (me.floating && !me.preventDefaultAlign && (!hasX || !hasY)) { + if (me.floatParent) { + pos = me.floatParent.getTargetEl().getViewRegion(); + xy = me.el.getAlignToXY(me.alignTarget || me.floatParent.getTargetEl(), alignSpec, alignOffset); + pos.x = xy[0] - pos.x; + pos.y = xy[1] - pos.y; + } else { + xy = me.el.getAlignToXY(me.alignTarget || me.container, alignSpec, alignOffset); + pos = me.el.translateXY(xy[0], xy[1]); + } + x = hasX ? x : pos.x; + y = hasY ? y : pos.y; + hasX = hasY = true; + } + if (hasX || hasY) { + me.setPosition(x, y); + } + me.onBoxReady(width, height); + controller = me.controller; + if (controller && controller.boxReady) { + controller.boxReady(me, width, height); + } + }, + /** + * Allows additional behavior before rendering. + * + * **Note:** If the Component has a {@link Ext.Component#controller ViewController} + * and the controller has a {@link Ext.app.ViewController#beforeRender beforeRender} + * method it will be called passing the Component as the single param. + * + * @template + * @protected + */ + beforeRender: function() { + var me = this, + floating = me.floating, + layout = me.getComponentLayout(), + cls = me.userCls, + controller; + me._renderState = 1; + me.ariaUsesMainElement = me.ariaEl === 'el'; + controller = me.controller; + if (controller && controller.beforeRender) { + controller.beforeRender(me); + } + // Force bindings to be created + me.initBindable(); + if (me.renderConfigs) { + me.flushRenderConfigs(); + } + if (cls) { + me.addCls(cls); + } + if (floating) { + me.addCls(me.fixed ? me._fixedLayerCls : me._layerCls); + cls = floating.cls; + if (cls) { + me.addCls(cls); + } + } + // Just before rendering, set the frame flag if we are an always-framed component like Window or Tip. + me.frame = me.frame || me.alwaysFramed; + if (!layout.initialized) { + layout.initLayout(); + } + // Attempt to set overflow style prior to render if the targetEl can be accessed. + // If the targetEl does not exist yet, this will take place in finishRender + me.initOverflow(); + me.setUI(me.ui); + }, + /** + * @private + * Called from the selected frame generation template to insert this Component's inner structure inside the framing structure. + * + * When framing is used, a selected frame generation template is used as the primary template of the #getElConfig instead + * of the configured {@link Ext.Component#renderTpl renderTpl}. The renderTpl is invoked by this method which is injected into the framing template. + */ + doApplyRenderTpl: function(out, values) { + // Careful! This method is bolted on to the frameTpl so all we get for context is + // the renderData! The "this" pointer is the frameTpl instance! + var me = values.$comp, + tpl; + // Don't do this if the component is already rendered: + if (!me.rendered) { + tpl = me.initRenderTpl(); + tpl.applyOut(values.renderData, out); + } + }, + getElConfig: function() { + var me = this, + autoEl = me.autoEl, + frameInfo = me.getFrameInfo(), + config = { + tag: 'div', + tpl: frameInfo ? me.initFramingTpl(frameInfo.table) : me.initRenderTpl() + }, + layoutTargetCls = me.layoutTargetCls, + protoEl = me.protoEl, + ariaRole = me.ariaRole, + frameData; + me.initStyles(protoEl); + // If we're not framing, then just add to the element, otherwise we need to add + // it to the frameBody, since it's our targetEl, but we don't have a handle on it yet. + if (layoutTargetCls && !frameInfo) { + protoEl.addCls(layoutTargetCls); + } + protoEl.writeTo(config); + protoEl.flush(); + if (autoEl) { + if (Ext.isString(autoEl)) { + config.tag = autoEl; + } else { + Ext.apply(config, autoEl); + } + } + if (ariaRole && me.ariaUsesMainElement) { + config.role = ariaRole; + if (!me.ariaStaticRoles[ariaRole]) { + config['aria-hidden'] = !!me.hidden; + config['aria-disabled'] = !!me.disabled; + // ariaLabelledBy takes precedence + if (me.ariaLabel && !me.ariaLabelledBy) { + config['aria-label'] = me.ariaLabel; + } + // We don't want to handle collapsibleness in subclasses + if (me.collapsible) { + config['aria-expanded'] = !me.collapsed; + } + // In some cases we need to force some ARIA attributes + // to be rendered on the ariaEl upfront, e.g. certain + // state and decorator attributes. It is not semantically + // correct to set these in ariaAttributes config, so + // we're using ariaRenderAttributes instance config + // when available. + if (me.ariaRenderAttributes) { + Ext.apply(config, me.ariaRenderAttributes); + } + if (me.config.ariaAttributes) { + Ext.apply(config, me.getAriaAttributes()); + } + } + } + // It's important to assign the id here as an autoEl.id could have been (wrongly) applied and this would get things out of sync + config.id = me.id; + if (config.tpl) { + // Use the framingTpl as the main content creating template. It will call out to this.applyRenderTpl(out, values) + if (frameInfo) { + config.tplData = frameData = me.getFrameRenderData(); + frameData.renderData = me.initRenderData(); + } else { + config.tplData = me.initRenderData(); + } + } + // After we have gathered all rendering information, this is no longer needed. + me.ariaRenderAttributes = null; + return config; + }, + /** + * This function takes the position argument passed to onRender and returns a + * DOM element that you can use in the insertBefore. + * @param {String/Number/Ext.dom.Element/HTMLElement} position Index, element id or element you want + * to put this component before. + * @return {HTMLElement} DOM element that you can use in the insertBefore + */ + getInsertPosition: function(position) { + // Convert the position to an element to insert before + if (position !== undefined) { + if (Ext.isNumber(position)) { + position = this.container.dom.childNodes[position]; + } else { + position = Ext.getDom(position); + } + } + return position; + }, + getRenderTree: function() { + var me = this, + ret = null; + if (!me.hasListeners.beforerender || me.fireEvent('beforerender', me) !== false) { + me._renderState = 1; + me.beforeRender(); + // Flag to let the layout's finishRenderItems and afterFinishRenderItems + // know which items to process + me.rendering = true; + me._renderState = 2; + ret = me.getElConfig(); + if (me.el) { + // Since we are producing a render tree, we produce a "proxy el" that will + // sit in the rendered DOM precisely where me.el belongs. We replace the + // proxy el in the finishRender phase. + ret.id = me.$pid = Ext.id(null, me.el.identifiablePrefix); + } + } + //ret['data-cmp'] = me.id; + return ret; + }, + /** + * Initialized the renderData to be used when rendering the renderTpl. + * @return {Object} Object with keys and values that are going to be applied to the renderTpl + * @protected + */ + initRenderData: function() { + var me = this, + ariaRole = me.ariaRole, + data, ariaAttr; + data = Ext.apply({ + $comp: me, + id: me.id, + ui: me.ui, + uiCls: me.uiCls, + baseCls: me.baseCls, + componentCls: me.componentCls, + frame: me.frame, + hasTabGuard: !!me.tabGuard, + scrollerCls: me.scrollerCls, + childElCls: '', + // overridden in RTL + ariaEl: me.ariaEl + }, me.renderData); + // This code is similar (in fact, almost identical) to the one in getElConfig; + // we duplicate it for performance reasons. + if (ariaRole && !me.ariaUsesMainElement) { + ariaAttr = { + role: ariaRole + }; + if (!me.ariaStaticRoles[ariaRole]) { + ariaAttr['aria-hidden'] = !!me.hidden; + ariaAttr['aria-disabled'] = !!me.disabled; + // ariaLabelledBy takes precedence + if (me.ariaLabel && !me.ariaLabelledBy) { + ariaAttr['aria-label'] = me.ariaLabel; + } + // We don't want to handle collapsibleness in subclasses + if (me.collapsible) { + ariaAttr['aria-expanded'] = !me.collapsed; + } + if (me.ariaRenderAttributes) { + Ext.apply(ariaAttr, me.ariaRenderAttributes); + } + if (me.config.ariaAttributes) { + Ext.apply(ariaAttr, me.getAriaAttributes()); + } + } + data.ariaAttributes = ariaAttr; + } + return data; + }, + /** + * Template method called when this Component's DOM structure is created. + * + * At this point, this Component's (and all descendants') DOM structure *exists* but it has not + * been layed out (positioned and sized). + * + * Subclasses which override this to gain access to the structure at render time should + * call the parent class's method before attempting to access any child elements of the Component. + * + * @param {Ext.dom.Element} parentNode The parent Element in which this Component's encapsulating element is contained. + * @param {Number} containerIdx The index within the parent Container's child collection of this Component. + * + * @template + * @protected + */ + onRender: function(parentNode, containerIdx) { + var me = this, + x = me.x, + y = me.y, + lastBox = null, + el = me.el, + scroller = me.scrollable, + width, height; + me.applyRenderSelectors(); + // Update the scroller very early in first layout so that it has the overflow element + // before any 'boxready', onResize, or 'resize' code gets to run. + if (scroller && scroller.isScroller) { + scroller.setElement(me.getOverflowEl()); + // IE browsers don't restore scroll position if the component was scrolled and + // then hidden and shown again, so we must do it manually. + // See EXTJS-16233. + if (Ext.isIE) { + me.showListenerIE = Ext.on('show', me.onGlobalShow, me, { + destroyable: true + }); + } + } + // Flag set on getRenderTree to flag to the layout's postprocessing routine that + // the Component is in the process of being rendered and needs postprocessing. + me.rendering = null; + me.rendered = true; + me._renderState = 3; + if (me.renderConfigs) { + me.flushRenderConfigs(); + } + // We need to remember these to avoid writing them during the initial layout: + if (x != null) { + lastBox = { + x: x + }; + } + if (y != null) { + (lastBox = lastBox || {}).y = y; + } + // Framed components need their width/height to apply to the frame, which is + // best handled in layout at present. + if (!me.getFrameInfo()) { + width = me.width; + height = me.height; + if (typeof width === 'number') { + lastBox = lastBox || {}; + lastBox.width = width; + } + if (typeof height === 'number') { + lastBox = lastBox || {}; + lastBox.height = height; + } + } + me.lastBox = el.lastBox = lastBox; + }, + /** + * Renders the Component into the passed HTML element. + * + * **If you are using a {@link Ext.container.Container Container} object to house this + * Component, then do not use the render method.** + * + * A Container's child Components are rendered by that Container's + * {@link Ext.container.Container#layout layout} manager when the Container is first rendered. + * + * When creating complex UIs, it is important to remember that sizing and positioning + * of child items is the responsibility of the Container's {@link Ext.container.Container#layout layout} + * manager. If you expect child items to be sized in response to user interactions, you must + * configure the Container with a layout manager which creates and manages the type of layout you + * have in mind. + * + * **Omitting the Container's {@link Ext.Container#layout layout} config means that a basic + * layout manager is used which does nothing but render child components sequentially into the + * Container. No sizing or positioning will be performed in this situation.** + * + * @param {Ext.dom.Element/HTMLElement/String} [container] The element this Component should be + * rendered into. If it is being created from existing markup, this should be omitted. + * @param {String/Number} [position] The element ID or DOM node index within the container **before** + * which this component will be inserted (defaults to appending to the end of the container) + */ + render: function(container, position) { + var me = this, + el = me.el, + ownerLayout = me.ownerLayout, + vetoed, tree, nextSibling; + if (el && !el.isElement) { + me.wrapPrimaryEl(el); + // ensure me.el is wrapped + el = me.el; + } + if (!me.skipLayout) { + Ext.suspendLayouts(); + } + container = me.initContainer(container); + nextSibling = me.getInsertPosition(position); + if (!el) { + tree = me.getRenderTree(); + // calls beforeRender + if (ownerLayout && ownerLayout.transformItemRenderTree) { + tree = ownerLayout.transformItemRenderTree(tree); + } + // tree will be null if a beforerender listener returns false + if (tree) { + if (nextSibling) { + el = Ext.DomHelper.insertBefore(nextSibling, tree); + } else { + el = Ext.DomHelper.append(container, tree); + } + me.wrapPrimaryEl(el); + // Just rendered a bunch of stuff so fill up the cache with those els we + // will need. + me.cacheRefEls(el); + } + } else { + if (!me.hasListeners.beforerender || me.fireEvent('beforerender', me) !== false) { + me.beforeRender(); + // We're simulating the above block here as much as possible, but we're already + // given an el, so we don't need to create it. We still need to initialize the renderTpl later. + me.needsRenderTpl = me.rendering = true; + me._renderState = 2; + // Set configured styles on pre-rendered Component's element + me.initStyles(el); + if (me.allowDomMove !== false) { + if (nextSibling) { + container.dom.insertBefore(el.dom, nextSibling); + } else { + container.dom.appendChild(el.dom); + } + } + } else { + vetoed = true; + } + } + if (el && !vetoed) { + me.finishRender(position); + } + if (!me.skipLayout) { + Ext.resumeLayouts(!me.hidden && !container.isDetachedBody); + } + }, + /** + * Ensures that this component is attached to `document.body`. If the component was + * rendered to {@link Ext#getDetachedBody}, then it will be appended to `document.body`. + * Any configured position is also restored. + * @param {Boolean} [runLayout=false] True to run the component's layout. + */ + ensureAttachedToBody: function(runLayout) { + var comp = this, + body; + while (comp.ownerCt) { + comp = comp.ownerCt; + } + if (comp.container.isDetachedBody) { + comp.container = body = Ext.getBody(); + body.appendChild(comp.el.dom); + if (runLayout) { + comp.updateLayout(); + } + if (typeof comp.x === 'number' || typeof comp.y === 'number') { + comp.setPosition(comp.x, comp.y); + } + } + }, + //========================================================================= + privates: { + /** + * Sets references to elements inside the component. This applies {@link Ext.Component#cfg-renderSelectors renderSelectors} + * as well as {@link Ext.Component#cfg-childEls childEls}. + * @private + */ + applyRenderSelectors: function() { + var me = this, + selectors = me.renderSelectors, + el = me.el, + query, selector; + me.attachChildEls(el); + // Cache focusEl as a property for speedier lookups + if (typeof me.focusEl === 'string') { + me.focusEl = me[me.focusEl]; + } + // For the majority of Components, their ariaEl is going to be their main el. + me.ariaEl = me[me.ariaEl] || me.el; + // We still support renderSelectors. There are a few places in the framework that + // need them and they are a documented part of the API. In fact, we support mixing + // childEls and renderSelectors (no reason not to). + if (selectors) { + for (selector in selectors) { + query = selectors[selector]; + if (query) { + me[selector] = el.selectNode(query, false); + } + } + } + }, + /** + * Ensures that all elements with "data-ref" attributes get loaded into the cache. + * This really helps on IE8 where `getElementById` is a search not a lookup. By + * populating our cache with one search of the DOM we then have random access to + * the elements as we do our `childEls` wire up. + * @private + */ + cacheRefEls: function(el) { + el = el || this.el; + var cache = Ext.cache, + El = Ext.dom.Element, + dom = el.isElement ? el.dom : el, + refs = dom.querySelectorAll('[data-ref]'), + len = refs.length, + ref, i; + for (i = 0; i < len; i++) { + ref = refs[i]; + if (!cache[ref.id]) { + new El(ref); + } + } + }, + // jshint ignore:line + /** + * Handles autoRender. + * Floating Components may have an ownerCt. If they are asking to be constrained, constrain them within that + * ownerCt, and have their z-index managed locally. Floating Components are always rendered to document.body + * @private + */ + doAutoRender: function() { + var me = this; + if (!me.rendered) { + if (me.floating) { + me.render(me.renderTo || document.body); + } else { + me.render(Ext.isBoolean(me.autoRender) ? Ext.getBody() : me.autoRender); + } + } + }, + doRenderContent: function(out, renderData) { + // Careful! This method is bolted on to the renderTpl so all we get for context is + // the renderData! The "this" pointer is the renderTpl instance! + var me = renderData.$comp, + data = me.data; + if (me.html) { + Ext.DomHelper.generateMarkup(me.html, out); + delete me.html; + } + if (me.tpl) { + // Make sure this.tpl is an instantiated XTemplate + if (!me.tpl.isTemplate) { + me.tpl = new Ext.XTemplate(me.tpl); + } + if (data) { + me.data = data = data.isEntity ? data.getData(true) : data; + //me.tpl[me.tplWriteMode](target, me.data); + me.tpl.applyOut(data, out); + } + } + }, + doRenderFramingTabGuard: function(out, renderData, position) { + // Careful! This method is bolted on to the frameTpl so all we get for context is + // the renderData! The "this" pointer is the frameTpl instance! + // Container layout implements doRenderTabGuard(), *not* Component itself! + var layout = renderData.$comp.layout; + // The "renderData" property is placed in scope for the renderTpl, but we don't + // want to render tab guards at that level in addition to the framing level: + renderData.renderData.$skipTabGuards = true; + if (layout && layout.doRenderTabGuard) { + layout.doRenderTabGuard.call(this, out, renderData, position); + } + }, + flushRenderConfigs: function() { + var me = this, + configs = me.renderConfigs, + state = me._renderState, + bucket, i, name, newConfigs, value; + if (configs) { + for (i = 0; i <= state; ++i) { + bucket = configs[i]; + if (bucket) { + configs[i] = null; + for (name in bucket) { + value = bucket[name]; + (newConfigs || (newConfigs = {}))[name] = me[name]; + me[name] = value; + } + } + } + if (newConfigs) { + me.setConfig(newConfigs); + } + } + }, + /** + * This method visits the rendered component tree in a "top-down" order. That is, this + * code runs on a parent component before running on a child. This method calls the + * {@link #onRender} method of each component. + * @param {Number} containerIdx The index into the Container items of this Component. + * + * @private + */ + finishRender: function(containerIdx) { + var me = this, + cache = Ext.cache, + // our element cache + proxy, first, id, tpl, data, dom, el; + // We are typically called w/me.el==null as a child of some ownerCt that is being + // rendered. We are also called by render for a normal component (w/o a configured + // me.el). In this case, render sets me.el and me.rendering (indirectly). Lastly + // we are also called on a component (like a Viewport) that has a configured me.el + // (body for a Viewport) when render is called. In this case, it is not flagged as + // "me.rendering" yet because it does not produce a renderTree. We use this to know + // not to regen the renderTpl. + if (!me.el || me.$pid) { + if (me.container) { + el = cache[me.id]; + dom = el ? el.dom : me.container.getById(me.id, true); + } else { + id = me.$pid || me.id; + el = cache[id]; + dom = el ? el.dom : Ext.getDom(id); + } + if (!me.el) { + // Typical case: we produced the el during render + me.wrapPrimaryEl(dom); + } else { + // We were configured with an el and created a proxy, so now we can swap + // the proxy for me.el: + delete me.$pid; + if (!me.el.dom) { + // make sure me.el is an Element + me.wrapPrimaryEl(me.el); + } + // Insert the configured el before the proxy el: + dom.parentNode.insertBefore(me.el.dom, dom); + // We need to transplant rendered content from the proxy to the + // configured el. This would included the renderTpl of the component + // and its layout (innerCt's and such) as well as all child items. + // + proxy = dom; + // hold on to the rendered DOM + dom = me.el.dom; + // we'll be using the configured el though + first = dom.firstChild; + // rendered content in proxy goes first + while (proxy.firstChild) { + dom.insertBefore(proxy.firstChild, first); + } + // We need the classes rendered on to the proxy as well (things like + // "x-panel"): + me.el.addCls(proxy.className); + Ext.removeNode(proxy); + } + } + // now proxy can go + // TODO - what about style? + else if (me.needsRenderTpl) { + // We were configured with an el and then told to render (e.g., Viewport). We + // need to generate the proper DOM. Insert first because the layout system + // insists that child Component elements indices match the Component indices. + tpl = me.initRenderTpl(); + if (tpl) { + data = me.initRenderData(); + tpl.insertFirst(me.getTargetEl(), data); + } + // Just rendered a bunch of stuff so fill up the cache with those els we + // will need. + me.cacheRefEls(); + } + // else we are rendering + me.el.component = me; + if (!me.container) { + // top-level rendered components will already have me.container set up + me.container = Ext.get(me.el.dom.parentNode); + } + if (me.ctCls) { + me.container.addCls(me.ctCls); + } + // Sets the rendered flag and clears the rendering flag + me.onRender(me.container, containerIdx); + // If we could not access a target protoEl in beforeRender, we have to set the overflow styles here. + if (!me.overflowInited) { + me.initOverflow(); + } + // Tell the encapsulating element to hide itself in the way the Component is configured to hide + // This means DISPLAY, VISIBILITY or OFFSETS. + me.el.setVisibilityMode(Ext.Element[me.hideMode.toUpperCase()]); + if (me.overCls) { + me.el.hover(me.addOverCls, me.removeOverCls, me); + } + if (me.hasListeners.render) { + me.fireEvent('render', me); + } + me.afterRender(); + // this can cause a layout + if (me.hasListeners.afterrender) { + me.fireEvent('afterrender', me); + } + me.initEvents(); + if (me.hidden) { + // Hiding during the render process should not perform any ancillary + // actions that the full hide process does; It is not hiding, it begins in a hidden state.' + // So just make the element hidden according to the configured hideMode + me.el.hide(); + } + }, + finishRenderChildren: function() { + var layout = this.getComponentLayout(); + layout.finishRender(); + }, + getFrameRenderData: function() { + var me = this, + // we are only called if framing so this has already been determined: + frameInfo = me.frameSize, + mcStyle = ''; + if (me._syncFrameHeight && me.height) { + // Buttons need their frame's MC element to have an explicit height in order + // for percentage heights to work on elements inside the frame + mcStyle = 'height:' + (me.height - frameInfo.height) + 'px'; + } + return { + $comp: me, + id: me.id, + fgid: me.id + '-frame', + ui: me.ui, + uiCls: me.uiCls, + frameCls: me.frameCls, + frameBodyCls: me.layoutTargetCls || '', + baseCls: me.baseCls, + hasTabGuard: me.tabGuard, + top: !!frameInfo.top, + left: !!frameInfo.left, + right: !!frameInfo.right, + bottom: !!frameInfo.bottom, + mcStyle: mcStyle, + // can be optionally set by a subclass or override to be an extra class to + // be applied to all framing elements (used by RTL) + frameElCls: '' + }; + }, + /** + * @private + * On render, reads an encoded style attribute, "filter" from the style of this Component's element. + * This information is memoized based upon the CSS class name of this Component's element. + * Because child Components are rendered as textual HTML as part of the topmost Container, a dummy div is inserted + * into the document to receive the document element's CSS class name, and therefore style attributes. + */ + getFrameInfo: function() { + // If native framing can be used, or this component is not going to be framed, then do not attempt to read CSS framing info. + if (Ext.supports.CSS3BorderRadius || !this.frame) { + return false; + } + var me = this, + frameInfoCache = me.frameInfoCache, + cls = me.getFramingInfoCls() + '-frameInfo', + frameInfo = frameInfoCache[cls], + styleEl, info, frameTop, frameRight, frameBottom, frameLeft, borderTopWidth, borderRightWidth, borderBottomWidth, borderLeftWidth, paddingTop, paddingRight, paddingBottom, paddingLeft; + if (frameInfo == null) { + // Get the singleton frame style proxy with our el class name stamped into it. + styleEl = Ext.fly(me.getStyleProxy(cls), 'frame-style-el'); + info = styleEl.getStyle('font-family'); + info = info && info.split('-'); + if (info && info.length >= 5) { + // The framing data is encoded as + // + // D=div|T=table + // | H=horz|V=vert + // | | + // | | + // [DT][HV]-[T-R-B-L]-[T-R-B-L]-[T-R-B-L] + // / / | | \ \ + // / / | | \ \ + // / / / \ \ \ + // / / border-width \ \ + // frame-size padding + // + // The first 2 chars hold the div/table and horizontal/vertical flags. + // The 3 sets of TRBL 4-tuples are the CSS3 values for border-radius, + // border-width and padding, respectively. + // + frameTop = parseInt(info[1], 10); + frameRight = parseInt(info[2], 10); + frameBottom = parseInt(info[3], 10); + frameLeft = parseInt(info[4], 10); + borderTopWidth = parseInt(info[5], 10) || 0; + borderRightWidth = parseInt(info[6], 10) || 0; + borderBottomWidth = parseInt(info[7], 10) || 0; + borderLeftWidth = parseInt(info[8], 10) || 0; + paddingTop = parseInt(info[9], 10) || 0; + paddingRight = parseInt(info[10], 10) || 0; + paddingBottom = parseInt(info[11], 10) || 0; + paddingLeft = parseInt(info[12], 10) || 0; + frameInfo = { + table: info[0].charAt(0) === 't', + vertical: info[0].charAt(1) === 'v', + top: frameTop, + right: frameRight, + bottom: frameBottom, + left: frameLeft, + // Ext.layout.ContextItem needs width/height + width: frameLeft + frameRight, + height: frameTop + frameBottom, + border: { + top: borderTopWidth, + right: borderRightWidth, + bottom: borderBottomWidth, + left: borderLeftWidth, + width: borderLeftWidth + borderRightWidth, + height: borderTopWidth + borderBottomWidth + }, + padding: { + top: paddingTop, + right: paddingRight, + bottom: paddingBottom, + left: paddingLeft, + width: paddingLeft + paddingRight, + height: paddingTop + paddingBottom + } + }; + } else { + frameInfo = false; + } + // This happens when you set frame: true explicitly without using the x-frame mixin in sass. + // This way IE can't figure out what sizes to use and thus framing can't work. + if (me.frame === true && !frameInfo) { + Ext.log.error('You have set frame: true explicity on this component (' + me.getXType() + ') and it ' + 'does not have any framing defined in the CSS template. In this case IE cannot figure out ' + 'what sizes to use and thus framing on this component will be disabled.'); + } + frameInfoCache[cls] = frameInfo; + } + me.frame = !!frameInfo; + me.frameSize = frameInfo; + return frameInfo; + }, + getFramingInfoCls: function() { + return this.baseCls + '-' + this.ui; + }, + /** + * @private + * Returns an offscreen div with the same class name as the element this is being rendered. + * This is because child item rendering takes place in a detached div which, being not + * part of the document, has no styling. + */ + getStyleProxy: function(cls) { + var result = this.styleProxyEl || (Ext.Component.prototype.styleProxyEl = Ext.getBody().createChild({ + // tell the spec runner to ignore this element when checking if the dom is clean + 'data-sticky': true, + role: 'presentation', + style: { + position: 'absolute', + top: '-10000px' + } + }, null, true)); + result.className = cls; + return result; + }, + /** + * @private + */ + getFrameTpl: function(table) { + return this.lookupTpl(table ? 'frameTableTpl' : 'frameTpl'); + }, + initContainer: function(container) { + var me = this; + // If you render a component specifying the el, we get the container + // of the el, and make sure we dont move the el around in the dom + // during the render + if (!container && me.el) { + container = me.el.dom.parentNode; + me.allowDomMove = false; + } + me.container = container.dom ? container : Ext.get(container); + return me.container; + }, + initOverflow: function() { + var me = this, + // Call the style calculation early which sets the scrollFlags property + overflowStyle = me.getOverflowStyle(), + scrollFlags = me.scrollFlags, + overflowEl = me.getOverflowEl(), + hasOverflow = (scrollFlags.y || scrollFlags.x); + // Not rendered, or the targetEl has been configured as a string, wait until the call from finishRender + if (!hasOverflow || !overflowEl || !overflowEl.isElement) { + return; + } + me.overflowInited = true; + overflowEl.setStyle(overflowStyle); + }, + // Create the framingTpl from the string. + // Poke in a reference to applyRenderTpl(frameInfo, out) + initFramingTpl: function(table) { + var tpl = this.getFrameTpl(table); + if (tpl && !tpl.applyRenderTpl) { + this.setupFramingTpl(tpl); + } + return tpl; + }, + /** + * Initializes the renderTpl. + * @return {Ext.XTemplate} The renderTpl XTemplate instance. + * @private + */ + initRenderTpl: function() { + var tpl = this.lookupTpl('renderTpl'); + if (tpl && !tpl.renderContent) { + this.setupRenderTpl(tpl); + } + return tpl; + }, + /** + * @private + * Inject a reference to the function which applies the render template into the framing template. The framing template + * wraps the content. + */ + setupFramingTpl: function(frameTpl) { + frameTpl.applyRenderTpl = this.doApplyRenderTpl; + frameTpl.renderTabGuard = this.doRenderFramingTabGuard; + }, + setupRenderTpl: function(renderTpl) { + renderTpl.renderBody = renderTpl.renderContent = this.doRenderContent; + }, + /** + * Updates the frame elements to match new framing. The current `frameBody` is + * preserved by transplanting it into the new frame. All other frame `childEls` + * are destroyed and recreated if needed by the new frame. This method cannot + * transition from framed to non-framed or vise-versa or between table and div + * based framing. + * @private + */ + updateFrame: function() { + if (Ext.supports.CSS3BorderRadius || !this.frame) { + return; + } + var me = this, + dom = me.el.dom, + frameTable = me.frameTable, + oldFrameBody = me.frameBody, + oldFrameBodyDom = oldFrameBody.dom, + frameInfo = me.getFrameInfo(), + childEls, childElName, div, el, first, frameData, frameDom, frameTpl, i, newBody, newFrameEls; + // This is a bit tricky because we will be generating elements with the same + // id's (mostly) as our current frame. We have to do most of this work with + // the raw DOM nodes due to the duplicate id's (which prevents us from using + // an Element wrapper until we resolve the duplicates). + // First off, render the new frameTpl to an off-document element. + div = document.createElement('div'); + frameData = me.getFrameRenderData(); + // If the container was configured with tab guards, they were already rendered. + frameData.hasTabGuard = false; + frameTpl = me.getFrameTpl(frameInfo.table); + frameTpl.insertFirst(div, frameData); + // Capture the new frameEls (we'll need to update our childEls to these later + // once we've destroyed the old ones). + newFrameEls = div.querySelectorAll('[data-ref]'); + newBody = div.querySelector('[data-ref="frameBody"]'); + // Now we can insert the new frameEls before the current frameBody. + for (first = oldFrameBodyDom; first.parentNode !== dom; ) { + first = first.parentNode; + } + while (div.firstChild) { + dom.insertBefore(div.firstChild, first); + } + // And transplant the oldFrameBody into the new frame + newBody.parentNode.replaceChild(oldFrameBodyDom, newBody); + oldFrameBodyDom.className = newBody.className; + oldFrameBody.setSize(); + // clear any size set by layout + // Remove the old frame elements, except for frameBody of course: + childEls = me.getChildEls(); + if (frameTable) { + frameTable.destroy(); + me.frameTable = null; + } + for (childElName in childEls) { + if (childEls[childElName].frame) { + el = me[childElName]; + if (el && el !== oldFrameBody) { + el.destroy(); + me[childElName] = null; + } + } + } + // Now we are free to acquire the childEls to the new elements: + for (i = newFrameEls.length; i--; ) { + childElName = (frameDom = newFrameEls[i]).getAttribute('data-ref'); + if (childElName !== 'frameBody') { + me[childElName] = new Ext.dom.Element(frameDom); + } + } + }, + // Cache the frame information object so as not to cause style recalculations + frameInfoCache: {} + } +}); +// private + +/** + * @class Ext.state.Provider + *

Abstract base class for state provider implementations. The provider is responsible + * for setting values and extracting values to/from the underlying storage source. The + * storage source can vary and the details should be implemented in a subclass. For example + * a provider could use a server side database or the browser localstorage where supported.

+ * + *

This class provides methods for encoding and decoding typed variables including + * dates and defines the Provider interface. By default these methods put the value and the + * type information into a delimited string that can be stored. These should be overridden in + * a subclass if you want to change the format of the encoded value and subsequent decoding.

+ */ +Ext.define('Ext.state.Provider', { + mixins: { + observable: 'Ext.util.Observable' + }, + /** + * @cfg {String} prefix A string to prefix to items stored in the underlying state store. + * Defaults to 'ext-' + */ + prefix: 'ext-', + /** + * @event statechange + * Fires when a state change occurs. + * @param {Ext.state.Provider} this This state provider + * @param {String} key The state key which was changed + * @param {String} value The encoded value for the state + */ + constructor: function(config) { + var me = this; + Ext.apply(me, config); + me.state = {}; + me.mixins.observable.constructor.call(me); + }, + /** + * Returns the current value for a key + * @param {String} name The key name + * @param {Object} defaultValue A default value to return if the key's value is not found + * @return {Object} The state data + */ + get: function(name, defaultValue) { + var ret = this.state[name]; + return ret === undefined ? defaultValue : ret; + }, + /** + * Clears a value from the state + * @param {String} name The key name + */ + clear: function(name) { + var me = this; + delete me.state[name]; + me.fireEvent("statechange", me, name, null); + }, + /** + * Sets the value for a key + * @param {String} name The key name + * @param {Object} value The value to set + */ + set: function(name, value) { + var me = this; + me.state[name] = value; + me.fireEvent("statechange", me, name, value); + }, + /** + * Decodes a string previously encoded with {@link #encodeValue}. + * @param {String} value The value to decode + * @return {Object} The decoded value + */ + decodeValue: function(value) { + // a -> Array + // n -> Number + // d -> Date + // b -> Boolean + // s -> String + // o -> Object + // -> Empty (null) + var me = this, + re = /^(a|n|d|b|s|o|e)\:(.*)$/, + matches = re.exec(unescape(value)), + all, type, keyValue, values, vLen, v; + if (!matches || !matches[1]) { + return; + } + // non state + type = matches[1]; + value = matches[2]; + switch (type) { + case 'e': + return null; + case 'n': + return parseFloat(value); + case 'd': + return new Date(Date.parse(value)); + case 'b': + return (value === '1'); + case 'a': + all = []; + if (value) { + values = value.split('^'); + vLen = values.length; + for (v = 0; v < vLen; v++) { + value = values[v]; + all.push(me.decodeValue(value)); + } + }; + return all; + case 'o': + all = {}; + if (value) { + values = value.split('^'); + vLen = values.length; + for (v = 0; v < vLen; v++) { + value = values[v]; + keyValue = value.split('='); + all[keyValue[0]] = me.decodeValue(keyValue[1]); + } + }; + return all; + default: + return value; + } + }, + /** + * Encodes a value including type information. Decode with {@link #decodeValue}. + * @param {Object} value The value to encode + * @return {String} The encoded value + */ + encodeValue: function(value) { + var flat = '', + i = 0, + enc, len, key; + if (value == null) { + return 'e:1'; + } else if (typeof value === 'number') { + enc = 'n:' + value; + } else if (typeof value === 'boolean') { + enc = 'b:' + (value ? '1' : '0'); + } else if (Ext.isDate(value)) { + enc = 'd:' + value.toUTCString(); + } else if (Ext.isArray(value)) { + for (len = value.length; i < len; i++) { + flat += this.encodeValue(value[i]); + if (i !== len - 1) { + flat += '^'; + } + } + enc = 'a:' + flat; + } else if (typeof value === 'object') { + for (key in value) { + if (typeof value[key] !== 'function' && value[key] !== undefined) { + flat += key + '=' + this.encodeValue(value[key]) + '^'; + } + } + enc = 'o:' + flat.substring(0, flat.length - 1); + } else { + enc = 's:' + value; + } + return escape(enc); + } +}); + +/** + * This is the global state manager. By default all components that are "state aware" check this class + * for state information if you don't pass them a custom state provider. In order for this class + * to be useful, it must be initialized with a provider when your application initializes. Example usage: + * + * // in your initialization function + * init: function() { + * Ext.state.Manager.setProvider(new Ext.state.CookieProvider()); + * } + * + * This class passes on calls from components to the underlying {@link Ext.state.Provider} so that + * there is a common interface that can be used without needing to refer to a specific provider instance + * in every component. + */ +Ext.define('Ext.state.Manager', { + singleton: true, + requires: [ + 'Ext.state.Provider' + ], + constructor: function() { + this.provider = new Ext.state.Provider(); + }, + /** + * Configures the default state provider for your application + * @param {Ext.state.Provider} stateProvider The state provider to set + */ + setProvider: function(stateProvider) { + this.provider = stateProvider; + }, + /** + * Returns the current value for a key + * @param {String} key The key name + * @param {Object} defaultValue The default value to return if the key lookup does not match + * @return {Object} The state data + */ + get: function(key, defaultValue) { + return this.provider.get(key, defaultValue); + }, + /** + * Sets the value for a key + * @param {String} key The key name + * @param {Object} value The state data + */ + set: function(key, value) { + this.provider.set(key, value); + }, + /** + * Clears a value from the state + * @param {String} key The key name + */ + clear: function(key) { + this.provider.clear(key); + }, + /** + * Gets the currently configured state provider + * @return {Ext.state.Provider} The state provider + */ + getProvider: function() { + return this.provider; + } +}); + +/** + * @class Ext.state.Stateful + * A mixin for being able to save the state of an object to an underlying + * {@link Ext.state.Provider}. + */ +Ext.define('Ext.state.Stateful', { + mixinId: 'state', + requires: [ + 'Ext.state.Manager', + 'Ext.util.TaskRunner' + ], + config: { + /** + * @cfg {Boolean/Object} [stateful=false] + * A flag which causes the object to attempt to restore the state of + * internal properties from a saved state on startup. The object must have + * a {@link #stateId} for state to be managed. + * + * Auto-generated ids are not guaranteed to be stable across page loads and + * cannot be relied upon to save and restore the same state for a object. + * + * For state saving to work, the state manager's provider must have been + * set to an implementation of {@link Ext.state.Provider} which overrides the + * {@link Ext.state.Provider#set set} and {@link Ext.state.Provider#get get} + * methods to save and recall name/value pairs. A built-in implementation, + * {@link Ext.state.CookieProvider} is available. + * + * To set the state provider for the current page: + * + * Ext.state.Manager.setProvider(new Ext.state.CookieProvider({ + * expires: new Date(new Date().getTime()+(1000*60*60*24*7)), //7 days from now + * })); + * + * A stateful object attempts to save state when one of the events + * listed in the {@link #stateEvents} configuration fires. + * + * To save state, a stateful object first serializes its state by + * calling *{@link #getState}*. + * + * The Component base class implements {@link #getState} to save its width and + * height within the state only if they were initially configured, and have + * changed from the configured value. + * + * The Panel class saves its collapsed state in addition to that. + * + * The Grid class saves its column state and store state (sorters and filters and grouper) in addition to its superclass state. + * + * If there is more application state to be save, the developer must provide an implementation which + * first calls the superclass method to inherit the above behaviour, and then injects new properties + * into the returned object. + * + * The value yielded by `getState` is passed to {@link Ext.state.Manager#set} + * which uses the configured {@link Ext.state.Provider} to save the object + * keyed by the {@link #stateId}. + * + * During construction, a stateful object attempts to *restore* its state by calling + * {@link Ext.state.Manager#get} passing the {@link #stateId} + * + * The resulting object is passed to {@link #applyState}*. The default implementation of + * {@link #applyState} simply copies properties into the object, but a developer may + * override this to support restoration of more complex application state. + * + * You can perform extra processing on state save and restore by attaching + * handlers to the {@link #beforestaterestore}, {@link #staterestore}, + * {@link #beforestatesave} and {@link #statesave} events. In some simple cases, + * passing an object for the `stateful` config may suffice. If an object is + * provided, the properties of that object are used to include or exclude stateful + * properties returned by `getState`. For example: + * + * stateful: { + * height: false, // never persist the height + * width: true // always persist the width + * } + * + * The above is roughly equivalent to the following: + * + * getState: function () { + * var state = this.callParent(); + * + * delete state.height; + * state.width = this.width; + * + * return state; + * } + */ + stateful: null + }, + /** + * @cfg {String} stateId + * The unique id for this object to use for state management purposes. + * + * See {@link #stateful} for an explanation of saving and restoring state. + */ + /** + * @cfg {String[]} stateEvents + * An array of events that, when fired, should trigger this object to + * save its state. `stateEvents` defaults to the `stateEvents` associated with the + * component you are using. Any events you statically set will be appended to that list. + * `stateEvents` may be any type of event supported by this object, including + * browser or custom events (e.g., `['click', 'customerchange']`). + * + * See `{@link #stateful}` for an explanation of saving and + * restoring object state. + */ + /** + * @cfg {Number} saveDelay + * A buffer to be applied if many state events are fired within a short period. + */ + saveDelay: 100, + /** + * @event beforestaterestore + * Fires before the state of the object is restored. Return false from an event handler to stop the restore. + * @param {Ext.state.Stateful} this + * @param {Object} state The hash of state values returned from the StateProvider. If this + * event is not vetoed, then the state object is passed to *`applyState`*. By default, + * that simply copies property values into this object. The method maybe overriden to + * provide custom state restoration. + */ + /** + * @event staterestore + * Fires after the state of the object is restored. + * @param {Ext.state.Stateful} this + * @param {Object} state The hash of state values returned from the StateProvider. This is passed + * to *`applyState`*. By default, that simply copies property values into this + * object. The method maybe overridden to provide custom state restoration. + */ + /** + * @event beforestatesave + * Fires before the state of the object is saved to the configured state provider. Return false to stop the save. + * @param {Ext.state.Stateful} this + * @param {Object} state The hash of state values. This is determined by calling + * *`getState()`* on the object. This method must be provided by the + * developer to return whatever representation of state is required, by default, Ext.state.Stateful + * has a null implementation. + */ + /** + * @event statesave + * Fires after the state of the object is saved to the configured state provider. + * @param {Ext.state.Stateful} this + * @param {Object} state The hash of state values. This is determined by calling + * *`getState()`* on the object. This method must be provided by the + * developer to return whatever representation of state is required, by default, Ext.state.Stateful + * has a null implementation. + */ + constructor: function() { + var me = this; + if (!me.stateEvents) { + me.stateEvents = []; + } + // NOTE: The stateful config will be initConfig'd before we get here, so the + // stateful property will be correct... + if (me.stateful) { + me.addStateEvents(me.stateEvents); + me.initState(); + } + }, + /** + * Add events that will trigger the state to be saved. If the first argument is an + * array, each element of that array is the name of a state event. Otherwise, each + * argument passed to this method is the name of a state event. + * + * @param {String/String[]} events The event name or an array of event names. + */ + addStateEvents: function(events) { + var me = this, + i, event, stateEventsByName, eventArray; + if (me.stateful && me.getStateId()) { + eventArray = (typeof events === 'string') ? arguments : events; + stateEventsByName = me.stateEventsByName || (me.stateEventsByName = {}); + for (i = eventArray.length; i--; ) { + event = eventArray[i]; + if (event && !stateEventsByName[event]) { + stateEventsByName[event] = 1; + me.on(event, me.onStateChange, me); + } + } + } + }, + /** + * This method is called when any of the {@link #stateEvents} are fired. + * @private + */ + onStateChange: function() { + var me = this, + delay = me.saveDelay, + statics, runner; + if (!me.stateful) { + return; + } + if (delay) { + if (!me.stateTask) { + statics = Ext.state.Stateful; + runner = statics.runner || (statics.runner = new Ext.util.TaskRunner()); + me.stateTask = runner.newTask({ + run: me.saveState, + scope: me, + interval: delay, + repeat: 1, + fireIdleEvent: false + }); + } + me.stateTask.start(); + } else { + me.saveState(); + } + }, + /** + * Saves the state of the object to the persistence store. + */ + saveState: function() { + var me = this, + stateful = me.getStateful(), + id = stateful && me.getStateId(), + hasListeners = me.hasListeners, + cfg, configs, plugins, plugin, i, len, state, pluginState; + if (id) { + state = me.getState() || {}; + //pass along for custom interactions + if (Ext.isObject(stateful)) { + configs = me.self.getConfigurator(); + configs = configs.configs; + // configs[name]: Ext.Config(name) + for (i in stateful) { + if (stateful[i]) { + if (!(i in state)) { + cfg = configs[i]; + // if class declared this as a config + state[i] = cfg ? me[cfg.get]() : me[i]; + } + } else { + delete state[i]; + } + } + } + /* + * Gather state from those plugins that implement a getState method + */ + plugins = me.getPlugins() || []; + for (i = 0 , len = plugins.length; i < len; i++) { + plugin = plugins[i]; + if (plugin && plugin.getState) { + pluginState = plugin.getState(state); + if (pluginState && !state[plugin.ptype]) { + //first duplicate plugin wins + state[plugin.ptype] = pluginState; + } + } + } + if (!hasListeners.beforestatesave || me.fireEvent('beforestatesave', me, state) !== false) { + Ext.state.Manager.set(id, state); + if (hasListeners.statesave) { + me.fireEvent('statesave', me, state); + } + } + } + }, + /** + * Gets the current state of the object. By default this function returns null, + * it should be overridden in subclasses to implement methods for getting the state. + * @return {Object} The current state + */ + getState: function() { + return null; + }, + /** + * Applies the state to the object. This should be overridden in subclasses to do + * more complex state operations. By default it applies the state properties onto + * the current object. + * @param {Object} state The state + */ + applyState: function(state) { + if (state) { + Ext.apply(this, state); + } + }, + /** + * Gets the state id for this object. + * @return {String} The 'stateId' or the implicit 'id' specified by component configuration. + * @private + */ + getStateId: function() { + var me = this; + return me.stateId || (me.autoGenId ? null : me.id); + }, + /** + * Initializes the state of the object upon construction. + * @private + */ + initState: function() { + var me = this, + id = me.stateful && me.getStateId(), + hasListeners = me.hasListeners, + state, combinedState, i, len, plugins, plugin, pluginType; + if (id) { + combinedState = Ext.state.Manager.get(id); + if (combinedState) { + state = Ext.apply({}, combinedState); + if (!hasListeners.beforestaterestore || me.fireEvent('beforestaterestore', me, combinedState) !== false) { + //Notify all plugins FIRST (if interested) in new state + plugins = me.getPlugins() || []; + for (i = 0 , len = plugins.length; i < len; i++) { + plugin = plugins[i]; + if (plugin) { + pluginType = plugin.ptype; + if (plugin.applyState) { + plugin.applyState(state[pluginType], combinedState); + } + delete state[pluginType]; + } + } + //clean to prevent unwanted props on the component in final phase + me.applyState(state); + if (hasListeners.staterestore) { + me.fireEvent('staterestore', me, combinedState); + } + } + } + } + }, + /** + * Conditionally saves a single property from this object to the given state object. + * The idea is to only save state which has changed from the initial state so that + * current software settings do not override future software settings. Only those + * values that are user-changed state should be saved. + * + * @param {String} propName The name of the property to save. + * @param {Object} state The state object in to which to save the property. + * @param {String} stateName (optional) The name to use for the property in state. + * @return {Boolean} True if the property was saved, false if not. + */ + savePropToState: function(propName, state, stateName) { + var me = this, + value = me[propName], + config = me.initialConfig; + if (me.hasOwnProperty(propName)) { + if (!config || config[propName] !== value) { + if (state) { + state[stateName || propName] = value; + } + return true; + } + } + return false; + }, + /** + * Gathers additional named properties of the instance and adds their current values + * to the passed state object. + * @param {String/String[]} propNames The name (or array of names) of the property to save. + * @param {Object} state The state object in to which to save the property values. + * @return {Object} state + */ + savePropsToState: function(propNames, state) { + var me = this, + i, n; + if (typeof propNames === 'string') { + me.savePropToState(propNames, state); + } else { + for (i = 0 , n = propNames.length; i < n; ++i) { + me.savePropToState(propNames[i], state); + } + } + return state; + }, + /** + * Destroys this stateful object. + */ + destroy: function() { + var task = this.stateTask; + if (task) { + task.destroy(); + this.stateTask = null; + } + } +}); +// No callParent() here, it's a mixin. + +/** + * Base class for all Ext components. + * + * The Component base class has built-in support for basic hide/show and enable/disable + * and size control behavior. + * + * ## xtypes + * + * Every component has a specific xtype, which is its Ext-specific type name, along with + * methods for checking the xtype like {@link #getXType} and {@link #isXType}. See the + * [Component Guide](../../../guides/core_concepts/components.html) for more information on xtypes + * and the Component hierarchy. + * + * ## Finding components + * + * All Components are registered with the {@link Ext.ComponentManager} on construction so + * that they can be referenced at any time via {@link Ext#getCmp Ext.getCmp}, passing the + * {@link #id}. + * + * Additionally the {@link Ext.ComponentQuery} provides a CSS-selectors-like way to look + * up components by their xtype and many other attributes. For example the following code + * will find all textfield components inside component with `id: 'myform'`: + * + * Ext.ComponentQuery.query('#myform textfield'); + * + * ## Extending Ext.Component + * + * All subclasses of Component may participate in the automated Ext component + * life cycle of creation, rendering and destruction which is provided by the + * {@link Ext.container.Container Container} class. Components may be added to a Container + * through the {@link Ext.container.Container#cfg-items items} config option at the time + * the Container is created, or they may be added dynamically via the + * {@link Ext.container.Container#method-add add} method. + * + * All user-developed visual widgets that are required to participate in automated + * life cycle and size management should subclass Component. + * + * See the Creating new UI controls chapter in [Component Guide](../../../guides/core_concepts/components.html) + * for details on how and to either extend or augment Ext JS base classes to create custom Components. + * + * ## The Ext.Component class by itself + * + * Usually one doesn't need to instantiate the Ext.Component class. There are subclasses + * which implement specialized use cases, covering most application needs. However it is + * possible to instantiate a base Component, and it can be rendered to document, or handled + * by layouts as the child item of a Container: + * + * @example + * Ext.create('Ext.Component', { + * html: 'Hello world!', + * width: 300, + * height: 200, + * padding: 20, + * style: { + * color: '#FFFFFF', + * backgroundColor:'#000000' + * }, + * renderTo: Ext.getBody() + * }); + * + * The Component above creates its encapsulating `div` upon render, and use the configured + * HTML as content. More complex internal structure may be created using the + * {@link #renderTpl} configuration, although to display database-derived mass data, it is + * recommended that an ExtJS data-backed Component such as a {@link Ext.view.View View}, + * {@link Ext.grid.Panel GridPanel}, or {@link Ext.tree.Panel TreePanel} be used. + */ +Ext.define('Ext.Component', { + alternateClassName: 'Ext.AbstractComponent', + xtype: [ + 'component', + 'box' + ], + requires: [ + 'Ext.ComponentQuery', + 'Ext.ComponentManager', + 'Ext.util.ProtoElement', + 'Ext.dom.CompositeElement', + 'Ext.plugin.Abstract', + 'Ext.plugin.Manager', + 'Ext.scroll.Scroller' + ], + // Note that Floating must be mixed in before Positionable. + mixins: [ + 'Ext.mixin.Inheritable', + 'Ext.util.Floating', + 'Ext.util.Positionable', + 'Ext.util.Observable', + 'Ext.mixin.ComponentDelegation', + 'Ext.mixin.Bindable', + 'Ext.util.Animate', + 'Ext.util.ElementContainer', + 'Ext.util.Renderable', + 'Ext.state.Stateful', + 'Ext.mixin.Focusable', + 'Ext.mixin.Accessible', + 'Ext.mixin.Keyboard' + ], + uses: [ + 'Ext.overrides.*', + 'Ext.Element', + 'Ext.DomHelper', + 'Ext.XTemplate', + 'Ext.ComponentLoader', + 'Ext.layout.Context', + 'Ext.layout.Layout', + 'Ext.layout.component.Auto', + 'Ext.LoadMask', + 'Ext.ZIndexManager', + 'Ext.util.DelayedTask', + 'Ext.resizer.Resizer', + 'Ext.util.ComponentDragger' + ], + statics: { + AUTO_ID: 1000, + pendingLayouts: null, + layoutSuspendCount: 0, + // Collapse/expand directions + DIRECTION_TOP: 'top', + DIRECTION_RIGHT: 'right', + DIRECTION_BOTTOM: 'bottom', + DIRECTION_LEFT: 'left', + VERTICAL_DIRECTION_Re: /^(?:top|bottom)$/, + // RegExp whih specifies characters in an xtype which must be translated to '-' when generating auto IDs. + // This includes dot, comma and whitespace + INVALID_ID_CHARS_Re: /[\.,\s]/g, + /** + * @property {String} ariaHighContrastModeCls CSS class to be applied + * to the document body when High Contrast mode is detected in Windows. + * @private + */ + ariaHighContrastModeCls: Ext.baseCSSPrefix + 'aria-highcontrast', + /** + * Cancels layout of a component. + * @param {Ext.Component} comp + * @param isDestroying + */ + cancelLayout: function(comp, isDestroying) { + var context = this.runningLayoutContext || this.pendingLayouts; + if (context) { + context.cancelComponent(comp, false, isDestroying); + } + }, + /** + * Find the Widget or Component to which the given event/element belongs. + * + * @param {Ext.event.Event/Ext.dom.Element/HTMLElement} el The element or event + * from which to start to find an owning Component. + * @param {Ext.dom.Element/HTMLElement} [limit] The element at which to stop upward + * searching for an owning Component, or the number of Components to traverse + * before giving up. Defaults to the document's HTML element. + * @param {String} [selector] An optional {@link Ext.ComponentQuery} selector to + * filter the target. + * @return {Ext.Component/null} Component, or null + * + * @since 6.5.0 + */ + from: function(el, limit, selector) { + return Ext.ComponentManager.from(el, limit, selector); + }, + /** + * Find the Widget or Component to which the given Element belongs. + * + * @param {Ext.dom.Element/HTMLElement} el The element from which to start to find an owning Component. + * @param {Ext.dom.Element/HTMLElement} [limit] The element at which to stop upward searching for an + * owning Component, or the number of Components to traverse before giving up. + * Defaults to the document's HTML element. + * @param {String} [selector] An optional {@link Ext.ComponentQuery} selector to filter the target. + * @return {Ext.Component/null} Component, or null + * + * @deprecated 6.5.0 Use {@link Ext.Component#method!from} instead. + * @since 6.0.1 + */ + fromElement: function(el, limit, selector) { + return Ext.ComponentManager.from(el, limit, selector); + }, + /** + * Performs all pending layouts that were scheduled while + * {@link Ext.Component#suspendLayouts suspendLayouts} was in effect. + * @static + */ + flushLayouts: function() { + var me = this, + context = me.pendingLayouts; + if (context && context.invalidQueue.length) { + me.pendingLayouts = null; + me.runningLayoutContext = context; + Ext.override(context, { + runComplete: function() { + // we need to release the layout queue before running any of the + // finishedLayout calls because they call afterComponentLayout + // which can re-enter by calling updateLayout/doComponentLayout. + me.runningLayoutContext = null; + var Scroller = Ext.scroll.Scroller, + GlobalEvents = Ext.GlobalEvents, + result; + if (Scroller.viewport) { + Scroller.viewport.restoreState(); + } + result = this.callParent(); + // not "me" here! + if (GlobalEvents.hasListeners.afterlayout) { + GlobalEvents.fireEvent('afterlayout'); + } + return result; + } + }); + context.run(); + } + }, + /** + * Resumes layout activity in the whole framework. + * + * {@link Ext#suspendLayouts} is alias of {@link Ext.Component#suspendLayouts}. + * + * @param {Boolean} [flush=false] `true` to perform all the pending layouts. This can also be + * achieved by calling {@link Ext.Component#flushLayouts flushLayouts} directly. + * @static + */ + resumeLayouts: function(flush) { + if (this.layoutSuspendCount && !--this.layoutSuspendCount) { + if (flush) { + this.flushLayouts(); + } + if (Ext.GlobalEvents.hasListeners.resumelayouts) { + Ext.GlobalEvents.fireEvent('resumelayouts'); + } + } + }, + /** + * Stops layouts from happening in the whole framework. + * + * It's useful to suspend the layout activity while updating multiple components and + * containers: + * + * Ext.suspendLayouts(); + * // batch of updates... + * Ext.resumeLayouts(true); + * + * {@link Ext#suspendLayouts} is alias of {@link Ext.Component#suspendLayouts}. + * + * See also {@link Ext#batchLayouts} for more abstract way of doing this. + * + * @static + */ + suspendLayouts: function() { + ++this.layoutSuspendCount; + }, + /** + * Updates layout of a component. + * + * @param {Ext.Component} comp The component to update. + * @param {Boolean} [defer=false] `true` to just queue the layout if this component. + * @static + */ + updateLayout: function(comp, defer) { + var me = this, + running = me.runningLayoutContext, + pending; + if (running) { + running.queueInvalidate(comp); + } else { + pending = me.pendingLayouts || (me.pendingLayouts = new Ext.layout.Context()); + pending.queueInvalidate(comp); + if (!defer && !me.layoutSuspendCount && !comp.isLayoutSuspended()) { + me.flushLayouts(); + } + } + } + }, + // + // *********************************************************************************** + // Begin Config + // *********************************************************************************** + // We do not want "_hidden" style backing properties. + $configPrefixed: false, + // We also want non-config system properties to go to the instance. + $configStrict: false, + clearPropertiesOnDestroy: 'async', + manageLayoutScroll: true, + config: { + /** + * @cfg {Object} data + * The initial set of data to apply to the `{@link #tpl}` to update the content + * area of the Component. + * + * @accessor + * @since 3.4.0 + */ + data: null, + /** + * @cfg {Boolean} modelValidation + * This config enables binding to your `{@link Ext.data.Model#validators}`. This + * is only processed by form fields (e.g., `Ext.form.field.Text`) at present, but + * this setting is inherited and so can be set on a parent container. + * + * When set to `true` by a component or not set by a component but inherited from + * an ancestor container, `Ext.data.Validation` records are used to automatically + * bind validation results for any form field to which a `value` is bound. + * + * While this config can be set arbitrarily high in the component hierarchy, doing + * so can create a lot overhead if most of your form fields do not actually rely on + * `validators` in your data model. + * + * Using this setting for a form that is bound to an `Ext.data.Model` might look + * like this: + * + * { + * xtype: 'panel', + * modelValidation: true, + * items: [{ + * xtype: 'textfield', + * bind: '{theUser.firstName}' + * },{ + * xtype: 'textfield', + * bind: '{theUser.lastName}' + * },{ + * xtype: 'textfield', + * bind: '{theUser.phoneNumber}' + * },{ + * xtype: 'textfield', + * bind: '{theUser.email}' + * }] + * } + * + * Notice that "validation" is a pseudo-association defined for all entities. See + * `{@link Ext.data.Model#getValidation}` for further details. + */ + /** + * @cfg {Number} maxHeight + * The maximum value in pixels which this Component will set its height to. + * + * **Warning:** This will override any size management applied by layout managers. + */ + maxHeight: null, + /** + * @cfg {Number} maxWidth + * The maximum value in pixels which this Component will set its width to. + * + * **Warning:** This will override any size management applied by layout managers. + */ + maxWidth: null, + /** + * @cfg {Number} minHeight + * The minimum value in pixels which this Component will set its height to. + * + * **Warning:** This will override any size management applied by layout managers. + */ + minHeight: null, + /** + * @cfg {Number} minWidth + * The minimum value in pixels which this Component will set its width to. + * + * **Warning:** This will override any size management applied by layout managers. + */ + minWidth: null, + /** + * @cfg {Boolean/String/Object} scrollable + * Configuration options to make this Component scrollable. Acceptable values are: + * + * - `true` to enable auto scrolling. + * - `false` (or `null`) to disable scrolling - this is the default. + * - `x` or `horizontal` to enable horizontal scrolling only + * - `y` or `vertical` to enable vertical scrolling only + * + * Also accepts a configuration object for a `{@link Ext.scroll.Scroller}` if + * if advanced configuration is needed. + * + * The getter for this config returns the {@link Ext.scroll.Scroller Scroller} + * instance. You can use the Scroller API to read or manipulate the scroll position: + * + * // scrolls the component to 5 on the x axis and 10 on the y axis + * component.getScrollable().scrollTo(5, 10); + */ + scrollable: null + }, + /** + * @cfg {Object} renderConfig + * renderConfig wraps configs that do not get applied until after the component is + * rendered. Unlike normal config system properties, renderConfigs use a special + * setter method to store values on the instance instead of running the apply and + * update methods if it is called before the component is rendered. Then, after the + * component has been rendered, these values are processed by the normal apply and + * update method for the config. + * + * This means that calling the get method for the config prior to render will return + * whatever raw value has been set, while calling the getter after render will return + * the value after processing by the config's apply method. If this distinction needs + * to be made, it is the caller's responsibility to check for the rendered state and + * handle such intermediate config values. + */ + renderConfig: { + /** + * @cfg {Object} touchAction + * + * Emulates the behavior of the CSS + * [touch-action](https://www.w3.org/TR/pointerevents/#the-touch-action-css-property) + * property in a cross-browser compatible manner. + * + * Keys in this object are touch action names, and values are `false` to disable + * a touch action or `true` to enable it. Accepted keys are: + * + * - `panX` + * - `panY` + * - `pinchZoom` + * - `doubleTapZoom` + * + * All touch actions are enabled (`true`) by default, so it is usually only necessary + * to specify which touch actions to disable. For example, the following disables + * only horizontal scrolling and pinch-to-zoom on the component's main element: + * + * touchAction: { + * panX: false, + * pinchZoom: false + * } + * + * Touch actions can be specified on child elements using the child element name, + * for example: + * + * // disables horizontal scrolling on the main element, and double-tap-zoom + * // on the child element named "body" + * touchAction: { + * panY: false + * body: { + * doubleTapZoom: false + * } + * } + * + * The primary motivation for setting the touch-action of an element is to prevent + * the browser's default handling of a gesture such as pinch-to-zoom, or + * drag-to-scroll, so that the application can implement its own handling of that + * gesture on the element. Suppose, for example, a component has a custom drag + * handler on its element and wishes to prevent horizontal scrolling of its container + * while it is being dragged: + * + * Ext.create('Ext.Component', { + * touchAction: { + * panX: false + * }, + * listeners: { + * drag: function(e) { + * // implement drag logic + * } + * } + * }); + */ + touchAction: null + }, + /** + * @property defaultBindProperty + * @inheritdoc + */ + defaultBindProperty: 'html', + /** + * @cfg {String} alignTarget + * A Component or Element by which to position this component according to the {@link #defaultAlign}. + * Defaults to the owning Container. + * + * *Only applicable if this component is {@link #cfg-floating}* + * + * *Used upon first show*. + */ + alignTarget: null, + /** + * @cfg anchor + * @inheritDoc Ext.layout.container.Anchor#cfg-anchor + */ + /** + * @cfg {String/Object} autoEl + * A tag name or {@link Ext.dom.Helper DomHelper} spec used to create the {@link #getEl Element} which will + * encapsulate this Component. + * + * You do not normally need to specify this. For the base classes {@link Ext.Component} and + * {@link Ext.container.Container}, this defaults to **'div'**. The more complex Sencha classes use a more + * complex DOM structure specified by their own {@link #cfg-renderTpl}s. + * + * This is intended to allow the developer to create application-specific utility Components encapsulated by + * different DOM elements. Example usage: + * + * { + * xtype: 'component', + * autoEl: { + * tag: 'img', + * src: 'http://www.example.com/example.jpg' + * } + * }, { + * xtype: 'component', + * autoEl: { + * tag: 'blockquote', + * html: 'autoEl is cool!' + * } + * }, { + * xtype: 'container', + * autoEl: 'ul', + * cls: 'ux-unordered-list', + * items: { + * xtype: 'component', + * autoEl: 'li', + * html: 'First list item' + * } + * } + * + * @since 2.3.0 + */ + /** + * @cfg {Boolean/String/HTMLElement/Ext.dom.Element} autoRender + * This config is intended mainly for non-{@link #cfg-floating} Components which may or may not be shown. Instead of using + * {@link #renderTo} in the configuration, and rendering upon construction, this allows a Component to render itself + * upon first _{@link Ext.Component#method-show show}_. If {@link #cfg-floating} is `true`, the value of this config is omitted as if it is `true`. + * + * Specify as `true` to have this Component render to the document body upon first show. + * + * Specify as an element, or the ID of an element to have this Component render to a specific element upon first + * show. + */ + autoRender: false, + /** + * @cfg {Boolean} [autoScroll=false] + * `true` to use overflow:'auto' on the components layout element and show scroll bars automatically when necessary, + * `false` to clip any overflowing content. + * + * This should not be combined with {@link #overflowX} or {@link #overflowY}. + * @deprecated 5.1.0 Use {@link #scrollable} instead + */ + /** + * @cfg {Boolean} autoShow + * `true` to automatically show the component upon creation. This config option may only be used for + * {@link #cfg-floating} components or components that use {@link #autoRender}. + * + * @since 2.3.0 + */ + autoShow: false, + /** + * @cfg {String} baseCls + * The base CSS class to apply to this component's element. This will also be prepended to elements within this + * component like Panel's body will get a class `x-panel-body`. This means that if you create a subclass of Panel, and + * you want it to get all the Panels styling for the element and the body, you leave the `baseCls` `x-panel` and use + * `componentCls` to add specific styling for this component. + */ + baseCls: Ext.baseCSSPrefix + 'component', + /** + * @cfg {Number/String/Boolean} border + * Specifies the border size for this component. The border can be a single numeric value to apply to all sides or it can + * be a CSS style specification for each style, for example: '10 5 3 10' (top, right, bottom, left). + * + * For components that have no border by default, setting this won't make the border appear by itself. + * You also need to specify border color and style: + * + * border: 5, + * style: { + * borderColor: 'red', + * borderStyle: 'solid' + * } + * + * To turn off the border, use `border: false`. + */ + /** + * @cfg childEls + * @inheritdoc Ext.util.ElementContainer#cfg-childEls + */ + childEls: { + frameTable: { + frame: true + }, + frameTL: { + frame: 'tl' + }, + frameTC: { + frame: 'tc' + }, + frameTR: { + frame: 'tr' + }, + frameML: { + frame: 'ml' + }, + frameBody: { + frame: 'mc' + }, + frameMR: { + frame: 'mr' + }, + frameBL: { + frame: 'bl' + }, + frameBC: { + frame: 'bc' + }, + frameBR: { + frame: 'br' + } + }, + /** + * @cfg {String/String[]} [cls=''] + * An optional extra CSS class that will be added to this component's Element. + * The value can be a string, a list of strings separated by spaces, or an array of strings. This can be useful + * for adding customized styles to the component or any of its children using standard CSS rules. + * + * @since 1.1.0 + */ + /** + * @cfg {Number} [columnWidth] + * Defines the column width inside {@link Ext.layout.container.Column column layout}. + * + * The columnWidth property is always evaluated as a percentage and must be a decimal value greater than 0 and + * less than 1 (e.g., .25). See the description at the top of {@link Ext.layout.container.Column column layout} for + * additional usage details when combining width and columnWidth configs within the layout. + */ + /** + * @cfg {String} componentCls + * CSS Class to be added to a components root level element to give distinction to it via styling. + */ + // @cmd-auto-dependency { aliasPrefix : "layout." } + /** + * @cfg {String/Object} componentLayout + * The sizing and positioning of a Component's internal Elements is the responsibility of the Component's layout + * manager which sizes a Component's internal structure in response to the Component being sized. + * + * Generally, developers will not use this configuration as all provided Components which need their internal + * elements sizing (Such as {@link Ext.form.field.Base input fields}) come with their own componentLayout managers. + * + * The {@link Ext.layout.container.Auto default layout manager} will be used on instances of the base Ext.Component + * class which simply sizes the Component's encapsulating element to the height and width specified in the + * {@link #setSize} method. + * + */ + componentLayout: 'autocomponent', + /** + * @cfg {Object/String} constraintInsets + * An object or a string (in TRBL order) specifying insets from the configured {@link #constrainTo constrain region} + * within which this component must be constrained when positioning or sizing. + * example: + * + * constraintInsets: '10 10 10 10' // Constrain with 10px insets from parent + */ + /** + * @cfg {Ext.util.Region/Ext.dom.Element} constrainTo + * A {@link Ext.util.Region Region} (or an element from which a Region measurement will be read) which is used + * to constrain the component. Only applies when the component is floating. + */ + /** + * @cfg {String} contentEl + * Specify an existing HTML element, or the `id` of an existing HTML element to use as the content for this component. + * + * This config option is used to take an existing HTML element and place it in the layout element of a new component + * (it simply moves the specified DOM element _after the Component is rendered_ to use as the content. + * + * **Notes:** + * + * The specified HTML element is appended to the layout element of the component _after any configured + * {@link #html HTML} has been inserted_, and so the document will not contain this element at the time + * the {@link #event-render} event is fired. + * + * The specified HTML element used will not participate in any **`{@link Ext.container.Container#layout layout}`** + * scheme that the Component may use. It is just HTML. Layouts operate on child + * **`{@link Ext.container.Container#cfg-items items}`**. + * + * Add either the `x-hidden` or the `x-hidden-display` CSS class to prevent a brief flicker of the content before it + * is rendered to the panel. + * + * @since 3.4.0 + */ + /** + * @cfg {String} defaultAlign + * The default {@link Ext.util.Positionable#getAlignToXY Ext.dom.Element#getAlignToXY} anchor position value for this component + * relative to its {@link #alignTarget} (which defaults to its owning Container). + * + * _Only applicable if this component is {@link #cfg-floating}_ + * + * *Used upon first show*. + */ + defaultAlign: 'c-c', + /** + * @cfg {Boolean} disabled + * `true` to disable the component. + * @since 2.3.0 + */ + disabled: false, + // http://www.w3.org/TR/html5/disabled-elements.html + disabledRe: /^(?:button|input|select|textarea|optgroup|option|fieldset)$/i, + nonMaskableRe: (function() { + var re = [ + 'input', + 'select', + 'textarea', + 'optgroup', + 'option', + 'table' + ]; + // All IE browsers 9 and below except for IE 9 standards. + if (Ext.isIE9m && !(Ext.isIE9 && !Ext.isIEQuirks)) { + //

.insertAdjacentHTML('BeforeEnd', '

...
') yields + // 'Invalid source HTML for this operation' in all IEs not IE 9 standards. + re.push('p'); + } + return new RegExp('^(?:' + re.join('|') + ')$', 'i'); + }()), + /** + * @cfg {String} disabledCls + * CSS class to add when the Component is disabled. + */ + disabledCls: Ext.baseCSSPrefix + 'item-disabled', + /** + * @cfg {'top'/'bottom'/'left'/'right'} dock + * The side of the {@link Ext.panel.Panel panel} where this component is to be + * docked when specified in the panel's + * {@link Ext.panel.Panel#dockedItems dockedItems} config. + * + * Possible values are: + * + * - top + * - bottom + * - left + * - right + */ + /** + * @cfg {Boolean/Object} draggable + * Specify as true to make a {@link #cfg-floating} Component draggable using the Component's encapsulating element as + * the drag handle. + * + * This may also be specified as a config object for the {@link Ext.util.ComponentDragger ComponentDragger} which is + * instantiated to perform dragging. + * + * For example to create a Component which may only be dragged around using a certain internal element as the drag + * handle, use the delegate option: + * + * new Ext.Component({ + * constrain: true, + * floating: true, + * style: { + * backgroundColor: '#fff', + * border: '1px solid black' + * }, + * html: '

The title

The content

', + * draggable: { + * delegate: 'h1' + * } + * }).show(); + */ + draggable: false, + /** + * @cfg {Number} flex + * Flex may be applied to **child items** of a box layout ({@link Ext.layout.container.VBox vbox} or + * {@link Ext.layout.container.HBox hbox}). Each child item with a flex property will + * fill space (horizontally in `hbox`, vertically in `vbox`) according to that item's + * **relative** flex value compared to the sum of all items with a flex value specified. + * + * Any child items that have either a `flex` of `0` or `undefined` + * will not be 'flexed' (the initial size will not be changed). + */ + /** + * @cfg {Boolean} floating + * Specify as true to float the Component outside of the document flow using CSS absolute positioning. + * + * Components such as {@link Ext.window.Window Window}s and {@link Ext.menu.Menu Menu}s are floating by default. + * + * Floating Components that are programmatically {@link Ext.Component#method-render rendered} will register + * themselves with the global {@link Ext.WindowManager ZIndexManager} + * + * ### Floating Components as child items of a Container + * + * A floating Component may be used as a child item of a Container. This just allows the floating Component to seek + * a ZIndexManager by examining the ownerCt chain. + * + * When configured as floating, Components acquire, at render time, a {@link Ext.ZIndexManager ZIndexManager} which + * manages a stack of related floating Components. The ZIndexManager sorts its stack according to + * an incrementing access counter and the {@link Ext.util.Floating#alwaysOnTop alwaysOnTop} config when the Component's {@link #toFront} method is called. + * + * The ZIndexManager is found by traversing up the {@link #ownerCt} chain to find an ancestor which itself is + * floating. This is so that descendant floating Components of floating _Containers_ (Such as a ComboBox dropdown + * within a Window) can have its zIndex managed relative to any siblings, but always **above** that floating + * ancestor Container. + * + * If no floating ancestor is found, a floating Component registers itself with the default {@link Ext.WindowManager + * ZIndexManager}. + * + * Floating components _do not participate in the Container's layout_. Because of this, they are not rendered until + * you explicitly {@link #method-show} them. + * + * After rendering, the ownerCt reference is deleted, and the {@link #floatParent} property is set to the found + * floating ancestor Container. If no floating ancestor Container was found the {@link #floatParent} property will + * not be set. + */ + floating: false, + /** + * @cfg {Boolean} [formBind=false] + * When inside FormPanel, any component configured with `formBind: true` will + * be enabled/disabled depending on the validity state of the form. + * See {@link Ext.form.Panel} for more information and example. + */ + /** + * @cfg {Boolean} frame + * Specify as `true` to have the Component inject framing elements within the Component at render time to provide a + * graphical rounded frame around the Component content. + * + * This is only necessary when running on outdated, or non standard-compliant browsers such as Microsoft's Internet + * Explorer prior to version 9 which do not support rounded corners natively. + * + * The extra space taken up by this framing is available from the read only property {@link #frameSize}. + */ + /** + * @cfg {Number|String} height + * The height of this component. A numeric value will be interpreted as the number of + * pixels; a string value will be treated as a CSS value with units. + */ + /** + * @cfg {Boolean} hidden + * `true` to hide the component. + * @since 2.3.0 + */ + hidden: false, + /** + * @cfg {String} hideMode + * A String which specifies how this Component's encapsulating DOM element will be hidden. Values may be: + * + * - `'display'` : The Component will be hidden using the `display: none` style. + * - `'visibility'` : The Component will be hidden using the `visibility: hidden` style. + * - `'offsets'` : The Component will be hidden by absolutely positioning it out of the visible area of the document. + * This is useful when a hidden Component must maintain measurable dimensions. Hiding using `display` results in a + * Component having zero dimensions. + * + * @since 1.1.0 + */ + hideMode: 'display', + /** + * @cfg {String/Object} [html=''] + * An HTML fragment, or a {@link Ext.dom.Helper DomHelper} specification to use as the layout element content. + * The HTML content is added after the component is rendered, so the document will not contain this HTML at the time + * the {@link #event-render} event is fired. This content is inserted into the body _before_ any configured {@link #contentEl} + * is appended. + * + * @since 3.4.0 + */ + /** + * @cfg {String} id + * The **unique** id of this component instance. + * + * Use of this config should be considered carefully as this value must be unique across + * all existing components. Components created with an `id` may be accessed globally + * using {@link Ext#getCmp Ext.getCmp}. + * + * Instead of using assigned ids, consider a {@link #reference} config and a {@link #cfg-controller ViewController} + * to respond to events and perform processing upon this Component. + * + * Alternatively, {@link #itemId} and {@link Ext.ComponentQuery ComponentQuery} can be + * used to perform selector-based searching for Components analogous to DOM querying. + * The {@link Ext.container.Container Container} class contains several helpful + * {@link Ext.container.Container#down shortcut methods} to query its descendant + * Components by selector. + * + * Note that this `id` will also be used as the element id for the containing HTML + * element that is rendered to the page for this component. This allows you to write + * id-based CSS rules to style the specific instance of this component uniquely, and + * also to select sub-elements using this component's `id` as the parent. + * + * Defaults to an {@link #getId auto-assigned id}. + * + * **Note**: Valid identifiers start with a letter or underscore and are followed by + * (optional) additional letters, underscores, digits or hyphens. + * + * @since 1.1.0 + */ + /** + * @cfg {String} itemId + * The **unique** id of this component instance within its container. See also the + * {@link #reference} config. + * + * An `itemId` can be used as an alternative way to get a reference to a component when no object reference is + * available. Instead of using an `{@link #id}` with {@link Ext#getCmp getCmp}, use + * `itemId` with {@link Ext.container.Container#getComponent getComponent} which will + * retrieve `itemId`'s or {@link #id}'s. Since `itemId`'s are an index to the container's + * internal collection, the `itemId` is scoped locally to the container -- avoiding + * potential conflicts with {@link Ext.ComponentManager}, which requires a **unique** {@link #id} value. + * + * var c = new Ext.panel.Panel({ // + * height: 300, + * renderTo: document.body, + * layout: 'auto', + * items: [{ + * itemId: 'p1', + * title: 'Panel 1', + * height: 150 + * },{ + * itemId: 'p2', + * title: 'Panel 2', + * height: 150 + * }] + * }); + * + * p1 = c.getComponent('p1'); // not the same as Ext.getCmp() + * console.log(p1); + * p2 = p1.ownerCt.getComponent('p2'); // reference via a sibling + * console.log(p2); + * + * Also see {@link #id}, `{@link Ext.container.Container#query}`, `{@link Ext.container.Container#down}` and + * `{@link Ext.container.Container#child}`. + * + * **Note**: Valid identifiers start with a letter or underscore and are followed by + * (optional) additional letters, underscores, digits or hyphens. + * + * **Note**: to access the container of an item see {@link #ownerCt}. + * + * @since 3.4.0 + */ + /** + * @cfg {Ext.ComponentLoader/Object} loader + * A configuration object or an instance of a {@link Ext.ComponentLoader} to load remote content + * for this Component. + * + * Ext.create('Ext.Component', { + * loader: { + * url: 'content.html', + * autoLoad: true + * }, + * renderTo: Ext.getBody() + * }); + */ + /** + * @cfg {Number/String} margin + * Specifies the margin for this component. The margin can be a single numeric value to apply to all sides or it can + * be a CSS style specification for each style, for example: '10 5 3 10' (top, right, bottom, left). + */ + /** + * @cfg {String} maskElement + * Related to the {@link #cfg-childEls} configuration which specifies named properties which correspond to component sub-elements. + * + * The name of the element property in this component to mask when masked by a LoadMask. + * + * Defaults to `null` to indicate that Components cannot by default contain a LoadMask, and that any LoadMask should be rendered into the document body. + * + * For example, Panels use `"el"` to indicate that the whole panel should be masked. This could be configured to be + * `"body"` so that only the body is masked and toolbars and the header are still mouse-accessible. + */ + maskElement: null, + /** + * @cfg {Object} [maskDefaults] Default LoadMask configuration for {@link #method-setLoading}. + */ + /** + * @cfg {String} [overCls=''] + * An optional extra CSS class that will be added to this component's Element when the mouse moves over the Element, + * and removed when the mouse moves out. This can be useful for adding customized 'active' or 'hover' styles to the + * component or any of its children using standard CSS rules. + * + * @since 2.3.0 + */ + /** + * @cfg {String} overflowX + * Possible values are: + * + * - `'auto'` to enable automatic horizontal scrollbar (Style overflow-x: 'auto'). + * - `'scroll'` to always enable horizontal scrollbar (Style overflow-x: 'scroll'). + * + * The default is overflow-x: 'hidden'. This should not be combined with {@link #autoScroll}. + * @deprecated 5.1.0 Use {@link #scrollable} instead + */ + /** + * @cfg {String} overflowY + * Possible values are: + * + * - `'auto'` to enable automatic vertical scrollbar (Style overflow-y: 'auto'). + * - `'scroll'` to always enable vertical scrollbar (Style overflow-y: 'scroll'). + * + * The default is overflow-y: 'hidden'. This should not be combined with {@link #autoScroll}. + * @deprecated 5.1.0 Use {@link #scrollable} instead + */ + /** + * @cfg {Number/String} padding + * Specifies the padding for this component. The padding can be a single numeric value to apply to all sides or it + * can be a CSS style specification for each style, for example: '10 5 3 10' (top, right, bottom, left). + */ + /** + * @cfg {Array/Ext.enums.Plugin/Object/Ext.plugin.Abstract} plugins + * This config describes one or more plugin config objects used to create plugin + * instances for this component. + * + * Plugins are a way to bundle and reuse custom functionality. Plugins should extend + * `Ext.plugin.Abstract` but technically the only requirement for a valid plugin + * is that it contain an `init` method that accepts a reference to its owner. Once + * a plugin is created, the owner will call the `init` method, passing a reference + * to itself. Each plugin can then call methods or respond to events on its owner + * as needed to provide its functionality. + * + * This config's value can take several different forms. + * + * The value can be a single string with the plugin's {@link Ext.enums.Plugin alias}: + * + * plugins: 'cellediting', + * + * The preferred form for multiple plugins or to configure plugins is the keyed-object + * form (new in version 6.5): + * + * plugins: { + * gridviewdragdrop: true, + * cellediting: { + * clicksToEdit: 1 + * } + * }, + * + * The keys are `id`'s as well as the default type alias. + * + * The `plugins` config can also be an array of plugin aliases: + * + * plugins: [ 'cellediting', 'gridviewdragdrop' ], + * + * An array can also contain elements that are config objects with a `ptype` property + * holding the type alias: + * + * plugins: ['gridviewdragdrop', { + * ptype: 'cellediting', + * clicksToEdit: 1 + * }], + * + * @since 2.3.0 + */ + /** + * @cfg {"north"/"south"/"east"/"west"/"center"} [region=undefined] + * Defines the region inside {@link Ext.layout.container.Border border layout}. + * + * Possible values: + * + * - north - Positions component at top. + * - south - Positions component at bottom. + * - east - Positions component at right. + * - west - Positions component at left. + * - center - Positions component at the remaining space. + * There **must** be a component with `region: "center"` in every border layout. + */ + /** + * @cfg {Object} renderData + * + * The data used by {@link #renderTpl} in addition to the following property values of the component: + * + * - id + * - ui + * - uiCls + * - baseCls + * - componentCls + * - frame + * + * See {@link #renderSelectors} and {@link #cfg-childEls} for usage examples. + */ + /** + * @cfg {Object} renderSelectors + * An object containing properties specifying CSS selectors which identify child elements + * created by the render process. + * + * After the Component's internal structure is rendered according to the {@link #renderTpl}, this object is iterated through, + * and the found Elements are added as properties to the Component using the `renderSelector` property name. + * + * For example, a Component which renders a title and description into its element: + * + * Ext.create('Ext.Component', { + * renderTo: Ext.getBody(), + * renderTpl: [ + * '

{title}

', + * '

{desc}

' + * ], + * renderData: { + * title: "Error", + * desc: "Something went wrong" + * }, + * renderSelectors: { + * titleEl: 'h1.title', + * descEl: 'p' + * }, + * listeners: { + * afterrender: function(cmp){ + * // After rendering the component will have a titleEl and descEl properties + * cmp.titleEl.setStyle({color: "red"}); + * } + * } + * }); + * + * The use of `renderSelectors` is deprecated (for performance reasons). The above + * code should be refactored into something like this: + * + * Ext.create('Ext.Component', { + * renderTo: Ext.getBody(), + * renderTpl: [ + * '

{title}

', + * '

{desc}

' + * ], + * renderData: { + * title: "Error", + * desc: "Something went wrong" + * }, + * childEls: [ + * 'titleEl', + * 'descEl' + * ] + * }); + * + * To use `childEls` yet retain the use of selectors (which remains as expensive as + * `renderSelectors`): + * + * Ext.create('Ext.Component', { + * renderTo: Ext.getBody(), + * renderTpl: [ + * '

{title}

', + * '

{desc}

' + * ], + * renderData: { + * title: "Error", + * desc: "Something went wrong" + * }, + * childEls: { + * titleEl: { selectNode: 'h1.title' }, + * descEl: { selectNode: 'p' } + * } + * }); + * + * @deprecated 5.0 Use {@link #cfg-childEls} instead. + */ + /** + * @cfg {String/HTMLElement/Ext.dom.Element} renderTo + * Specify the `id` of the element, a DOM element or an existing Element that this component will be rendered into. + * + * **Notes:** + * + * Do *not* use this option if the Component is to be a child item of a {@link Ext.container.Container Container}. + * It is the responsibility of the {@link Ext.container.Container Container}'s + * {@link Ext.container.Container#layout layout manager} to render and manage its child items. + * + * When using this config, a call to `render()` is not required. + * + * See also: {@link #method-render}. + * + * @since 2.3.0 + */ + /** + * @cfg {Ext.XTemplate/String/String[]} renderTpl + * An {@link Ext.XTemplate XTemplate} used to create the internal structure inside this Component's encapsulating + * {@link #getEl Element}. + * + * You do not normally need to specify this. For the base classes {@link Ext.Component} and + * {@link Ext.container.Container}, this defaults to **`null`** which means that they will be initially rendered + * with no internal structure; they render their {@link #getEl Element} empty. The more specialized + * classes with complex DOM structures provide their own template definitions. + * + * This is intended to allow the developer to create application-specific utility Components with customized + * internal structure. + * + * Upon rendering, any created child elements may be automatically imported into object properties using the + * {@link #renderSelectors} and {@link #cfg-childEls} options. + * @protected + */ + renderTpl: '{%this.renderContent(out,values)%}', + /** + * @cfg {Boolean/Object} resizable + * Specify as `true` to apply a {@link Ext.resizer.Resizer Resizer} to this Component after rendering. + * + * May also be specified as a config object to be passed to the constructor of {@link Ext.resizer.Resizer Resizer} + * to override any defaults. By default the Component passes its minimum and maximum size, and uses + * `{@link Ext.resizer.Resizer#dynamic}: false` + */ + /** + * @cfg {String} resizeHandles + * A valid {@link Ext.resizer.Resizer} handles config string. Only applies when resizable = true. + */ + resizeHandles: 'all', + /** + * @cfg {Boolean/Number} shrinkWrap + * + * The possible values for shrinkWrap are: + * + * - 0 (or `false`): Neither width nor height depend on content. + * - 1: Width depends on content (shrink wraps), but height does not. + * - 2: Height depends on content (shrink wraps), but width does not. + * - 3 (or `true`): Both width and height depend on content (shrink wrap). + * + * In CSS terms, shrink-wrap width is analogous to an inline-block element as opposed + * to a block-level element. + * + * @localdoc ##Non-Panel Components + * + * The shrinkWrap config is a class-level config and should be used when defining a + * subclass. + * It is not intended to be set as a config on instances of a given component. + * + * For non-Panel components, shrinkWrap is a descriptive config only. It should be + * set when defining your own custom class including the DOM elements used to + * construct the component. The shrinkWrap property does not itself apply styling on + * the component elements. Rather, it should describe the CSS styling you've applied + * to your custom component (_refer to the numeric matrix above_). + * + * When a component is owned by a container the layout of that container will inspect + * the component's shrinkWrap property during layout. The layout then uses the + * content-wrapping policy described by shrinkWrap to correctly size and position the + * container's child items. + */ + shrinkWrap: 2, + /** + * @cfg stateEvents + * @inheritdoc Ext.state.Stateful#cfg-stateEvents + * @localdoc By default the following stateEvents are added: + * + * - {@link #event-resize} + */ + /** + * @cfg {String/Object} style + * A custom style specification to be applied to this component's Element. Should be a valid argument to + * {@link Ext.dom.Element#applyStyles}. + * + * new Ext.panel.Panel({ + * title: 'Some Title', + * renderTo: Ext.getBody(), + * width: 400, height: 300, + * layout: 'form', + * items: [{ + * xtype: 'textarea', + * style: { + * width: '95%', + * marginBottom: '10px' + * } + * }, + * new Ext.button.Button({ + * text: 'Send', + * minWidth: '100', + * style: { + * marginBottom: '10px' + * } + * }) + * ] + * }); + * + * @since 1.1.0 + */ + /** + * @cfg {Boolean} toFrontOnShow + * True to automatically call {@link #toFront} when the {@link #method-show} method is called on an already visible, + * floating component. + */ + toFrontOnShow: true, + /** + * @cfg {Ext.XTemplate/Ext.Template/String/String[]} tpl + * An {@link Ext.Template}, {@link Ext.XTemplate} or an array of strings to form an Ext.XTemplate. Used in + * conjunction with the `{@link #data}` and `{@link #tplWriteMode}` configurations. + * + * @since 3.4.0 + */ + /** + * @property {Boolean} synthetic + * This property is `true` if the component was created internally by the framework + * and is not explicitly user-defined. This is set for such things as `Splitter` + * instances managed by `border` and `box` layouts. + * @private + */ + synthetic: false, + /** + * @cfg {String} tplWriteMode + * The Ext.(X)Template method to use when updating the content area of the Component. + * See `{@link Ext.XTemplate#overwrite}` for information on default mode. + * + * @since 3.4.0 + */ + tplWriteMode: 'overwrite', + /** + * @cfg {String} ui + * A UI style for a component. + */ + ui: 'default', + /** + * @cfg {String[]} uiCls + * An array of of `classNames` which are currently applied to this component. + * @private + */ + uiCls: [], + /** + * @cfg {String/String[]} userCls + * One or more CSS classes to add to the component's primary element. This config + * is intended solely for use by the component instantiator (the "user"), not by + * derived classes. + * + * For example: + * + * items: [{ + * xtype: 'button', + * userCls: 'my-button' + * ... + * }] + * @accessor + */ + userCls: null, + /** + * @cfg {Number} weight + * A value to control how Components are laid out in a {@link Ext.layout.container.Border Border} layout or as docked items. + * + * In a Border layout, this can control how the regions (not the center) region lay out if the west or east take full height + * or if the north or south region take full width. Also look at the {@link Ext.layout.container.Border#regionWeights} on the Border layout. An example to show how you can + * take control of this is: + * + * Ext.create('Ext.container.Viewport', { + * layout : 'border', + * defaultType : 'panel', + * items : [ + * { + * region : 'north', + * title : 'North', + * height : 100 + * }, + * { + * region : 'south', + * title : 'South', + * height : 100, + * weight : -25 + * }, + * { + * region : 'west', + * title : 'West', + * width : 200, + * weight : 15 + * }, + * { + * region : 'east', + * title : 'East', + * width : 200 + * }, + * { + * region : 'center', + * title : 'center' + * } + * ] + * }); + * + * If docked items, the weight will order how the items are laid out. Here is an example to put a {@link Ext.toolbar.Toolbar} above + * a {@link Ext.panel.Panel}'s header: + * + * Ext.create('Ext.panel.Panel', { + * renderTo : document.body, + * width : 300, + * height : 300, + * title : 'Panel', + * html : 'Panel Body', + * dockedItems : [ + * { + * xtype : 'toolbar', + * items : [ + * { + * text : 'Save' + * } + * ] + * }, + * { + * xtype : 'toolbar', + * weight : -10, + * items : [ + * { + * text : 'Remove' + * } + * ] + * } + * ] + * }); + */ + weight: null, + /** + * @cfg {Number|String} width + * The width of this component. A numeric value will be interpreted as the number of + * pixels; a string value will be treated as a CSS value with units. + */ + /** + * @cfg {Ext.enums.Widget} xtype + * **Note:** Only applies to {@link Ext.Component} derived classes when used as + * a config in {@link Ext#define Ext.define}. + * + * This property provides a shorter alternative to creating objects than using a full + * class name. Using `xtype` is the most common way to define component instances, + * especially in a container. For example, the items in a form containing text fields + * could be created explicitly like so: + * + * items: [ + * Ext.create('Ext.form.field.Text', { + * fieldLabel: 'Foo' + * }), + * Ext.create('Ext.form.field.Text', { + * fieldLabel: 'Bar' + * }), + * Ext.create('Ext.form.field.Number', { + * fieldLabel: 'Num' + * }) + * ] + * + * But by using `xtype`, the above becomes: + * + * items: [ + * { + * xtype: 'textfield', + * fieldLabel: 'Foo' + * }, + * { + * xtype: 'textfield', + * fieldLabel: 'Bar' + * }, + * { + * xtype: 'numberfield', + * fieldLabel: 'Num' + * } + * ] + * + * When the `xtype` is common to many items, {@link Ext.container.Container#defaultType} + * is another way to specify the `xtype` for all items that don't have an explicit `xtype`: + * + * defaultType: 'textfield', + * items: [ + * { fieldLabel: 'Foo' }, + * { fieldLabel: 'Bar' }, + * { fieldLabel: 'Num', xtype: 'numberfield' } + * ] + * + * Each member of the `items` array is now just a "configuration object". These objects + * are used to create and configure component instances. A configuration object can be + * manually used to instantiate a component using {@link Ext#widget}: + * + * var text1 = Ext.create('Ext.form.field.Text', { + * fieldLabel: 'Foo' + * }); + * + * // or alternatively: + * + * var text1 = Ext.widget({ + * xtype: 'textfield', + * fieldLabel: 'Foo' + * }); + * + * This conversion of configuration objects into instantiated components is done when + * a container is created as part of its {Ext.container.AbstractContainer#initComponent} + * process. As part of the same process, the `items` array is converted from its raw + * array form into a {@link Ext.util.MixedCollection} instance. + * + * You can define your own `xtype` on a custom {@link Ext.Component component} by specifying + * the `xtype` property in {@link Ext#define}. For example: + * + * Ext.define('MyApp.PressMeButton', { + * extend: 'Ext.button.Button', + * xtype: 'pressmebutton', + * text: 'Press Me' + * }); + * + * Care should be taken when naming an `xtype` in a custom component because there is + * a single, shared scope for all xtypes. Third part components should consider using + * a prefix to avoid collisions. + * + * Ext.define('Foo.form.CoolButton', { + * extend: 'Ext.button.Button', + * xtype: 'ux-coolbutton', + * text: 'Cool!' + * }); + * + * See {@link Ext.enums.Widget} for list of all available xtypes. + * + * @since 2.3.0 + */ + /** + * @cfg {Number} tabIndex + * DOM tabIndex attribute for this component's {@link #focusEl}. + */ + // *********************************************************************************** + // End Config + // *********************************************************************************** + //
+ // + // *********************************************************************************** + // Begin Properties + // *********************************************************************************** + /** + * @private + */ + allowDomMove: true, + /** + * @property {Boolean} autoGenId + * `true` indicates an `id` was auto-generated rather than provided by configuration. + * @private + */ + autoGenId: false, + /** + * @private + */ + borderBoxCls: Ext.baseCSSPrefix + 'border-box', + /** + * @property {Number} componentLayoutCounter + * @private + * The number of component layout calls made on this object. + */ + componentLayoutCounter: 0, + /** + * @property {String} contentPaddingProperty + * The name of the padding property that is used by the layout to manage + * padding. See {@link Ext.layout.container.Auto#managePadding managePadding} + */ + contentPaddingProperty: 'padding', + /** + * @private + */ + deferLayouts: false, + /** + * @property {Ext.Container} floatParent + * **Only present for {@link #cfg-floating} Components which were inserted as child items of Containers.** + * + * There are other similar relationships such as the {@link Ext.button.Button button} which activates a {@link Ext.button.Button#cfg-menu menu}, or the + * {@link Ext.menu.Item menu item} which activated a {@link Ext.menu.Item#cfg-menu submenu}, or the + * {@link Ext.grid.column.Column column header} which activated the column menu. + * + * These differences are abstracted away by the {@link #up} method. + * + * Floating Components that are programmatically {@link Ext.Component#method-render rendered} will not have a `floatParent` + * property. + * + * See {@link #cfg-floating} and {@link #zIndexManager} + * @readonly + */ + /** + * @property {Object} frameSize + * @readonly + * Indicates the width of any framing elements which were added within the encapsulating + * element to provide graphical, rounded borders. See the {@link #frame} config. This + * property is `null` if the component is not framed. + * + * This is an object containing the frame width in pixels for all four sides of the + * Component containing the following properties: + * + * @property {Number} [frameSize.top=0] The width of the top framing element in pixels. + * @property {Number} [frameSize.right=0] The width of the right framing element in pixels. + * @property {Number} [frameSize.bottom=0] The width of the bottom framing element in pixels. + * @property {Number} [frameSize.left=0] The width of the left framing element in pixels. + * @property {Number} [frameSize.width=0] The total width of the left and right framing elements in pixels. + * @property {Number} [frameSize.height=0] The total height of the top and right bottom elements in pixels. + */ + frameSize: null, + /** + * @private + */ + horizontalPosProp: 'left', + /** + * @property {Boolean} isComponent + * `true` in this class to identify an object as an instantiated Component, or subclass thereof. + */ + isComponent: true, + /** + * @property {Boolean} _isLayoutRoot + * Setting this property to `true` causes the {@link #isLayoutRoot} method to return + * `true` and stop the search for the top-most component for a layout. + * @protected + */ + _isLayoutRoot: false, + /** + * @private + */ + layoutSuspendCount: 0, + /** + * @cfg {Boolean} liquidLayout + * Components that achieve their internal layout results using solely CSS with no JS + * intervention must set this to true. This allows the component to opt out of the + * layout run when used inside certain container layouts such as {@link + * Ext.layout.container.Form Form} and {@link Ext.layout.container.Auto Auto} + * resulting in a performance gain. The following components currently use liquid + * layout (`liquidLayout: true`): + * + * - All Form Fields (subclasses of {@link Ext.form.field.Base}) + * - {@link Ext.button.Button} + * + * It is important to keep in mind that components using liquidLayout do not fire + * the following events: + * + * - {@link #event-resize} + * - {@link #event-boxready} + * + * In addition, liquidLayout components do not call the following template methods: + * + * - {@link #method!afterComponentLayout} + * - {@link #method!onBoxReady} + * - {@link #method!onResize} + * + * Any component that needs to fire these events or to have these methods called during + * its life cycle needs to set `liquidLayout` to `false`. The following example + * demonstrates how to enable the resize event for a + * {@link Ext.form.field.TextArea TextArea Field}: + * + * @example + * var win = Ext.create({ + * xtype: 'window', + * title: 'Resize This Window!', + * height: 100, + * width: 200, + * layout: 'anchor', + * items: [{ + * xtype: 'textarea', + * anchor: '0 0', + * liquidLayout: false // allows the textarea to fire "resize" + * }] + * }), + * textfield = win.items.getAt(0); + * + * win.show(); + * + * textfield.on('resize', function(textfield, width, height) { + * Ext.Msg.alert('Text Field Resized', 'width: ' + width + ', height: ' + height); + * }); + * + * Use caution when setting `liquidLayout` to `false` as it carries a performance penalty + * since it means the layout system must perform expensive DOM reads to determine the + * Component's size. + */ + liquidLayout: false, + /** + * @property {Boolean} maskOnDisable + * This is an internal flag that you use when creating custom components. By default this is set to `true` which means + * that every component gets a mask when it's disabled. Components like FieldContainer, FieldSet, Field, Button, Tab + * override this property to `false` since they want to implement custom disable logic. + */ + maskOnDisable: true, + /** + * @property {Ext.Container} ownerCt + * This Component's owner {@link Ext.container.Container Container} (is set automatically + * when this Component is added to a Container). + * + * *Important.* This is not a universal upwards navigation pointer. It indicates the Container which owns and manages + * this Component if any. There are other similar relationships such as the {@link Ext.button.Button button} which activates a {@link Ext.button.Button#cfg-menu menu}, or the + * {@link Ext.menu.Item menu item} which activated a {@link Ext.menu.Item#cfg-menu submenu}, or the + * {@link Ext.grid.column.Column column header} which activated the column menu. + * + * These differences are abstracted away by the {@link #up} method. + * + * **Note**: to access items within the Container see {@link #itemId}. + * @readonly + * @since 2.3.0 + */ + /** + * @property {Boolean} rendered + * Indicates whether or not the component has been rendered. + * @readonly + * @since 1.1.0 + */ + rendered: false, + /** + * @private + */ + rootCls: Ext.baseCSSPrefix + 'body', + /** + * @private + */ + scrollerCls: Ext.baseCSSPrefix + 'scroll-scroller', + /** + * @property {Object} scrollFlags + * An object property which provides unified information as to which dimensions are + * scrollable based upon the {@link #scrollable} settings (And for *views* of trees and + * grids, the owning panel's {@link Ext.panel.Table#scroll scroll} setting). + * + * Note that if you set overflow styles using the {@link #style} config or + * {@link Ext.panel.Panel#bodyStyle bodyStyle} config, this object does not include + * that information. Use {@link #scrollable} if you need to access these flags. + * + * This object has the following properties: + * @property {Boolean} scrollFlags.x `true` if this Component is scrollable + * horizontally - style setting may be `'auto'` or `'scroll'`. + * @property {Boolean} scrollFlags.y `true` if this Component is scrollable + * vertically - style setting may be `'auto'` or `'scroll'`. + * @property {Boolean} scrollFlags.both `true` if this Component is scrollable both + * horizontally and vertically. + * @property {String} scrollFlags.overflowX The `overflow-x` style setting, `'auto'` + * or `'scroll'` or `''`. + * @property {String} scrollFlags.overflowY The `overflow-y` style setting, `'auto'` + * or `'scroll'` or `''`. + * @readonly + * @private + */ + _scrollFlags: { + auto: { + // x:auto, y:auto + auto: { + overflowX: 'auto', + overflowY: 'auto', + x: true, + y: true, + both: true + }, + // x:auto, y:false + 'false': { + overflowX: 'auto', + overflowY: 'hidden', + x: true, + y: false, + both: false + }, + // x:auto, y:scroll + scroll: { + overflowX: 'auto', + overflowY: 'scroll', + x: true, + y: true, + both: true + } + }, + 'false': { + // x:false, y:auto + auto: { + overflowX: 'hidden', + overflowY: 'auto', + x: false, + y: true, + both: false + }, + // x:false, y:false + 'false': { + overflowX: 'hidden', + overflowY: 'hidden', + x: false, + y: false, + both: false + }, + // x:false, y:scroll + scroll: { + overflowX: 'hidden', + overflowY: 'scroll', + x: false, + y: true, + both: false + } + }, + scroll: { + // x:scroll, y:auto + auto: { + overflowX: 'scroll', + overflowY: 'auto', + x: true, + y: true, + both: true + }, + // x:scroll, y:false + 'false': { + overflowX: 'scroll', + overflowY: 'hidden', + x: true, + y: false, + both: false + }, + // x:scroll, y:scroll + scroll: { + overflowX: 'scroll', + overflowY: 'scroll', + x: true, + y: true, + both: true + } + }, + none: { + overflowX: '', + overflowY: '', + x: false, + y: false, + both: false + } + }, + _scrollableCfg: { + x: { + x: true, + y: false + }, + y: { + x: false, + y: true + }, + horizontal: { + x: true, + y: false + }, + vertical: { + x: false, + y: true + }, + both: { + x: true, + y: true + }, + 'true': { + x: true, + y: true + } + }, + validIdRe: Ext.validIdRe, + // *********************************************************************************** + // End Properties + // *********************************************************************************** + // + // + // *********************************************************************************** + // Begin Events + // *********************************************************************************** + /** + * @event afterlayoutanimation + * This event first after a component's layout has been updated by a layout that + * included animation (e.g., a {@link Ext.panel.Panel panel} in an + * {@link Ext.layout.container.Accordion accordion} layout). + * @param {Ext.Component} this + * @since 6.0.0 + */ + /** + * @event beforeactivate + * Fires before a Component has been visually activated. Returning `false` from an event listener can prevent + * the activate from occurring. + * + * **Note** This event is only fired if this Component is a child of a {@link Ext.container.Container} + * that uses {@link Ext.layout.container.Card} as it's layout. + * @param {Ext.Component} this + */ + /** + * @event activate + * Fires after a Component has been visually activated. + * + * **Note** This event is only fired if this Component is a child of a {@link Ext.container.Container} + * that uses {@link Ext.layout.container.Card} as it's layout or this Component is a floating Component. + * @param {Ext.Component} this + */ + /** + * @event beforedeactivate + * Fires before a Component has been visually deactivated. Returning `false` from an event listener can + * prevent the deactivate from occurring. + * + * **Note** This event is only fired if this Component is a child of a {@link Ext.container.Container} + * that uses {@link Ext.layout.container.Card} as it's layout. + * @param {Ext.Component} this + */ + /** + * @event deactivate + * Fires after a Component has been visually deactivated. + * + * **Note** This event is only fired if this Component is a child of a {@link Ext.container.Container} + * that uses {@link Ext.layout.container.Card} as it's layout or this Component is a floating Component. + * @param {Ext.Component} this + */ + /** + * @event added + * Fires after a Component had been added to a Container. + * @param {Ext.Component} this + * @param {Ext.container.Container} container Parent Container + * @param {Number} pos position of Component + * @since 3.4.0 + */ + /** + * @event disable + * Fires after the component is disabled. + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event enable + * Fires after the component is enabled. + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event beforeshow + * Fires before the component is shown when calling the {@link Ext.Component#method-show show} method. Return `false` from an event + * handler to stop the show. + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event show + * Fires after the component is shown when calling the {@link Ext.Component#method-show show} method. + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event beforehide + * Fires before the component is hidden when calling the {@link Ext.Component#method-hide hide} method. Return `false` from an event + * handler to stop the hide. + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event hide + * Fires after the component is hidden. Fires after the component is hidden when calling the {@link Ext.Component#method-hide hide} + * method. + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event removed + * Fires when a component is removed from an Ext.container.Container + * @param {Ext.Component} this + * @param {Ext.container.Container} ownerCt Container which holds the component + * @since 3.4.0 + */ + /** + * @event beforerender + * Fires before the component is {@link #rendered}. Return `false` from an event handler to stop the + * {@link #method-render}. + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event render + * Fires after the component markup is {@link #rendered}. + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event afterrender + * Fires after the component rendering is finished. + * + * The `afterrender` event is fired after this Component has been {@link #rendered}, been post-processed by any + * `afterRender` method defined for the Component. + * @param {Ext.Component} this + * @since 3.4.0 + */ + /** + * @event boxready + * Fires *one time* - after the component has been laid out for the first time at its initial size. + * + * This event does not fire on components that use {@link #cfg-liquidLayout}, such as + * {@link Ext.button.Button Buttons} and {@link Ext.form.field.Base Form Fields}. + * @param {Ext.Component} this + * @param {Number} width The initial width. + * @param {Number} height The initial height. + */ + /** + * @event beforedestroy + * Fires before the component is destroyed. + * + * **Note:** This event should not be used to try to veto the destruction sequence by returning + * `false`, even though this is often permitted in other "before" events. Doing so will have + * unpredictable side-effects and can result in partially destroyed objects. Instead look to + * other events like {@link Ext.panel.Panel#event!beforeclose beforeclose} that occur prior to + * the call to the {@link Ext.Base#method!destroy destroy} method. + * + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event destroy + * Fires after the component is {@link #method-destroy}ed. + * @param {Ext.Component} this + * @since 1.1.0 + */ + /** + * @event resize + * Fires after the component is resized. Note that this does *not* fire when the component is first laid out at its initial + * size. To hook that point in the life cycle, use the {@link #boxready} event. + * + * This event does not fire on components that use {@link #cfg-liquidLayout}, such as + * {@link Ext.button.Button Buttons} and {@link Ext.form.field.Base Form Fields}. + * @param {Ext.Component} this + * @param {Number} width The new width that was set. + * @param {Number} height The new height that was set. + * @param {Number} oldWidth The previous width. + * @param {Number} oldHeight The previous height. + */ + /** + * @event move + * Fires after the component is moved. + * @param {Ext.Component} this + * @param {Number} x The new x position. + * @param {Number} y The new y position. + */ + // *********************************************************************************** + // End Events + // *********************************************************************************** + // + /** + * Creates new Component. + * @param {Ext.dom.Element/String/Object} config The configuration options may be specified as either: + * + * - **an element** : it is set as the internal element and its id used as the component id + * - **a string** : it is assumed to be the id of an existing element and is used as the component id + * - **anything else** : it is assumed to be a standard config object and is applied to the component + */ + constructor: function(config) { + var me = this, + i, len, xhooks, controller, autoScroll, overflowX, overflowY, scrollable; + config = config || {}; + if (config.initialConfig) { + // Being initialized from an Ext.Action instance... + if (config.isAction) { + me.baseAction = config; + } + config = config.initialConfig; + } + // component cloning / action set up + else if (config.tagName || config.dom || Ext.isString(config)) { + // element object + config = { + applyTo: config, + id: config.id || config + }; + } + // Make initialConfig available early so that config getters may access it + /** + * @property {Object} initialConfig + * @readonly + * The config object passed to the constructor during Component creation. + */ + me.initialConfig = config; + me.$iid = ++Ext.$nextIid; + // We want to determine very early on whether or not we are a reference holder, + // so peek at either the incoming config or the class config to see if we have + // a controller defined. + if ((config && config.controller) || me.config.controller) { + me.referenceHolder = true; + } + // Ensure that we have an id early so that config getters may access it + me.getId(); + me.protoEl = new Ext.util.ProtoElement(); + me.$calledInitConfig = true; + me.initConfig(config); + delete me.$calledInitConfig; + if (me.scrollable == null) { + autoScroll = me.autoScroll; + if (autoScroll) { + scrollable = !!autoScroll; + } else { + overflowX = me.overflowX; + overflowY = me.overflowY; + if (overflowX || overflowY) { + scrollable = { + x: (overflowX && overflowX !== 'hidden') ? overflowX : false, + y: (overflowY && overflowY !== 'hidden') ? overflowY : false + }; + } + } + if (scrollable) { + me.setScrollable(scrollable); + } + } + xhooks = me.xhooks; + if (xhooks) { + delete me.xhooks; + Ext.override(me, xhooks); + } + me.mixins.elementCt.constructor.call(me); + if (!me.validIdRe.test(me.id)) { + Ext.raise('Invalid component "id": "' + me.id + '"'); + } + if (!me.validIdRe.test(me.itemId)) { + Ext.raise('Invalid component "itemId": "' + me.itemId + '"'); + } + me.setupProtoEl(); + // initComponent, beforeRender, or event handlers may have set the style or `cls` property since the `protoEl` was set up + // so we must apply styles and classes here too. + if (me.cls) { + me.initialCls = me.cls; + me.protoEl.addCls(me.cls); + } + if (me.style) { + me.initialStyle = me.style; + me.protoEl.setStyle(me.style); + } + me.renderData = me.renderData || {}; + me.initComponent(); + // initComponent gets a chance to change the id property before registering + if (!me.preventRegister) { + Ext.ComponentManager.register(me); + } + me.mixins.state.constructor.call(me); + me.addStateEvents('resize'); + controller = me.getController(); + if (controller) { + controller.init(me); + } + // Move this into Observable? + if (me.plugins) { + for (i = 0 , len = me.plugins.length; i < len; i++) { + me.plugins[i] = me.initPlugin(me.plugins[i]); + } + } + me.loader = me.getLoader(); + if (me.disabled) { + me.disabled = false; + me.disable(true); + } + if (me.renderTo) { + me.render(me.renderTo); + } + // EXTJSIV-1935 - should be a way to do afterShow or something, but that + // won't work. Likewise, rendering hidden and then showing (w/autoShow) has + // implications to afterRender so we cannot do that. + // Auto show only works unilaterally on *uncontained* Components. + // If contained, then it is the Container's responsibility to do the showing at next layout time. + if (me.autoShow && !me.$initParent) { + me.show(); + } + if (Ext.isDefined(me.disabledClass)) { + if (Ext.isDefined(Ext.global.console)) { + Ext.global.console.warn('Ext.Component: disabledClass has been deprecated. Please use disabledCls.'); + } + me.disabledCls = me.disabledClass; + delete me.disabledClass; + } + // If we were configured from an instance of Ext.Action, (or configured with a baseAction option), + // register this Component as one of its items + if (me.baseAction) { + me.baseAction.addComponent(me); + } + }, + beforeInitConfig: function() { + if (!this.$calledInitConfig) { + Ext.raise('initConfig should not be called by subclasses, it will be called by Ext.Component'); + } + this.mixins.observable.constructor.call(this); + }, + // + // *********************************************************************************** + // Begin Component Methods + // *********************************************************************************** + /** + * Adds a CSS class to the top level element representing this component. + * @param {String/String[]} cls The CSS class name to add. + * @return {Ext.Component} Returns the Component to allow method chaining. + */ + addCls: function(cls) { + var me = this, + el = me.rendered ? me.el : me.protoEl; + el.addCls.apply(el, arguments); + return me; + }, + /** + * Adds a `cls` to the `uiCls` array, which will also call {@link #addUIClsToElement} and adds to all elements of this + * component. + * @param {String/String[]} classes A string or an array of strings to add to the `uiCls`. + * @param {Boolean} [skip] `true` to skip adding it to the class and do it later (via the return). + */ + addClsWithUI: function(classes, skip) { + var me = this, + clsArray = [], + i = 0, + uiCls = me.uiCls = Ext.Array.clone(me.uiCls), + activeUI = me.activeUI, + length, cls; + if (typeof classes === "string") { + classes = (classes.indexOf(' ') < 0) ? [ + classes + ] : Ext.String.splitWords(classes); + } + length = classes.length; + for (; i < length; i++) { + cls = classes[i]; + if (cls && !me.hasUICls(cls)) { + uiCls.push(cls); + // We can skip this bit if there isn't an activeUI because we'll be called again from setUI + if (activeUI) { + clsArray = clsArray.concat(me.addUIClsToElement(cls)); + } + } + } + if (skip !== true && activeUI) { + me.addCls(clsArray); + } + return clsArray; + }, + /** + * Called by the layout system after the Component has been laid out. + * + * This method is not called on components that use {@link #cfg-liquidLayout}, such as + * {@link Ext.button.Button Buttons} and {@link Ext.form.field.Base Form Fields}. + * + * @param {Number} width The width that was set + * @param {Number} height The height that was set + * @param {Number/undefined} oldWidth The old width, or `undefined` if this was the initial layout. + * @param {Number/undefined} oldHeight The old height, or `undefined` if this was the initial layout. + * + * @template + * @protected + */ + afterComponentLayout: function(width, height, oldWidth, oldHeight) { + var me = this, + scroller = me.scrollable; + if (++me.componentLayoutCounter === 1) { + me.afterFirstLayout(width, height); + } else if (me.manageLayoutScroll && scroller) { + scroller.restoreState(); + } + if (width !== oldWidth || height !== oldHeight) { + me.onResize(width, height, oldWidth, oldHeight); + } + if (me.floating) { + me.onAfterFloatLayout(); + } + }, + /** + * @protected + * Adds a plugin. May be called at any time in the component's life cycle. + */ + addPlugin: function(plugin) { + var me = this; + plugin = me.constructPlugin(plugin); + if (me.plugins) { + me.plugins.push(plugin); + } else { + me.plugins = [ + plugin + ]; + } + if (me.pluginsInitialized) { + me.initPlugin(plugin); + } + return plugin; + }, + /** + * Save a property to the given state object if it is not its default or configured + * value. + * + * @param {Object} state The state object. + * @param {String} propName The name of the property on this object to save. + * @param {String} [value] The value of the state property (defaults to `this[propName]`). + * @return {Object} The state object or a new object if state was `null` and the property + * was saved. + * @protected + */ + addPropertyToState: function(state, propName, value) { + var me = this, + len = arguments.length; + // If the property is inherited, it is a default and we don't want to save it to + // the state, however if we explicitly specify a value, always save it + if (len === 3 || me.hasOwnProperty(propName)) { + if (len < 3) { + value = me[propName]; + } + // If the property has the same value as was initially configured, again, we + // don't want to save it. + if (value !== me.initialConfig[propName]) { + (state || (state = {}))[propName] = value; + } + } + return state; + }, + /** + * Method which adds a specified UI + `uiCls` to the components element. Can be overridden + * to add the UI to more than just the component's element. + * @param {String} uiCls The UI class to add to the element. + * @protected + */ + addUIClsToElement: function(uiCls) { + var me = this, + baseClsUI = me.baseCls + '-' + me.ui + '-' + uiCls, + result = [ + Ext.baseCSSPrefix + uiCls, + me.baseCls + '-' + uiCls, + baseClsUI + ], + childEls, childElName, el, suffix; + if (me.rendered && me.frame && !Ext.supports.CSS3BorderRadius) { + // Loop through each frame element, and if they are defined add the ui: + baseClsUI += '-'; + childEls = me.getChildEls(); + for (childElName in childEls) { + suffix = childEls[childElName].frame; + if (suffix && suffix !== true) { + el = me[childElName]; + if (el) { + el.addCls(baseClsUI + suffix); + } + } + } + } + return result; + }, + /** + * Method which removes a specified UI + `uiCls` from the components element. The `cls` + * which is added to the element will be: `this.baseCls + '-' + ui + uiCls`. + * @param {String} uiCls The UI class to remove from the element. + * @protected + */ + removeUIClsFromElement: function(uiCls) { + var me = this, + baseClsUI = me.baseCls + '-' + me.ui + '-' + uiCls, + result = [ + Ext.baseCSSPrefix + uiCls, + me.baseCls + '-' + uiCls, + baseClsUI + ], + childEls, childElName, el, suffix; + if (me.rendered && me.frame && !Ext.supports.CSS3BorderRadius) { + // Loop through each frame element, and if they are defined remove the ui: + baseClsUI += '-'; + childEls = me.getChildEls(); + for (childElName in childEls) { + suffix = childEls[childElName].frame; + if (suffix && suffix !== true) { + el = me[childElName]; + if (el) { + el.removeCls(baseClsUI + suffix); + } + } + } + } + return result; + }, + /** + * @private + */ + adjustPosition: function(x, y) { + var me = this, + floatParentBox; + // Floating Components being positioned in their ownerCt have to be made absolute. + if (me.isContainedFloater()) { + floatParentBox = me.floatParent.getTargetEl().getViewRegion(); + x += floatParentBox.left; + y += floatParentBox.top; + } + return { + x: x, + y: y + }; + }, + /** + * Invoked after the Component has been hidden. + * + * Gets passed the same `callback` and `scope` parameters that #onHide received. + * + * @param {Function} [callback] + * @param {Object} [scope] + * @template + * @protected + */ + afterHide: function(callback, scope) { + var me = this, + container = me.ownerFocusableContainer; + // Top level focusEnter is only valid when a floating component stack is visible. + delete me.getInherited().topmostFocusEvent; + me.hiddenByLayout = null; + // Only lay out if there is an owning layout which might be affected by the hide + if (me.ownerLayout) { + me.updateLayout({ + isRoot: false + }); + } + if (container && !container.onFocusableChildHide.$nullFn) { + container.onFocusableChildHide(me); + } + me.fireHierarchyEvent('hide'); + me.fireEvent('hide', me); + // Have to fire callback the last, because it may destroy the Component + // and firing subsequent events will become impossible. Strictly speaking, + // hide event handler above could have destroyed the Component too, but + // in such case it is the responsibility of the callback to accommodate. + Ext.callback(callback, scope || me); + }, + /** + * Template method called after a Component has been positioned. + * + * @param {Number} x + * @param {Number} y + * + * @template + * @protected + */ + afterSetPosition: function(x, y) { + var me = this; + me.onPosition(x, y); + if (me.hasListeners.move) { + me.fireEvent('move', me, x, y); + } + }, + /** + * Invoked after the Component is shown (after #onShow is called). + * + * Gets passed the same parameters as #show. + * + * @param {String/Ext.dom.Element} [animateTarget] + * @param {Function} [callback] + * @param {Object} [scope] + * @template + * @protected + */ + afterShow: function(animateTarget, callback, scope) { + var me = this, + myEl = me.el, + zim = me.zIndexManager, + fromBox, toBox, ghostPanel; + // Default to configured animate target if none passed + animateTarget = me.getAnimateTarget(animateTarget); + // We are going to churn the zIndex stack, so suspend its reactions. + if (zim) { + zim.suspendReflow(); + } + // Need to be able to ghost the Component + if (!me.ghost) { + animateTarget = null; + } + // If we're animating, kick of an animation of the ghost from the target to the *Element* current box + if (animateTarget) { + toBox = { + x: myEl.getX(), + y: myEl.getY(), + width: myEl.dom.offsetWidth, + height: myEl.dom.offsetHeight + }; + fromBox = { + x: animateTarget.getX(), + y: animateTarget.getY(), + width: animateTarget.dom.offsetWidth, + height: animateTarget.dom.offsetHeight + }; + // Will move to front with underlying mask, and focus if necessary. + me.fireHierarchyEvent('show'); + // Ghost will brifly be topmost, but it is focusable: false + // And ghosting does not disturb focus. + ghostPanel = me.ghost(); + ghostPanel.el.stopAnimation(); + // Shunting it offscreen immediately, *before* the Animation class grabs it ensure no flicker. + ghostPanel.setX(-10000); + me.ghostBox = toBox; + ghostPanel.el.animate({ + from: fromBox, + to: toBox, + listeners: { + afteranimate: function() { + if (!me.destroying) { + ghostPanel.componentLayout.lastComponentSize = null; + me.unghost(); + me.ghostBox = null; + me.onShowComplete(callback, scope); + } + } + } + }); + } else { + me.onShowComplete(callback, scope); + me.fireHierarchyEvent('show'); + } + // Take a run through the zIndex stack ensuring modal, focus and topmost is correct + if (zim) { + zim.resumeReflow(true); + } + }, + animate: function(animObj) { + var me = this, + hasToWidth, hasToHeight, toHeight, toWidth, to, clearWidth, clearHeight, curWidth, w, curHeight, h, isExpanding, wasConstrained, wasConstrainedHeader, passedCallback, oldOverflow; + animObj = animObj || {}; + to = animObj.to || {}; + if (Ext.fx.Manager.hasFxBlock(me.id)) { + return me; + } + hasToWidth = Ext.isDefined(to.width); + if (hasToWidth) { + toWidth = Ext.Number.constrain(to.width, me.minWidth, me.maxWidth); + } + hasToHeight = Ext.isDefined(to.height); + if (hasToHeight) { + toHeight = Ext.Number.constrain(to.height, me.minHeight, me.maxHeight); + } + // Special processing for animating Component dimensions. + if (!animObj.dynamic && (hasToWidth || hasToHeight)) { + curWidth = (animObj.from ? animObj.from.width : undefined) || me.getWidth(); + w = curWidth; + curHeight = (animObj.from ? animObj.from.height : undefined) || me.getHeight(); + h = curHeight; + isExpanding = false; + if (hasToHeight && toHeight > curHeight) { + h = toHeight; + isExpanding = true; + } + if (hasToWidth && toWidth > curWidth) { + w = toWidth; + isExpanding = true; + } + // During animated sizing, overflow has to be hidden to clip expanded content + if (hasToHeight || hasToWidth) { + oldOverflow = me.el.getStyle('overflow'); + if (oldOverflow !== 'hidden') { + me.el.setStyle('overflow', 'hidden'); + } + } + // If any dimensions are being increased, we must resize the internal structure + // of the Component, but then clip it by sizing its encapsulating element back to original dimensions. + // The animation will then progressively reveal the larger content. + if (isExpanding) { + clearWidth = !Ext.isNumber(me.width); + clearHeight = !Ext.isNumber(me.height); + // Lay out this component at the new, larger size to get the internals correctly laid out. + // Then size the encapsulating **Element** back down to size. + // We will then just animate the element to reveal the correctly laid out content. + me.setSize(w, h); + me.el.setSize(curWidth, curHeight); + if (clearWidth) { + delete me.width; + } + if (clearHeight) { + delete me.height; + } + } + if (hasToWidth) { + to.width = toWidth; + } + if (hasToHeight) { + to.height = toHeight; + } + } + // No constraining during the animate - the "to" size has already been calculated with respect to all settings. + // Arrange to reinstate any constraining after the animation has completed + wasConstrained = me.constrain; + wasConstrainedHeader = me.constrainHeader; + if (wasConstrained || wasConstrainedHeader) { + me.constrain = me.constrainHeader = false; + passedCallback = animObj.callback; + animObj.callback = function() { + me.constrain = wasConstrained; + me.constrainHeader = wasConstrainedHeader; + // Call the original callback if any + if (passedCallback) { + passedCallback.call(animObj.scope || me, arguments); + } + if (oldOverflow !== 'hidden') { + me.el.setStyle('overflow', oldOverflow); + } + }; + } + return me.mixins.animate.animate.apply(me, arguments); + }, + applyScrollable: function(scrollable, oldScrollable) { + var me = this, + rendered = me.rendered, + scrollableCfg; + if (scrollable) { + if (scrollable === true || typeof scrollable === 'string') { + scrollableCfg = me._scrollableCfg[scrollable]; + if (!scrollableCfg) { + Ext.raise("'" + scrollable + "' is not a valid value for 'scrollable'"); + } + scrollable = scrollableCfg; + } + if (oldScrollable) { + oldScrollable.setConfig(scrollable); + scrollable = oldScrollable; + } else { + scrollable = Ext.Object.chain(scrollable); + // don't mutate the user's config + if (rendered) { + // we create the scroller without an element by default (because the + // element is not available at configuration time) and then assign + // the element in onBoxReady. If we got here it means the scroller + // is being configured after render, so we need to make sure the + // element is in its config object + scrollable.element = me.getOverflowEl(); + } + scrollable = Ext.scroll.Scroller.create(scrollable, me.scrollableType); + scrollable.component = me; + } + } + // We are disabling scrolling for this Component. + else if (oldScrollable) { + scrollable = oldScrollable; + oldScrollable.setConfig({ + x: false, + y: false + }); + } + if (me.rendered && !me.destroying && !me.destroyed) { + if (scrollable) { + me.getOverflowStyle(); + } else // refresh the scrollFlags + { + me.scrollFlags = me._scrollFlags.none; + } + me.updateLayout(); + } + return scrollable; + }, + /** + * This method is required by the Scroller to return the scrollable client region + * @return {Ext.util.Region} The scrolling viewport region. + * @private + */ + getScrollableClientRegion: function() { + return this.getScrollable().getElement().getClientRegion(); + }, + applyTouchAction: function(touchAction, oldTouchAction) { + if (oldTouchAction != null) { + touchAction = Ext.merge({}, oldTouchAction, touchAction); + } + return touchAction; + }, + /** + * Invoked before the Component is destroyed. + * This method is deprecated, override {@link #onDestroy} instead. + * + * @method + * @template + * @protected + * @deprecated 6.2.0 Please override {@link #onDestroy} instead + */ + beforeDestroy: Ext.emptyFn, + /** + * Occurs before componentLayout is run. In previous releases, this method could + * return `false` to prevent its layout but that is not supported in Ext JS 4.1 or + * higher. This method is simply a notification of the impending layout to give the + * component a chance to adjust the DOM. Ideally, DOM reads should be avoided at this + * time to reduce expensive document reflows. + * + * @template + * @protected + */ + beforeLayout: function() { + if (this.floating) { + this.onBeforeFloatLayout(); + } + }, + /** + * @private + * Template method called before a Component is positioned. + * + * Ensures that the position is adjusted so that the Component is constrained if so configured. + */ + beforeSetPosition: function(x, y, animate) { + var me = this, + pos = null, + x0, hasX, hasY, adj; + // Decode members of x if x is an array or an object. + // If it is numeric (including zero), we need do nothing. + if (x) { + // Position in first argument as an array of [x, y] + if (Ext.isNumber(x0 = x[0])) { + animate = y; + y = x[1]; + x = x0; + } + // Position in first argument as object w/ x & y properties + else if ((x0 = x.x) !== undefined) { + animate = y; + y = x.y; + x = x0; + } + } + if (me.constrain || me.constrainHeader) { + pos = me.calculateConstrainedPosition(null, [ + x, + y + ], true); + if (pos) { + x = pos[0]; + y = pos[1]; + } + } + hasX = (x !== undefined); + hasY = (y !== undefined); + if (hasX || hasY) { + // The component's position is the position it was told to be at. + // If it is contained, adjustPosition will add the floatParent's offsets. + me.x = x; + me.y = y; + adj = me.adjustPosition(x, y); + // Set up the return info and store the position in this object + pos = { + x: adj.x, + y: adj.y, + anim: animate, + hasX: hasX, + hasY: hasY + }; + } + return pos; + }, + /** + * Invoked before the Component is shown. + * + * @method + * @template + * @protected + */ + beforeShow: Ext.emptyFn, + /** + * Bubbles up the component/container hierarchy, calling the specified function with each component. The scope + * (*this*) of function call will be the scope provided or the current component. The arguments to the function will + * be the args provided or the current component. If the function returns false at any point, the bubble is stopped. + * + * @param {Function} fn The function to call + * @param {Object} [scope] The scope of the function. Defaults to current node. + * @param {Array} [args] The args to call the function with. Defaults to passing the current component. + * @return {Ext.Component} this + */ + bubble: function(fn, scope, args) { + var p = this; + while (p) { + if (fn.apply(scope || p, args || [ + p + ]) === false) { + break; + } + p = p.getBubbleTarget(); + } + return this; + }, + clearListeners: function() { + var me = this; + me.mixins.observable.clearListeners.call(me); + me.mixins.componentDelegation.clearDelegatedListeners.call(me); + }, + /** + * Clone the current component using the original config values passed into this instance by default. + * @param {Object} overrides A new config containing any properties to override in the cloned version. + * An id property can be passed on this object, otherwise one will be generated to avoid duplicates. + * @return {Ext.Component} clone The cloned copy of this component + */ + cloneConfig: function(overrides) { + overrides = overrides || {}; + var id = overrides.id || Ext.id(), + cfg = Ext.applyIf(overrides, this.initialConfig), + self; + cfg.id = id; + self = Ext.getClass(this); + // prevent dup id + return new self(cfg); + }, + /** + * Destroys the Component. This method **must not** be overridden because Component + * destruction sequence is conditional; if a `beforedestroy` handler returns `false` + * we must abort destruction. + * + * To add extra functionality to destruction time in a subclass, override the + * {@link #doDestroy} method. + * + * @since 1.1.0 + */ + destroy: function() { + var me = this; + if (!me.hasListeners.beforedestroy || me.fireEvent('beforedestroy', me) !== false) { + // isDestroying added for compat reasons + me.isDestroying = me.destroying = true; + me.doDestroy(); + // We need to defer clearing listeners until after doDestroy() completes, + // to let the interested parties fire events until the very end. + me.clearListeners(); + // isDestroying added for compat reasons + me.isDestroying = me.destroying = false; + me.callParent(); + // Ext.Base + // ComponentDelegation mixin does not install "after" interceptor on the + // base class destructor; Observable mixin does install the interceptor + // but cannot destroy itself automatically because Components are + // conditionally destructible. + me.mixins.componentDelegation.destroyComponentDelegation.call(me); + me.mixins.observable.destroyObservable.call(me, true); + } + }, + /** + * Perform the actual destruction sequence. + * + * As a rule of thumb, subclasses should destroy their child Components and/or other objects + * before calling parent method. Any object references will be nulled after this method + * has finished, to prevent the possibility of memory leaks. + * + * @private + * @since 6.2.0 + */ + doDestroy: function() { + var me = this, + focusableContainer = me.ownerFocusableContainer, + container = me.container, + selectors = me.renderSelectors, + selector, ownerCt, el; + ownerCt = me.floatParent || me.ownerCt; + if (me.floating) { + delete me.floatParent; + // A zIndexManager is stamped into a *floating* Component when it is added + // to a Container. If it has no zIndexManager at render time, it is assigned + // to the global Ext.WindowManager instance. + // It can also happen that Container's zIndexManager is destroyed before this. + if (me.zIndexManager && !me.zIndexManager.destroyed) { + me.zIndexManager.unregister(me); + } + // Some components may set floating as config object, which will be nulled + // in the base destructor. We need this property in Containers, so set it + // to Boolean instead. + me.floating = true; + } + me.removeBindings(); + if (!me.beforeDestroy.$emptyFn) { + me.beforeDestroy(); + } + me.destroyBindable(); + if (ownerCt && ownerCt.remove) { + ownerCt.remove(me, { + destroy: false + }); + } + me.stopAnimation(); + // Ensure that any ancillary components are destroyed. + if (me.rendered) { + Ext.destroy(me.loadMask, me.dd, me.resizer, me.proxy, me.proxyWrap, me.resizerComponent, me.scrollable, me.contentEl); + } + if (focusableContainer && !focusableContainer.onFocusableChildDestroy.$nullFn) { + focusableContainer.onFocusableChildDestroy(me); + } + if (me.focusable) { + me.destroyFocusable(); + } + // Destroying the floatingItems ZIndexManager will also destroy descendant floating Components + Ext.destroy(me.componentLayout, me.loadMask, me.floatingDescendants); + if (!me.onDestroy.$emptyFn) { + me.onDestroy(); + } + // Attempt to destroy all plugins + Ext.destroy(me.plugins); + if (me.rendered) { + Ext.Component.cancelLayout(me, true); + } + me.componentLayout = null; + if (me.hasListeners.destroy) { + me.fireEvent('destroy', me); + } + if (!me.preventRegister) { + Ext.ComponentManager.unregister(me); + } + me.mixins.state.destroy.call(me); + if (me.floating) { + me.onFloatDestroy(); + } + // make sure we clean up the element references after removing all events + if (me.rendered) { + if (me.showListenerIE) { + me.showListenerIE.destroy(); + me.showListenerIE = null; + } + if (!me.preserveElOnDestroy) { + me.el.destroy(); + } + // We don't own the container element so can't just destroy it as that would + // remove it from the DOM; we have to remove the Element instance from cache + // though. + if (me.collectContainerElement && container) { + if (!container.destroyed) { + container.collect(); + } + me.container = null; + } + me.el.component = null; + me.mixins.elementCt.destroy.call(me); + // removes childEls + if (selectors) { + for (selector in selectors) { + if (selectors.hasOwnProperty(selector)) { + el = me[selector]; + if (el) { + // in case any other code may have already removed it + delete me[selector]; + el.destroy(); + } + } + } + } + // This is a very special boolean that warrants explicit clearing + me.rendered = false; + } + }, + /** + * Disable the component. + * @param {Boolean} [silent=false] Passing `true` will suppress the `disable` event from being fired. + * @param fromParent (private) + * @since 1.1.0 + */ + disable: function(silent, fromParent) { + var me = this, + container = me.ownerFocusableContainer, + inherited = me.getInherited(); + if (!fromParent) { + inherited.disabled = true; + me.savedDisabled = true; + } + if (me.maskOnDisable) { + inherited.disableMask = true; + } + if (!me.disabled) { + if (container && !container.beforeFocusableChildDisable.$nullFn) { + container.beforeFocusableChildDisable(me); + } + me.addCls(me.disabledCls); + if (me.rendered) { + me.onDisable(); + } else { + me.disableOnRender = true; + } + me.disabled = true; + if (silent !== true) { + me.fireEvent('disable', me); + } + if (container && !container.onFocusableChildDisable.$nullFn) { + container.onFocusableChildDisable(me); + } + } + return me; + }, + doFireEvent: function(eventName, args, bubbles) { + var me = this, + ret; + ret = me.mixins.observable.doFireEvent.call(me, eventName, args, bubbles); + // The Component instance can be destroyed in the handler, in which case + // we can't fire delegated events on it anymore. + if (ret !== false && !me.destroyed) { + ret = me.mixins.componentDelegation.doFireDelegatedEvent.call(me, eventName, args); + } + return ret; + }, + /** + * Enable the component + * @param {Boolean} [silent=false] Passing `true` will suppress the `enable` event from being fired. + * @param fromParent (private) + * @since 1.1.0 + */ + enable: function(silent, fromParent) { + var me = this, + container = me.ownerFocusableContainer, + inherited = me.getInherited(); + if (!fromParent) { + delete me.getInherited().disabled; + me.savedDisabled = false; + } + if (me.maskOnDisable) { + delete inherited.disableMask; + } + if (me.disabled) { + // A parent is asking us to enable, but if we were disabled directly, keep + // our current state + if (!(fromParent && inherited.hasOwnProperty('disabled'))) { + if (container && !container.beforeFocusableChildEnable.$nullFn) { + container.beforeFocusableChildEnable(me); + } + me.disableOnRender = false; + me.removeCls(me.disabledCls); + if (me.rendered) { + me.onEnable(); + } + me.disabled = false; + if (silent !== true) { + me.fireEvent('enable', me); + } + if (container && !container.onFocusableChildEnable.$nullFn) { + container.onFocusableChildEnable(me); + } + } + } + return me; + }, + /** + * Find a container above this component at any level by a custom function. If the passed function returns true, the + * container will be returned. + * + * See also the {@link Ext.Component#up up} method. + * + * @param {Function} fn The custom function to call with the arguments (container, this component). + * @return {Ext.container.Container} The first Container for which the custom function returns true + */ + findParentBy: function(fn) { + var p; + // Iterate up the owner chain until we don't have one, or we find an ancestor which matches using the selector function. + for (p = this.getRefOwner(); p && !fn(p, this); p = p.getRefOwner()) {} + // do nothing + return p || null; + }, + /** + * Find a container above this component at any level by xtype or class + * + * See also the {@link Ext.Component#up up} method. + * + * @param {String/Ext.Class} xtype The xtype string for a component, or the class of the component directly + * @return {Ext.container.Container} The first Container which matches the given xtype or class + */ + findParentByType: function(xtype) { + return Ext.isFunction(xtype) ? this.findParentBy(function(p) { + return p.self === xtype || p.constructor === xtype; + }) : this.up(xtype); + }, + /** + * Retrieves plugin from this component's collection by its `ptype`. + * + * var grid = Ext.create('Ext.grid.Panel', { + * store: { + * fields: ['name'], + * data: [{ + * name: 'Scott Pilgrim' + * }] + * }, + * columns: [{ + * header: 'Name', + * dataIndex: 'name', + * editor: 'textfield', + * flex: 1 + * }], + * selType: 'cellmodel', + * plugins: [{ + * ptype: 'cellediting', + * clicksToEdit: 1, + * id: 'myplugin' + * }], + * height: 200, + * width: 400, + * renderTo: Ext.getBody() + * }); + * + * grid.findPlugin('cellediting'); // the cellediting plugin + * + * **Note:** See also {@link #getPlugin} + * + * @param {String} ptype The Plugin's `ptype` as specified by the class's + * {@link Ext.Class#cfg-alias alias} configuration. + * @return {Ext.plugin.Abstract} plugin instance or `undefined` if not found + */ + findPlugin: function(ptype) { + var i, + plugins = this.plugins, + ln = plugins && plugins.length; + for (i = 0; i < ln; i++) { + if (plugins[i].ptype === ptype) { + return plugins[i]; + } + } + }, + getAnimateTarget: function(target) { + target = target || this.animateTarget; + if (target) { + target = target.isComponent ? target.getEl() : Ext.get(target); + } + return target || null; + }, + /** + * @protected + * Implements an upward event bubbling policy. By default a Component bubbles events up to its {@link #getRefOwner reference owner}. + * + * Component subclasses may implement a different bubbling strategy by overriding this method. + */ + getBubbleTarget: function() { + return this.getRefOwner(); + }, + getComponentLayout: function() { + var me = this; + if (!me.componentLayout || !me.componentLayout.isLayout) { + me.setComponentLayout(Ext.layout.Layout.create(me.componentLayout, 'autocomponent')); + } + return me.componentLayout; + }, + /** + * Retrieves the top level element representing this component. + * @return {Ext.dom.Element} + * @since 1.1.0 + */ + getEl: function() { + return this.el; + }, + /** + * Gets the current height of the component's underlying element. + * @return {Number} + */ + getHeight: function() { + return this.el.getHeight(); + }, + /** + * Called by `getInherited` to initialize the inheritedState the first time it is + * requested. + * @protected + */ + initInheritedState: function(inheritedState) { + var me = this, + layout = me.componentLayout; + if (me.hidden) { + inheritedState.hidden = true; + } + if (me.collapseImmune) { + inheritedState.collapseImmune = true; + } + if (me.modelValidation !== undefined) { + inheritedState.modelValidation = me.modelValidation; + } + if (me.savedDisabled) { + inheritedState.disabled = true; + } + me.mixins.bindable.initInheritedState.call(me, inheritedState); + if (layout && layout.initInheritedState) { + layout.initInheritedState(inheritedState); + } + }, + /** + * Retrieves the `id` of this component. Will auto-generate an `id` if one has not already been set. + * @return {String} + */ + getId: function() { + var me = this, + xtype; + // If we have no id, attempt to gather it from our configuration. + // Autogenerate it if none was configured. + if (!(me.id || (me.id = me.initialConfig.id))) { + xtype = me.getXType(); + if (xtype) { + xtype = xtype.replace(Ext.Component.INVALID_ID_CHARS_Re, '-'); + } else { + xtype = Ext.name.toLowerCase() + '-comp'; + } + me.id = xtype + '-' + me.getAutoId(); + } + return me.id; + }, + /** + * Returns the value of {@link #itemId} assigned to this component, or when that + * is not set, returns the value of {@link #id}. + * @return {String} + */ + getItemId: function() { + return this.itemId || this.id; + }, + /** + * Gets the {@link Ext.ComponentLoader} for this Component. + * @return {Ext.ComponentLoader} The loader instance, null if it doesn't exist. + */ + getLoader: function() { + var me = this, + loader = me.loader; + if (loader) { + if (!loader.isLoader) { + me.loader = new Ext.ComponentLoader(Ext.apply({ + target: me + }, loader)); + } else { + loader.setTarget(me); + } + return me.loader; + } + return null; + }, + /** + * @protected + * Returns the element which is masked by the {@link #mask} method, or into which the {@link #setLoading LoadMask} is rendered into. + * + * The default implementation uses the {@link #maskElement} configuration to access the Component's child element by name. By default, {@link #maskElement} + * is `null` which means that `null` is returned from this method indicating that the mask needs to be rendered into the document because + * component structure should not be contaminated by mask elements. + * + * Some subclasses may override this method if they have knowledge about external structures where a mask could usefully be rendered. + * + * For example a {@link Ext.view.Table GridView} will request that its owning {@link Ext.panel.Table GridPanel} be masked. The + * GridPanel will have its own implementation of `getMaskTarget` which will return the element dictated by its own {@link #maskElement} + * Panels use `"el"` as their {@link #maskElement} by default, but that could be overridden to be `"body"` to leave toolbars and the header + * mouse-accessible. + * + */ + getMaskTarget: function() { + return this.maskElement ? this[this.maskElement] : null; + }, + /** + * Retrieves a plugin from this component's collection by its `id`. + * + * var grid = Ext.create('Ext.grid.Panel', { + * store: { + * fields: ['name'], + * data: [{ + * name: 'Scott Pilgrim' + * }] + * }, + * columns: [{ + * header: 'Name', + * dataIndex: 'name', + * editor: 'textfield', + * flex: 1 + * }], + * selType: 'cellmodel', + * plugins: [{ + * ptype: 'cellediting', + * clicksToEdit: 1, + * id: 'myplugin' + * }], + * height: 200, + * width: 400, + * renderTo: Ext.getBody() + * }); + * + * grid.getPlugin('myplugin'); // the cellediting plugin + * + * **Note:** See also {@link #findPlugin}. Prior to 6.2.0 the plugin had to have a + * `{@link Ext.plugin.Abstract#pluginId pluginId}` property but this can now be just + * `{@link Ext.plugin.Abstract#id id}`. Both are supported (so plugins with a + * matching `pluginId` are still found) but `id` is preferred. + * + * @param {String} id The `id` set on the plugin config object. + * @return {Ext.plugin.Abstract} plugin instance or `null` if not found + */ + getPlugin: function(id) { + var i, + plugins = this.plugins, + ln = plugins && plugins.length, + plugin; + for (i = 0; i < ln; i++) { + plugin = plugins[i]; + // pre-6.2 we only considered pluginId property... + if (plugin.id === id || plugin.pluginId === id) { + return plugin; + } + } + return null; + }, + /** + * Gets the current XY position of the component's underlying element. + * @param {Boolean} [local=false] If true the element's left and top are returned instead of page XY. + * @return {Number[]} The XY position of the element (e.g., [100, 200]) + */ + getPosition: function(local) { + var me = this, + xy, + isContainedFloater = me.isContainedFloater(), + floatParentBox; + // Local position for non-floaters means element's local position + if ((local === true) && !isContainedFloater) { + return [ + me.getLocalX(), + me.getLocalY() + ]; + } + xy = me.getXY(); + // Local position for floaters means position relative to the container's target element + if ((local === true) && isContainedFloater) { + floatParentBox = me.floatParent.getTargetEl().getViewRegion(); + xy[0] -= floatParentBox.left; + xy[1] -= floatParentBox.top; + } + return xy; + }, + /** + * Returns the "x" scroll position for this component. Only applicable for + * {@link #scrollable} components + * @return {Number} + */ + getScrollX: function() { + var scroller = this.getScrollable(); + return scroller ? scroller.getPosition().x : 0; + }, + /** + * Returns the "y" scroll position for this component. Only applicable for + * {@link #scrollable} components + * @return {Number} + */ + getScrollY: function() { + var scroller = this.getScrollable(); + return scroller ? scroller.getPosition().y : 0; + }, + /** + * Gets the current size of the component's underlying element. + * @param {Boolean} [contentSize] true to get the width/size minus borders and padding + * @return {Object} An object containing the element's size: + * @return {Number} return.width + * @return {Number} return.height + */ + getSize: function(contentSize) { + return this.el.getSize(contentSize); + }, + /** + * Returns an object that describes how this component's width and height are managed. + * All of these objects are shared and should not be modified. + * + * @return {Object} The size model for this component. + * @return {Ext.layout.SizeModel} return.width The {@link Ext.layout.SizeModel size model} + * for the width. + * @return {Ext.layout.SizeModel} return.height The {@link Ext.layout.SizeModel size model} + * for the height. + * @protected + */ + getSizeModel: function(ownerCtSizeModel) { + var me = this, + models = Ext.layout.SizeModel, + ownerContext = me.componentLayout.ownerContext, + width = me.width, + height = me.height, + typeofWidth, typeofHeight, hasPixelWidth, hasPixelHeight, hasWidthStyle, hasHeightStyle, heightModel, ownerLayout, policy, shrinkWrap, topLevel, widthModel, + // floating === a floating Component, floated === a border layout's slideout view of a region. + isFloating = me.floating || me.floated; + if (ownerContext) { + // If we are in the middle of a running layout, always report the current, + // dynamic size model rather than recompute it. This is not (only) a time + // saving thing, but a correctness thing since we cannot get the right answer + // otherwise. + widthModel = ownerContext.widthModel; + heightModel = ownerContext.heightModel; + } + if (!widthModel || !heightModel) { + hasPixelWidth = ((typeofWidth = typeof width) === 'number'); + hasPixelHeight = ((typeofHeight = typeof height) === 'number'); + topLevel = isFloating || !(ownerLayout = me.ownerLayout); + // Floating or no owner layout, e.g. rendered using renderTo + if (topLevel) { + policy = Ext.layout.Layout.prototype.autoSizePolicy; + shrinkWrap = isFloating ? 3 : me.shrinkWrap; + if (hasPixelWidth) { + widthModel = models.configured; + } + if (hasPixelHeight) { + heightModel = models.configured; + } + } else { + policy = ownerLayout.getItemSizePolicy(me, ownerCtSizeModel); + shrinkWrap = ownerLayout.isItemShrinkWrap(me); + } + if (ownerContext) { + ownerContext.ownerSizePolicy = policy; + } + shrinkWrap = (shrinkWrap === true) ? 3 : (shrinkWrap || 0); + // false->0, true->3 + // Now that we have shrinkWrap as a 0-3 value, we need to turn off shrinkWrap + // bits for any dimension that has a configured size not in pixels. These must + // be read from the DOM. + // + if (topLevel && shrinkWrap) { + if (width && typeofWidth === 'string') { + shrinkWrap &= 2; + // percentage, "30em" or whatever - not width shrinkWrap + hasWidthStyle = true; + } + if (height && typeofHeight === 'string') { + shrinkWrap &= 1; + // percentage, "30em" or whatever - not height shrinkWrap + hasHeightStyle = true; + } + } + if (shrinkWrap !== 3) { + if (!ownerCtSizeModel) { + ownerCtSizeModel = me.ownerCt && me.ownerCt.getSizeModel(); + } + if (ownerCtSizeModel) { + shrinkWrap |= (ownerCtSizeModel.width.shrinkWrap ? 1 : 0) | (ownerCtSizeModel.height.shrinkWrap ? 2 : 0); + } + } + if (!widthModel) { + if (!policy.setsWidth && !(me.frame && hasWidthStyle)) { + if (hasPixelWidth) { + widthModel = models.configured; + } else { + widthModel = (shrinkWrap & 1) ? models.shrinkWrap : models.natural; + } + } else if (policy.readsWidth) { + if (hasPixelWidth) { + widthModel = models.calculatedFromConfigured; + } else { + widthModel = (shrinkWrap & 1) ? models.calculatedFromShrinkWrap : models.calculatedFromNatural; + } + } else { + widthModel = models.calculated; + } + } + if (!heightModel) { + if (!policy.setsHeight && !(me.frame && hasHeightStyle)) { + if (hasPixelHeight) { + heightModel = models.configured; + } else { + heightModel = (shrinkWrap & 2) ? models.shrinkWrap : models.natural; + } + } else if (policy.readsHeight) { + if (hasPixelHeight) { + heightModel = models.calculatedFromConfigured; + } else { + heightModel = (shrinkWrap & 2) ? models.calculatedFromShrinkWrap : models.calculatedFromNatural; + } + } else { + heightModel = models.calculated; + } + } + } + // We return one of the cached objects with the proper "width" and "height" as the + // sizeModels we have determined. + return widthModel.pairsByHeightOrdinal[heightModel.ordinal]; + }, + /** + * The supplied default state gathering method for the Component class. + * + * This method returns dimension settings such as `flex`, `anchor`, `width` and `height` along with `collapsed` + * state. + * + * Subclasses which implement more complex state should call the superclass's implementation, and apply their state + * to the result if this basic state is to be saved. + * + * Note that Component state will only be saved if the Component has a {@link #stateId} and there as a StateProvider + * configured for the document. + * + * @return {Object} + */ + getState: function() { + var me = this, + state = null, + sizeModel = me.getSizeModel(); + if (sizeModel.width.configured) { + state = me.addPropertyToState(state, 'width'); + } + if (sizeModel.height.configured) { + state = me.addPropertyToState(state, 'height'); + } + return state; + }, + getUserCls: function() { + return this.userCls; + }, + setUserCls: function(cls) { + var me = this, + was = me.userCls; + if (cls !== was) { + me.userCls = cls; + if (me.rendered) { + me.el.replaceCls(was, cls); + } + } + return was; + }, + /** + * Gets the current width of the component's underlying element. + * @return {Number} + */ + getWidth: function() { + return this.el.getWidth(); + }, + /** + * Gets the xtype for this component as registered with {@link Ext.ComponentManager}. For a list of all available + * xtypes, see the {@link Ext.Component} header. Example usage: + * + * var t = new Ext.form.field.Text(); + * alert(t.getXType()); // alerts 'textfield' + * + * @return {String} The xtype + */ + getXType: function() { + return this.self.xtype; + }, + /** + * Returns this Component's xtype hierarchy as a slash-delimited string. For a list of all available xtypes, see the + * {@link Ext.Component} header. + * + * **If using your own subclasses, be aware that a Component must register its own xtype to participate in + * determination of inherited xtypes.** + * + * Example usage: + * + * @example + * var t = new Ext.form.field.Text(); + * alert(t.getXTypes()); // alerts 'component/field/textfield' + * + * @return {String} The xtype hierarchy string + * + * @since 2.3.0 + */ + getXTypes: function() { + var self = this.self, + xtypes, parentPrototype, parentXtypes; + if (!self.xtypes) { + xtypes = []; + parentPrototype = this; + while (parentPrototype) { + parentXtypes = parentPrototype.xtypes; + if (parentXtypes !== undefined) { + xtypes.unshift.apply(xtypes, parentXtypes); + } + parentPrototype = parentPrototype.superclass; + } + self.xtypeChain = xtypes; + self.xtypes = xtypes.join('/'); + } + return self.xtypes; + }, + /** + * Checks if the specified CSS class exists on this element's DOM node. + * @param {String} className The CSS class to check for. + * @return {Boolean} `true` if the class exists, else `false`. + * @method + */ + hasCls: function(className) { + var el = this.rendered ? this.el : this.protoEl; + return el.hasCls.apply(el, arguments); + }, + /** + * Checks if there is currently a specified `uiCls`. + * @param {String} cls The `cls` to check. + */ + hasUICls: function(cls) { + var me = this, + uiCls = me.uiCls || []; + return Ext.Array.contains(uiCls, cls); + }, + /** + * Hides this Component, setting it to invisible using the configured {@link #cfg-hideMode}. + * @param {String/Ext.dom.Element/Ext.Component} [animateTarget=null] **only valid for {@link #cfg-floating} Components + * such as {@link Ext.window.Window Window}s or {@link Ext.tip.ToolTip ToolTip}s, or regular Components which have + * been configured with `floating: true`.**. The target to which the Component should animate while hiding. + * @param {Function} [callback] A callback function to call after the Component is hidden. + * @param {Object} [scope] The scope (`this` reference) in which the callback is executed. + * Defaults to this Component. + * @return {Ext.Component} this + */ + hide: function(animateTarget, callback, scope) { + var me = this, + container = me.ownerFocusableContainer; + if (me.pendingShow) { + // If this is a hierarchically hidden floating component with a pending show + // hide() simply cancels the pending show. + me.pendingShow = false; + } + if (!(me.rendered && !me.isVisible())) { + if (!me.hasListeners.beforehide || me.fireEvent('beforehide', me) !== false || me.hierarchicallyHidden) { + me.getInherited().hidden = me.hidden = true; + if (container && !container.beforeFocusableChildHide.$nullFn) { + container.beforeFocusableChildHide(me); + } + // Order of events is important here. Hierarchy event kicks off + // ZIndexManager's collection sorting and floater activation; + // The hidden flag must be set so that ZIndexManager takes it out of its stack. + me.fireHierarchyEvent('beforehide'); + if (me.rendered) { + me.onHide.apply(me, arguments); + } + } + } + return me; + }, + /** + * The initComponent template method is an important initialization step for a Component. It is intended to be + * implemented by each subclass of Ext.Component to provide any needed constructor logic. The + * initComponent method of the class being created is called first, with each initComponent method + * up the hierarchy to Ext.Component being called thereafter. This makes it easy to implement and, + * if needed, override the constructor logic of the Component at any step in the hierarchy. + * + * The initComponent method **must** contain a call to {@link Ext.Base#method!callParent callParent} in order + * to ensure that the parent class' initComponent method is also called. + * + * All config options passed to the constructor are applied to `this` before initComponent is called, + * so you can simply access them with `this.someOption`. + * + * The following example demonstrates using a dynamic string for the text of a button at the time of + * instantiation of the class. + * + * Ext.define('DynamicButtonText', { + * extend: 'Ext.button.Button', + * + * initComponent: function() { + * this.text = new Date(); + * this.renderTo = Ext.getBody(); + * this.callParent(); + * } + * }); + * + * Ext.onReady(function() { + * Ext.create('DynamicButtonText'); + * }); + * + * @template + * @protected + * @since 1.1.0 + */ + initComponent: function() { + var me = this, + width = me.width, + height = me.height; + // If plugins have been added by a subclass's initComponent before calling up to here (or any components + // that don't have a table view), the processed flag will not have been set, and we must process them again. + // We could just call getPlugins here however most components don't have them so prevent the extra function call. + if (me.plugins && !me.plugins.processed) { + me.constructPlugins(); + } + me.pluginsInitialized = true; + // this will properly (ignore or) constrain the configured width/height to their + // min/max values for consistency. + if (width != null || height != null) { + me.setSize(width, height); + } + if (me.listeners) { + me.on(me.listeners); + me.listeners = null; + } + //change the value to remove any on prototype + if (me.focusable) { + me.initFocusable(); + } + }, + /** + * Initialize any events on this component + * @protected + */ + initEvents: function() { + var me = this, + afterRenderEvents = me.afterRenderEvents, + afterRenderEvent, el, property, index, len; + if (afterRenderEvents) { + for (property in afterRenderEvents) { + el = me[property]; + if (el && el.on) { + afterRenderEvent = afterRenderEvents[property]; + for (index = 0 , len = afterRenderEvent.length; index < len; ++index) { + me.mon(el, afterRenderEvent[index]); + } + } + } + } + if (me.focusable) { + me.initFocusableEvents(); + } + // FocusableContainers are not themselves focusable, but they must process + // their keyMap config + me.initKeyMap(); + }, + /** + * Tests whether this Component matches a {@link Ext.ComponentQuery ComponentQuery} + * selector string. + * @param {String} selector The selector string to test against. + * @return {Boolean} `true` if this Component matches the selector. + */ + is: function(selector) { + return Ext.ComponentQuery.is(this, selector); + }, + /** + * Method to determine whether this Component is currently disabled. + * @return {Boolean} the disabled state of this Component. + */ + isDisabled: function() { + return this.disabled; + }, + /** + * Method to determine whether this Component is draggable. + * @return {Boolean} the draggable state of this component. + */ + isDraggable: function() { + return !!this.draggable; + }, + /** + * Method to determine whether this Component is droppable. + * @return {Boolean} the droppable state of this component. + */ + isDroppable: function() { + return !!this.droppable; + }, + /** + * Method to determine whether this Component is floating. + * @return {Boolean} the floating state of this component. + */ + isFloating: function() { + return this.floating; + }, + /** + * Method to determine whether this Component is currently set to hidden. + * @return {Boolean} the hidden state of this Component. + */ + isHidden: function() { + return this.hidden; + }, + getHidden: function() { + return this.hidden; + }, + isHierarchicallyHidden: function() { + var child = this, + hidden = false, + parent, parentInheritedState; + // It is possible for some components to be immune to collapse meaning the immune + // component remains visible when its direct parent is collapsed, e.g. panel header. + // Because of this, we must walk up the component hierarchy to determine the true + // visible state of the component. + for (; (parent = child.ownerCt || child.floatParent); child = parent) { + parentInheritedState = parent.getInherited(); + if (parentInheritedState.hidden) { + hidden = true; + break; + } + if (child.getInherited().collapseImmune) { + // The child or one of its ancestors is immune to collapse. + if (parent.collapsed && !child.collapseImmune) { + // If the child's direct parent is collapsed, and the child + // itself does not have collapse immunity we know that + // the child is not visible. + hidden = true; + break; + } + } else { + // We have ascended the tree to a point where collapse immunity + // is not in play. This means if any ancestor above this point + // is collapsed, then the component is not visible. + hidden = !!parentInheritedState.collapsed; + break; + } + } + return hidden; + }, + /** + * Checks if this component will be contained by the passed component as part of its + * layout run. If `true`, then the layout on `this` can be skipped because it will be + * encompassed when the layout for `comp` runs. Typical cases where this may be be `false` + * is when asking about floaters nested in containers. + * @param {Ext.Component} ownerCandidate The potential owner. + * @return {Boolean} `true` if this component is a layout child of `comp`. + * + * @private + */ + isLayoutChild: function(ownerCandidate) { + return !this.floating && !!this.up(ownerCandidate); + }, + /** + * Determines whether this Component is the root of a layout. This returns `true` if + * this component can run its layout without assistance from or impact on its owner. + * If this component cannot run its layout given these restrictions, `false` is returned + * and its owner will be considered as the next candidate for the layout root. + * + * Setting the {@link #_isLayoutRoot} property to `true` causes this method to always + * return `true`. This may be useful when updating a layout of a Container which shrink + * wraps content, and you know that it will not change size, and so can safely be the + * topmost participant in the layout run. + * @protected + */ + isLayoutRoot: function() { + var me = this, + ownerLayout = me.ownerLayout; + // Return true if we have been explicitly flagged as the layout root, or if we are floating. + // Sometimes floating Components get an ownerCt ref injected into them which is *not* a true ownerCt, merely + // an upward link for reference purposes. For example a grid column menu is linked to the + // owning header via an ownerCt reference. + if (!ownerLayout || me._isLayoutRoot || me.floating) { + return true; + } + return ownerLayout.isItemLayoutRoot(me); + }, + /** + * Returns `true` if layout is suspended for this component. This can come from direct + * suspension of this component's layout activity ({@link Ext.Container#suspendLayout}) or if one + * of this component's containers is suspended. + * + * @return {Boolean} `true` layout of this component is suspended. + */ + isLayoutSuspended: function() { + var comp = this, + ownerLayout; + while (comp) { + if (comp.layoutSuspendCount || comp.suspendLayout) { + return true; + } + ownerLayout = comp.ownerLayout; + if (!ownerLayout) { + break; + } + // TODO - what about suspending a Layout instance? + // this works better than ownerCt since ownerLayout means "is managed by" in + // the proper sense... some floating components have ownerCt but won't have an + // ownerLayout + comp = ownerLayout.owner; + } + return false; + }, + /** + * Returns `true` if this component is visible. + * + * @param {Boolean} [deep=false] Pass `true` to interrogate the visibility status of all parent Containers to + * determine whether this Component is truly visible to the user. + * + * Generally, to determine whether a Component is hidden, the no argument form is needed. For example when creating + * dynamically laid out UIs in a hidden Container before showing them. + * + * @return {Boolean} `true` if this component is visible, `false` otherwise. + * + * @since 1.1.0 + */ + isVisible: function(deep) { + var me = this, + hidden; + if (me.hidden || !me.rendered || me.destroyed) { + hidden = true; + } else if (deep) { + hidden = me.isHierarchicallyHidden(); + } + return !hidden; + }, + /** + * Tests whether or not this Component is of a specific xtype. This can test whether this Component is descended + * from the xtype (default) or whether it is directly of the xtype specified (`shallow = true`). + * + * **If using your own subclasses, be aware that a Component must register its own xtype to participate in + * determination of inherited xtypes.** + * + * For a list of all available xtypes, see the {@link Ext.Component} header. + * + * Example usage: + * + * @example + * var t = new Ext.form.field.Text(); + * var isText = t.isXType('textfield'); // true + * var isBoxSubclass = t.isXType('field'); // true, descended from Ext.form.field.Base + * var isBoxInstance = t.isXType('field', true); // false, not a direct Ext.form.field.Base instance + * + * @param {String} xtype The xtype to check for this Component + * @param {Boolean} [shallow=false] `true` to check whether this Component is directly of the specified xtype, `false` to + * check whether this Component is descended from the xtype. + * @return {Boolean} `true` if this component descends from the specified xtype, `false` otherwise. + * + * @since 2.3.0 + */ + isXType: function(xtype, shallow) { + return shallow ? (Ext.Array.indexOf(this.xtypes, xtype) !== -1) : !!this.xtypesMap[xtype]; + }, + /** + * Returns masked state for this Component. + * + * @param {Boolean} [deep=false] True to look up this Component's parent masked state. + * + * @return {Boolean} True if masked, false otherwise. + */ + isMasked: function(deep) { + var me = this; + return !!(me.masked || (me.loadMask && me.loadMask.isVisible()) || (deep && me.getInherited().masked)); + }, + /** + * Gets a named template instance for this class. See {@link Ext.XTemplate#getTpl}. + * @param {String} name The name of the property that holds the template. + * @return {Ext.XTemplate} The template, `null` if not found. + * + * @since 6.2.0 + */ + lookupTpl: function(name) { + return Ext.XTemplate.getTpl(this, name); + }, + /** + * Set masked state for this Component. + * + * @param {Boolean} isMasked True if masked, false otherwise. + * @private + */ + setMasked: function(isMasked) { + var me = this, + container = me.ownerFocusableContainer; + if (isMasked) { + me.masked = true; + me.getInherited().masked = isMasked; + } else { + me.masked = false; + delete me.getInherited().masked; + } + if (container && !container.onFocusableChildMasked.$nullFn) { + container.onFocusableChildMasked(me, isMasked); + } + return me; + }, + /** + * Masks this component with a semi-opaque layer and makes the contents unavailable to clicks. + * + * See {@link #unmask}. + * + * @param {String} [msg] A message to show in the center of the mask layer. + * @param {String} [msgCls] A CSS class name to use on the message element in the center of the layer. + * @param {Number} elHeight (private) The height of element to be masked + */ + mask: function(msg, msgCls, elHeight) { + var box = this.lastBox, + // getMaskTarget may be overridden in subclasses/ + // null means that a LoadMask has to be rendered to document.body + // Element masking falls back to masking the local el + target = this.getMaskTarget() || this.el; + // Pass it the height of our element if we know it. + if (box) { + elHeight = box.height; + } + target.mask(msg, msgCls, elHeight); + this.setMasked(true); + }, + /** + * Returns the next node in the Component tree in tree traversal order. + * + * Note that this is not limited to siblings, and if invoked upon a node with no matching siblings, will walk the + * tree to attempt to find a match. Contrast with {@link #nextSibling}. + * @param {String} [selector] A {@link Ext.ComponentQuery ComponentQuery} selector to filter the following nodes. + * @param includeSelf (private) + * @return {Ext.Component} The next node (or the next node which matches the selector). + * Returns `null` if there is no matching node. + */ + nextNode: function(selector, includeSelf) { + var node = this, + ownerCt = node.ownerCt, + result, it, len, i, sib; + // If asked to include self, test me + if (includeSelf && node.is(selector)) { + return node; + } + if (ownerCt) { + for (it = ownerCt.items.items , i = Ext.Array.indexOf(it, node) + 1 , len = it.length; i < len; i++) { + sib = it[i]; + if (sib.is(selector)) { + return sib; + } + if (sib.down) { + result = sib.down(selector); + if (result) { + return result; + } + } + } + return ownerCt.nextNode(selector); + } + return null; + }, + /** + * Returns the next sibling of this Component. + * + * Optionally selects the next sibling which matches the passed {@link Ext.ComponentQuery ComponentQuery} selector. + * + * May also be referred to as **`next()`** + * + * Note that this is limited to siblings, and if no siblings of the item match, `null` is returned. Contrast with + * {@link #nextNode} + * @param {String} [selector] A {@link Ext.ComponentQuery ComponentQuery} selector to filter the following items. + * @return {Ext.Component} The next sibling (or the next sibling which matches the selector). + * Returns `null` if there is no matching sibling. + */ + nextSibling: function(selector) { + var o = this.ownerCt, + it, last, idx, c; + if (o) { + it = o.items; + idx = it.indexOf(this) + 1; + if (idx) { + if (selector) { + for (last = it.getCount(); idx < last; idx++) { + if ((c = it.getAt(idx)).is(selector)) { + return c; + } + } + } else { + if (idx < it.getCount()) { + return it.getAt(idx); + } + } + } + } + return null; + }, + /** + * Method to manage awareness of when components are added to their + * respective Container, firing an #added event. References are + * established at add time rather than at render time. + * + * Allows addition of behavior when a Component is added to a + * Container. At this stage, the Component is in the parent + * Container's collection of child items. After calling the + * superclass's `onAdded`, the `ownerCt` reference will be present, + * and if configured with a ref, the `refOwner` will be set. + * + * @param {Ext.container.Container} container Container which holds the component. + * @param {Number} pos Position at which the component was added. + * @param {Boolean} instanced `false` if this component was instanced by the parent + * container. `true` if the instance already existed when it was passed to the container. + * + * @template + * @protected + * @since 3.4.0 + */ + onAdded: function(container, pos, instanced) { + var me = this; + me.ownerCt = container; + me.onInheritedAdd(me, instanced); + if (me.hasListeners && me.hasListeners.added) { + me.fireEvent('added', me, container, pos); + } + if (Ext.GlobalEvents.hasListeners.added) { + me.fireHierarchyEvent('added'); + } + }, + /** + * Method to manage awareness of when components are removed from their + * respective Container, firing a #removed event. References are properly + * cleaned up after removing a component from its owning container. + * + * Allows addition of behavior when a Component is removed from + * its parent Container. At this stage, the Component has been + * removed from its parent Container's collection of child items, + * but has not been destroyed (It will be destroyed if the parent + * Container's `autoDestroy` is `true`, or if the remove call was + * passed a truthy second parameter). After calling the + * superclass's `onRemoved`, the `ownerCt` and the `refOwner` will not + * be present. + * @param {Boolean} destroying Will be passed as `true` if the Container performing the remove operation will delete this + * Component upon remove. + * + * @template + * @protected + * @since 3.4.0 + */ + onRemoved: function(destroying) { + var me = this, + focusTarget; + // Revert focus to closest sibling or ancestor unless we are being moved + // In which case Ext.container.Container's move methods will handle + // focus restoration. + if (!me.isLayoutMoving && me.el && me.el.contains(Ext.Element.getActiveElement())) { + focusTarget = me.findFocusTarget(); + if (focusTarget) { + focusTarget.focus(); + } + } + if (Ext.GlobalEvents.hasListeners.removed) { + me.fireHierarchyEvent('removed'); + } + if (me.hasListeners.removed) { + me.fireEvent('removed', me, me.ownerCt); + } + me.onInheritedRemove(destroying); + me.ownerCt = me.ownerLayout = null; + }, + /** + * Invoked when this component has first achieved size. This occurs after the + * {@link #componentLayout} has completed its initial run. + * + * This method is not called on components that use {@link #cfg-liquidLayout}, such as + * {@link Ext.button.Button Buttons} and {@link Ext.form.field.Base Form Fields}. + * + * **Note:** If the Component has a {@link Ext.Component#controller ViewController} + * and the controller has a {@link Ext.app.ViewController#boxReady boxReady} method + * it will be called passing the Component and its width and height. + * + * boxReady: function (view, width, height) { + * // ... + * } + * + * @param {Number} width The width of this component + * @param {Number} height The height of this component + * + * @template + * @protected + */ + onBoxReady: function(width, height) { + var me = this, + label; + // We have to do this lookup onBoxReady instead of afterRender + // to ensure that the components that could be referenced in + // me.ariaLabelledBy or me.ariaDescribedBy are already rendered + if (me.ariaLabelledBy || me.ariaDescribedBy) { + if (me.ariaLabelledBy) { + label = me.getAriaLabelEl(me.ariaLabelledBy); + if (label) { + me.ariaEl.dom.setAttribute('aria-labelledby', label); + } + } + if (me.ariaDescribedBy) { + label = me.getAriaLabelEl(me.ariaDescribedBy); + if (label) { + me.ariaEl.dom.setAttribute('aria-describedby', label); + } + } + } + if (me.resizable) { + me.initResizable(me.resizable); + } + // Draggability must be initialized after resizability + // Because if we have to be wrapped, the resizer wrapper must be dragged as a pseudo-Component + if (me.draggable) { + me.initDraggable(); + } + if (me.hasListeners.boxready) { + me.fireEvent('boxready', me, width, height); + } + }, + /** + * Allows addition of behavior to the destroy operation. + * + * @template + * @method + * @protected + */ + onDestroy: Ext.emptyFn, + /** + * Allows addition of behavior to the disable operation. + * After calling the superclass's `onDisable`, the Component will be disabled. + * + * @template + * @protected + */ + onDisable: function() { + var me = this, + dom, nodeName; + if (me.focusable) { + me.disableFocusable(); + } + if (!me.ariaStaticRoles[me.ariaRole]) { + me.ariaEl.dom.setAttribute('aria-disabled', true); + } + // Only mask if we're set to & nobody above us will do so + if (me.maskOnDisable && !me.getInheritedConfig('disableMask', true)) { + dom = me.el.dom; + nodeName = dom.nodeName; + if (me.disabledRe.test(nodeName)) { + dom.disabled = true; + } + if (!me.nonMaskableRe.test(nodeName)) { + me.mask(); + } + } + }, + /** + * Allows addition of behavior to the enable operation. + * After calling the superclass's `onEnable`, the Component will be enabled. + * + * @template + * @protected + */ + onEnable: function() { + var me = this, + dom, nodeName; + if (me.focusable) { + me.enableFocusable(); + } + if (!me.ariaStaticRoles[me.ariaRole]) { + me.ariaEl.dom.setAttribute('aria-disabled', false); + } + if (me.maskOnDisable && me.getInherited().hasOwnProperty('masked')) { + dom = me.el.dom; + nodeName = dom.nodeName; + if (me.disabledRe.test(nodeName)) { + dom.disabled = false; + } + if (!me.nonMaskableRe.test(nodeName)) { + me.unmask(); + } + } + }, + onGlobalShow: function(c) { + if (this.up(c)) { + this.getScrollable().restoreState(); + } + }, + /** + * Allows addition of behavior to the hide operation. After + * calling the superclass's onHide, the Component will be hidden. + * + * Gets passed the same parameters as #hide. + * + * @param {String/Ext.dom.Element/Ext.Component} [animateTarget] + * @param {Function} [callback] Callback function to be called when finished + * @param {Object} [scope] + * + * @template + * @protected + */ + onHide: function(animateTarget, callback, scope) { + var me = this, + ghostPanel, fromSize, toBox; + if (!me.ariaStaticRoles[me.ariaRole] && !me.destroying && !me.destroyed) { + me.ariaEl.dom.setAttribute('aria-hidden', true); + } + // Part of the Focusable mixin API. + // If we have focus now, move focus back to whatever had it before. + me.revertFocus(); + // Default to configured animate target if none passed + animateTarget = me.getAnimateTarget(animateTarget); + // Need to be able to ghost the Component + if (!me.ghost) { + animateTarget = null; + } + // If we're animating, kick off an animation of the ghost down to the target + if (animateTarget) { + toBox = { + x: animateTarget.getX(), + y: animateTarget.getY(), + width: animateTarget.dom.offsetWidth, + height: animateTarget.dom.offsetHeight + }; + ghostPanel = me.ghost(); + ghostPanel.el.stopAnimation(); + fromSize = me.getSize(); + ghostPanel.el.animate({ + to: toBox, + listeners: { + afteranimate: function() { + if (!me.destroying) { + ghostPanel.componentLayout.lastComponentSize = null; + me.unghost(false); + ghostPanel.el.setSize(fromSize); + me.afterHide(callback, scope); + } + } + } + }); + } else { + me.el.hide(); + } + if (!animateTarget) { + me.afterHide(callback, scope); + } + }, + /** + * @method + * Called after the component is moved, this method is empty by default but can be implemented by any + * subclass that needs to perform custom logic after a move occurs. + * + * @param {Number} x The new x position. + * @param {Number} y The new y position. + * + * @template + * @protected + */ + onPosition: Ext.emptyFn, + /** + * Called when the component is resized. + * + * This method is not called on components that use {@link #cfg-liquidLayout}, such as + * {@link Ext.button.Button Buttons} and {@link Ext.form.field.Base Form Fields}. + * + * @param {Number} width The new width that was set + * @param {Number} height The new height that was set + * @param {Number} oldWidth The previous width + * @param {Number} oldHeight The previous height + * + * @method + * @template + * @protected + */ + onResize: function(width, height, oldWidth, oldHeight) { + var me = this; + // constrain is a config on Floating + if (me.floating && me.constrain) { + me.doConstrain(); + } + if (me.hasListeners.resize) { + me.fireEvent('resize', me, width, height, oldWidth, oldHeight); + } + }, + /** + * Invoked when a scroll is initiated on this component via its {@link #scrollable scroller}. + * @method onScrollStart + * @param {Number} x The current x position + * @param {Number} y The current y position + * @template + * @protected + */ + /** + * Invoked when this component is scrolled via its {@link #scrollable scroller}. + * @method onScrollMove + * @param {Number} x The current x position + * @param {Number} y The current y position + * @template + * @protected + */ + /** + * Invoked when a scroll operation is completed via this component's {@link #scrollable scroller}. + * @method onScrollEnd + * @param {Number} x The current x position + * @param {Number} y The current y position + * @template + * @protected + */ + /** + * Allows addition of behavior to the show operation. After + * calling the superclass's onShow, the Component will be visible. + * + * Override in subclasses where more complex behaviour is needed. + * + * Gets passed the same parameters as #show. + * + * @param {String/Ext.dom.Element} [animateTarget] + * @param {Function} [callback] + * @param {Object} [scope] + * + * @template + * @protected + */ + onShow: function() { + var me = this; + if (!me.ariaStaticRoles[me.ariaRole]) { + me.ariaEl.dom.setAttribute('aria-hidden', false); + } + me.el.show(); + me.updateLayout({ + isRoot: false, + context: me._showContext + }); + // Constraining/containing element may have changed size while this Component was hidden + if (me.floating) { + if (me.maximized) { + me.fitContainer(); + } else if (me.constrain) { + me.doConstrain(); + } + } + }, + _showContext: { + show: true + }, + /** + * Invoked after the #afterShow method is complete. + * + * Gets passed the same `callback` and `scope` parameters that #afterShow received. + * + * @param {Function} [callback] + * @param {Object} [scope] + * + * @template + * @protected + */ + onShowComplete: function(callback, scope) { + var me = this, + container = me.ownerFocusableContainer; + if (me.floating) { + me.onFloatShow(); + } + Ext.callback(callback, scope || me); + me.fireEvent('show', me); + if (container && !container.onFocusableChildShow.$nullFn) { + container.onFocusableChildShow(me); + } + delete me.hiddenByLayout; + }, + onShowVeto: Ext.emptyFn, + /** + * Returns the previous node in the Component tree in tree traversal order. + * + * Note that this is not limited to siblings, and if invoked upon a node with no matching siblings, will walk the + * tree in reverse order to attempt to find a match. Contrast with {@link #previousSibling}. + * @param {String} [selector] A {@link Ext.ComponentQuery ComponentQuery} selector to filter the preceding nodes. + * @param includeSelf (private) + * @return {Ext.Component} The previous node (or the previous node which matches the selector). + * Returns `null` if there is no matching node. + */ + previousNode: function(selector, includeSelf) { + var node = this, + ownerCt = node.ownerCt, + result, it, i, sib; + // If asked to include self, test me + if (includeSelf && node.is(selector)) { + return node; + } + if (ownerCt) { + for (it = ownerCt.items.items , i = Ext.Array.indexOf(it, node) - 1; i > -1; i--) { + sib = it[i]; + if (sib.query) { + result = sib.query(selector); + result = result[result.length - 1]; + if (result) { + return result; + } + } + if (sib.is(selector)) { + return sib; + } + } + return ownerCt.previousNode(selector, true); + } + return null; + }, + /** + * Returns the previous sibling of this Component. + * + * Optionally selects the previous sibling which matches the passed {@link Ext.ComponentQuery ComponentQuery} + * selector. + * + * May also be referred to as **`prev()`** + * + * Note that this is limited to siblings, and if no siblings of the item match, `null` is returned. Contrast with + * {@link #previousNode} + * @param {String} [selector] A {@link Ext.ComponentQuery ComponentQuery} selector to filter the preceding items. + * @return {Ext.Component} The previous sibling (or the previous sibling which matches the selector). + * Returns `null` if there is no matching sibling. + */ + previousSibling: function(selector) { + var o = this.ownerCt, + it, idx, c; + if (o) { + it = o.items; + idx = it.indexOf(this); + if (idx !== -1) { + if (selector) { + for (--idx; idx >= 0; idx--) { + if ((c = it.getAt(idx)).is(selector)) { + return c; + } + } + } else { + if (idx) { + return it.getAt(--idx); + } + } + } + } + return null; + }, + /** + * Called by Component#doAutoRender + * + * Register a Container configured `floating: true` with this Component's {@link Ext.ZIndexManager ZIndexManager}. + * + * Components added in this way will not participate in any layout, but will be rendered + * upon first show in the way that {@link Ext.window.Window Window}s are. + */ + registerFloatingItem: function(cmp) { + var me = this; + if (!me.floatingDescendants) { + me.floatingDescendants = new Ext.ZIndexManager(me); + } + me.floatingDescendants.register(cmp); + }, + /** + * Removes a CSS class from the top level element representing this component. + * @param {String/String[]} cls The CSS class name to remove. + * @return {Ext.Component} Returns the Component to allow method chaining. + */ + removeCls: function(cls) { + var me = this, + el = me.rendered ? me.el : me.protoEl; + el.removeCls.apply(el, arguments); + return me; + }, + /** + * Removes a `cls` to the `uiCls` array, which will also call {@link #removeUIClsFromElement} and removes it from all + * elements of this component. + * @param {String/String[]} classes A string or an array of strings to remove to the `uiCls`. + * @param {Boolean} skip True to remove the class + */ + removeClsWithUI: function(classes, skip) { + var me = this, + clsArray = [], + i = 0, + extArray = Ext.Array, + remove = extArray.remove, + uiCls = me.uiCls = extArray.clone(me.uiCls), + activeUI = me.activeUI, + length, cls; + if (typeof classes === "string") { + classes = (classes.indexOf(' ') < 0) ? [ + classes + ] : Ext.String.splitWords(classes); + } + length = classes.length; + for (i = 0; i < length; i++) { + cls = classes[i]; + if (cls && me.hasUICls(cls)) { + remove(uiCls, cls); + //If there's no activeUI then there's nothing to remove + if (activeUI) { + clsArray = clsArray.concat(me.removeUIClsFromElement(cls)); + } + } + } + if (skip !== true && activeUI) { + me.removeCls(clsArray); + } + return clsArray; + }, + resumeLayouts: function(flushOptions) { + var me = this; + if (!me.rendered) { + return; + } + if (!me.layoutSuspendCount) { + Ext.log.warn('Mismatched call to resumeLayouts - layouts are currently not suspended.'); + } + if (me.layoutSuspendCount && !--me.layoutSuspendCount) { + me.suspendLayout = false; + if (flushOptions && !me.isLayoutSuspended()) { + me.updateLayout(flushOptions); + } + } + }, + /** + * Scrolls this Component by the passed delta values, optionally animating. + * + * All of the following are equivalent: + * + * comp.scrollBy(10, 10, true); + * comp.scrollBy([10, 10], true); + * comp.scrollBy({ x: 10, y: 10 }, true); + * + * @param {Number/Number[]/Object} deltaX Either the x delta, an Array specifying x and y deltas or + * an object with "x" and "y" properties. + * @param {Number/Boolean/Object} deltaY Either the y delta, or an animate flag or config object. + * @param {Boolean/Object} animate Animate flag/config object if the delta values were passed separately. + */ + scrollBy: function(deltaX, deltaY, animate) { + var scroller = this.getScrollable(); + if (scroller) { + scroller.scrollBy(deltaX, deltaY, animate); + } + }, + /** + * Scrolls this component to the specified `x` and `y` coordinates. Only applicable + * for {@link #scrollable} components. + * @param {Number} x + * @param {Number} y + * @param {Boolean/Object} [animate] true for the default animation or a standard Element + * animation config object + */ + scrollTo: function(x, y, animate) { + var scroller = this.getScrollable(); + if (scroller) { + scroller.scrollTo(x, y, animate); + } + }, + /** + * Sets the overflow on the content element of the component. + * @param {Boolean} scroll True to allow the Component to auto scroll. + * @return {Ext.Component} this + * @deprecated 5.0.0 Use {@link #setScrollable} instead + */ + setAutoScroll: function(scroll) { + this.setScrollable(!!scroll); + return this; + }, + /** + * @param {String/Number} border The border, see {@link #border}. If a falsey value is passed + * @param targetEl (private) + * the border will be removed. + */ + setBorder: function(border, targetEl) { + var me = this, + initial = !!targetEl; + if (me.rendered || initial) { + if (!initial) { + targetEl = me.el; + } + if (!border) { + border = 0; + } else if (border === true) { + border = '1px'; + } else { + border = this.unitizeBox(border); + } + targetEl.setStyle('border-width', border); + if (!initial) { + me.updateLayout(); + } + } + me.border = border; + }, + /** + * Sets the dock position of this component in its parent panel. Note that this only has effect if this item is part + * of the `dockedItems` collection of a parent that has a DockLayout (note that any Panel has a DockLayout by default) + * @param {Object} dock The dock position. + * @return {Ext.Component} this + */ + setDock: function(dock) { + var me = this, + ownerCt = me.ownerCt; + if (dock !== me.dock) { + if (ownerCt && ownerCt.moveDocked) { + ownerCt.moveDocked(me, dock); + } else { + me.dock = dock; + } + } + return me; + }, + /** + * Enable or disable the component. + * @param {Boolean} disabled `true` to disable. + */ + setDisabled: function(disabled) { + return this[disabled ? 'disable' : 'enable'](); + }, + /** + * Sets the flex property of this component. Only applicable when this component is + * an item of a box layout + * @private + * @param {Number} flex + */ + setFlex: function(flex) { + this.flex = flex; + }, + /** + * Sets the height of the component. This method fires the {@link #resize} event. + * + * @param {Number} height The new height to set. This may be one of: + * + * - A Number specifying the new height in pixels. + * - A String used to set the CSS height style. + * - `undefined` to leave the height unchanged. + * - `null` to clear the height. + * + * @return {Ext.Component} this + */ + setHeight: function(height) { + return this.setSize(undefined, height); + }, + /** + * This method allows you to show or hide a LoadMask on top of this component. + * + * The mask will be rendered into the element returned by {@link #getMaskTarget} which for most Components is the Component's + * element. See {@link #getMaskTarget} and {@link #maskElement}. + * + * Most Components will return `null` indicating that their LoadMask cannot reside inside their element, but must + * be rendered into the document body. + * + * {@link Ext.view.Table Grid Views} however will direct a LoadMask to be rendered into the owning {@link Ext.panel.Table GridPanel}. + * + * @param {Boolean/Object/String} load True to show the default LoadMask, a config object that will be passed to the + * LoadMask constructor, or a message String to show. False to hide the current LoadMask. + * @param targetEl (private) This param is deprecated + * @return {Ext.LoadMask} The LoadMask instance that has just been shown. + */ + setLoading: function(load, targetEl) { + var me = this, + config = { + target: me + }; + if (me.rendered) { + // Shows mask for anything but false. + if (load !== false) { + if (Ext.isString(load)) { + config.msg = load; + } else { + Ext.apply(config, load, me.maskDefaults); + } + // We do not already have a LoadMask: create one + if (!me.loadMask || !me.loadMask.isLoadMask) { + // Deprecated second parameter. + // maskElement config replaces this + if (targetEl && config.useTargetEl == null) { + config.useTargetEl = true; + } + me.loadMask = new Ext.LoadMask(config); + } else // Change any settings according to load config + { + Ext.apply(me.loadMask, config); + } + // If already visible, just update display with passed configs. + if (me.loadMask.isVisible()) { + me.loadMask.syncMaskState(); + } else // Otherwise show with new configs + { + me.loadMask.show(); + } + } else // load == falsy: Hide the mask if it exists + { + if (me.loadMask && me.loadMask.isLoadMask) { + me.loadMask.hide(); + } + } + } + return me.loadMask; + }, + /** + * Sets the margin on the target element. + * @param {Number/String} margin The margin to set. See the {@link #margin} config. + * @param preventLayout (private) + */ + setMargin: function(margin, preventLayout) { + var me = this; + if (me.rendered) { + if (!margin && margin !== 0) { + margin = ''; + } else { + if (margin === true) { + margin = 5; + } + margin = this.unitizeBox(margin); + } + me.margin = margin; + // See: EXTJS-13359 + me.margin$ = null; + me.getEl().setStyle('margin', margin); + if (!preventLayout) { + // Changing the margins can impact the position of this (and possibly) + // other subsequent components in the layout. + me.updateLayout(me._notAsLayoutRoot); + } + } else { + me.margin = margin; + } + }, + /** + * Sets the overflow x/y on the content element of the component. The x/y overflow + * values can be any valid CSS overflow (e.g., 'auto' or 'scroll'). By default, the + * value is 'hidden'. Passing `undefined` will preserve the current value. + * + * @param {String} overflowX The overflow-x value. + * @param {String} overflowY The overflow-y value. + * @return {Ext.Component} this + * @deprecated 5.0.0 Use {@link #setScrollable} instead + */ + setOverflowXY: function(overflowX, overflowY) { + this.setScrollable({ + x: (overflowX && overflowX !== 'hidden') ? overflowX : false, + y: (overflowY && overflowY !== 'hidden') ? overflowY : false + }); + return this; + }, + /** + * Sets the page XY position of the component. To set the left and top instead, use {@link #setPosition}. + * This method fires the {@link #event-move} event. + * @param {Number/Number[]} x The new x position or an array of `[x,y]`. + * @param {Number} [y] The new y position. + * @param {Boolean/Object} [animate] True to animate the Component into its new position. You may also pass an + * animation configuration. + * @return {Ext.Component} this + */ + setPagePosition: function(x, y, animate) { + var me = this, + p, floatParentBox; + if (Ext.isArray(x)) { + y = x[1]; + x = x[0]; + } + me.pageX = x; + me.pageY = y; + if (me.floating) { + // Floating Components which are registered with a Container have to have their x and y properties made relative + if (me.isContainedFloater()) { + floatParentBox = me.floatParent.getTargetEl().getViewRegion(); + if (Ext.isNumber(x) && Ext.isNumber(floatParentBox.left)) { + x -= floatParentBox.left; + } + if (Ext.isNumber(y) && Ext.isNumber(floatParentBox.top)) { + y -= floatParentBox.top; + } + } else { + p = me.el.translateXY(x, y); + x = p.x; + y = p.y; + } + me.setPosition(x, y, animate); + } else { + p = me.el.translateXY(x, y); + me.setPosition(p.x, p.y, animate); + } + return me; + }, + /** + * @member Ext.Component + * Sets the left and top of the component. To set the page XY position instead, use {@link Ext.Component#setPagePosition setPagePosition}. This + * method fires the {@link #event-move} event. + * @param {Number/Number[]/Object} x The new left, an array of `[x,y]`, or animation config object containing `x` and `y` properties. + * @param {Number} [y] The new top. + * @param {Boolean/Object} [animate] If `true`, the Component is _animated_ into its new position. You may also pass an + * animation configuration. + * @return {Ext.Component} this + */ + setPosition: function(x, y, animate) { + var me = this, + pos = me.beforeSetPosition.apply(me, arguments); + if (pos && me.rendered) { + x = pos.x; + y = pos.y; + if (animate) { + // Proceed only if the new position is different from the current + // one. We only do these DOM reads in the animate case as we don't + // want to incur the penalty of read/write on every call to setPosition + if (x !== me.getLocalX() || y !== me.getLocalY()) { + me.stopAnimation(); + me.animate(Ext.apply({ + duration: 1000, + listeners: { + afteranimate: Ext.Function.bind(me.afterSetPosition, me, [ + x, + y + ]) + }, + to: { + // Use local coordinates for a component + // We don't need to normalize this for RTL, the anim.target.Component + // calls setPosition, which will normalize the x value to right when + // it's necessary + left: x, + top: y + } + }, animate)); + } + } else { + me.setLocalXY(x, y); + me.afterSetPosition(x, y); + } + } + return me; + }, + /** + * Sets the "x" scroll position for this component. Only applicable for + * {@link #scrollable} components + * @param {Number} x + * @param {Boolean/Object} [animate] true for the default animation or a standard Element + * animation config object + */ + setScrollX: function(x, animate) { + var scroller = this.getScrollable(); + if (scroller) { + scroller.scrollTo(x, null, animate); + } + }, + /** + * Sets the "y" scroll position for this component. Only applicable for + * {@link #scrollable} components + * @param {Number} y + * @param {Boolean/Object} [animate] true for the default animation or a standard Element + * animation config object + */ + setScrollY: function(y, animate) { + var scroller = this.getScrollable(); + if (scroller) { + scroller.scrollTo(null, y, animate); + } + }, + /** + * Sets the width and height of this Component. This method fires the {@link #resize} event. This method can accept + * either width and height as separate arguments, or you can pass a size object like `{width:10, height:20}`. + * + * @param {Number/String/Object} width The new width to set. This may be one of: + * + * - A Number specifying the new width in pixels. + * - A String used to set the CSS width style. + * - A size object in the format `{width: widthValue, height: heightValue}`. + * - `undefined` to leave the width unchanged. + * + * @param {Number/String} height The new height to set (not required if a size object is passed as the first arg). + * This may be one of: + * + * - A Number specifying the new height in pixels. + * - A String used to set the CSS height style. Animation may **not** be used. + * - `undefined` to leave the height unchanged. + * + * @return {Ext.Component} this + */ + setSize: function(width, height) { + var me = this, + oldWidth = me.width, + oldHeight = me.height, + widthIsString, heightIsString; + // support for standard size objects + if (width && typeof width === 'object') { + height = width.height; + width = width.width; + } + // Constrain within configured maximum + if (typeof width === 'number') { + me.width = Ext.Number.constrain(width, me.minWidth, me.maxWidth); + } else if (width === null) { + delete me.width; + } else if (typeof width === 'string') { + // handle width specified as a string css style + widthIsString = true; + me.width = width; + } + if (typeof height === 'number') { + me.height = Ext.Number.constrain(height, me.minHeight, me.maxHeight); + } else if (height === null) { + delete me.height; + } else if (typeof height === 'string') { + // handle width specified as a string css style + heightIsString = true; + me.height = height; + } + // If not rendered, all we need to is set the properties. + // The initial layout will set the size + if (me.rendered && me.isVisible()) { + if (oldWidth !== me.width || oldHeight !== me.height) { + if (me.liquidLayout || widthIsString || heightIsString) { + // if we have a liquid layout we must setSize now, since the following + // updateLayout call will not set our size in the dom if we successfully + // opt out of the layout run + me.el.setSize(me.width, me.height); + } + // If we are changing size, then we are not the root. + me.updateLayout(me._notAsLayoutRoot); + } + } + return me; + }, + /** + * Sets the style for this Component's primary element. + * + * Styles should be a valid DOM element style property. + * [Valid style property names](http://www.w3schools.com/jsref/dom_obj_style.asp) + * (_along with the supported CSS version for each_) + * + * var name = Ext.create({ + * xtype: 'component', + * renderTo: Ext.getBody(), + * html: 'Phineas Flynn' + * }); + * + * // two-param syntax + * name.setStyle('color', 'white'); + * + * // single-param syntax + * name.setStyle({ + * fontWeight: 'bold', + * backgroundColor: 'gray', + * padding: '10px' + * }); + * + * @param {String/Object} property The style property to be set, or an object of + * multiple styles. + * @param {String} [value] The value to apply to the given property, or null if an + * object was passed. + * @return {Ext.Component} this + */ + setStyle: function(property, value) { + var el = this.el || this.protoEl; + el.setStyle(property, value); + return this; + }, + /** + * Sets the UI for the component. This will remove any existing UIs on the component. It will also loop through any + * `uiCls` set on the component and rename them so they include the new UI. + * @param {String} ui The new UI for the component. + */ + setUI: function(ui) { + var me = this, + uiCls = me.uiCls, + activeUI = me.activeUI, + classes; + if (ui === activeUI) { + // The ui hasn't changed + return; + } + // activeUI will only be set if setUI has been called before. If it hasn't there's no need to remove anything + if (activeUI) { + classes = me.removeClsWithUI(uiCls, true); + if (classes.length) { + me.removeCls(classes); + } + // Remove the UI from the element + me.removeUIFromElement(); + } else { + // We need uiCls to be empty otherwise our call to addClsWithUI won't do anything + me.uiCls = []; + } + // Set the UI + me.ui = ui; + // After the first call to setUI the values ui and activeUI should track each other but initially we need some + // way to tell whether the ui has really been set. + me.activeUI = ui; + // Add the new UI to the element + me.addUIToElement(); + classes = me.addClsWithUI(uiCls, true); + if (classes.length) { + me.addCls(classes); + } + // Changing the ui can lead to significant changes to a component's appearance, so the layout needs to be + // updated. Internally most calls to setUI are pre-render. Buttons are a notable exception as setScale changes + // the ui and often requires the layout to be updated. + if (me.rendered) { + me.updateLayout(); + } + }, + /** + * Convenience function to hide or show this component by Boolean. + * @param {Boolean} visible `true` to show, `false` to hide. + * @return {Ext.Component} this + * @since 1.1.0 + */ + setVisible: function(visible) { + return this[visible ? 'show' : 'hide'](); + }, + /** + * Sets the hidden state of this component. This is basically the same as + * `{@link #setVisible}` but the boolean parameter has the opposite meaning. + * @param {Boolean} hidden + * @return {Ext.Component} + */ + setHidden: function(hidden) { + return this.setVisible(!hidden); + }, + /** + * Sets the width of the component. This method fires the {@link #resize} event. + * + * @param {Number} width The new width to set. This may be one of: + * + * - A Number specifying the new width in pixels. + * - A String used to set the CSS width style. + * - `undefined` to leave the width unchanged. + * - `null` to clear the width. + * + * @return {Ext.Component} this + */ + setWidth: function(width) { + return this.setSize(width); + }, + /** + * Shows this Component, rendering it first if {@link #autoRender} or {@link #cfg-floating} are `true`. + * + * After being shown, a {@link #cfg-floating} Component (such as a {@link Ext.window.Window}), is activated it and + * brought to the front of its {@link #zIndexManager z-index stack}. + * + * @param {String/Ext.dom.Element} [animateTarget=null] **only valid for {@link #cfg-floating} Components such as {@link + * Ext.window.Window Window}s or {@link Ext.tip.ToolTip ToolTip}s, or regular Components which have been configured + * with `floating: true`.** The target from which the Component should animate from while opening. + * @param {Function} [callback] A callback function to call after the Component is displayed. + * Only necessary if animation was specified. + * @param {Object} [scope] The scope (`this` reference) in which the callback is executed. + * Defaults to this Component. + * @return {Ext.Component} this + */ + show: function(animateTarget, callback, scope) { + var me = this, + rendered = me.rendered, + container = me.ownerFocusableContainer; + if (me.hierarchicallyHidden || (me.floating && !rendered && me.isHierarchicallyHidden())) { + // If this is a hierarchically hidden floating component, we need to stash + // the arguments to this call so that the call can be deferred until the next + // time syncHidden() is called. + if (!rendered) { + // If the component has not yet been rendered it requires special treatment. + // Normally, for rendered components we can just set the pendingShow property + // and syncHidden() listens to events in the hierarchyEventSource and calls + // show() when this component becomes hierarchically visible. However, + // if the component has not yet been rendered the hierarchy event listeners + // have not yet been attached (since Floating is initialized during the + // render phase. This means we have to initialize the hierarchy event + // listeners right now to ensure that the component will show itself when + // it becomes hierarchically visible. + me.initHierarchyEvents(); + } + // defer the show call until next syncHidden(), but ignore animateTarget. + if (arguments.length > 1) { + arguments[0] = null; + // jshint ignore:line + me.pendingShow = arguments; + } else { + me.pendingShow = true; + } + } else if (rendered && me.isVisible()) { + if (me.floating) { + me.onFloatShow(); + // onFloatShow does not toFront this Component + // because that is done by our ZIndexManager in response to the global + // show event fired from afterShow. + // Since we will not execute afterShow if already visible, + // maintain behaviour by explicitly toFronting here. + if (me.toFrontOnShow) { + me.toFront(); + } + } + } else { + if (me.fireEvent('beforeshow', me) !== false) { + me.hidden = false; + delete this.getInherited().hidden; + // Render on first show if there is an autoRender config, or if this + // is a floater (Window, Menu, BoundList etc). + if (container && !container.beforeFocusableChildShow.$nullFn) { + container.beforeFocusableChildShow(me); + } + // We suspend layouts here because floaters/autoRenders + // will layout when onShow is called. If the render succeeded, + // the layout will be trigger inside onShow, so we don't flush + // in the first block. If, for some reason we couldn't render, then + // we resume layouts and force a flush because we don't know if something + // will force it. + Ext.suspendLayouts(); + if (!rendered && (me.autoRender || me.floating)) { + me.doAutoRender(); + rendered = me.rendered; + } + if (rendered) { + me.beforeShow(); + Ext.resumeLayouts(); + me.onShow.apply(me, arguments); + me.afterShow.apply(me, arguments); + } else { + Ext.resumeLayouts(true); + } + } else { + me.onShowVeto(); + } + } + return me; + }, + /** + * Displays component at specific xy position. + * A floating component (like a menu) is positioned relative to its ownerCt if any. + * Useful for popping up a context menu: + * + * listeners: { + * itemcontextmenu: function(view, record, item, index, event, options) { + * Ext.create('Ext.menu.Menu', { + * width: 100, + * height: 100, + * margin: '0 0 10 0', + * items: [{ + * text: 'regular item 1' + * },{ + * text: 'regular item 2' + * },{ + * text: 'regular item 3' + * }] + * }).showAt(event.getXY()); + * } + * } + * + * @param {Number/Number[]} x The new x position or array of `[x,y]`. + * @param {Number} [y] The new y position + * @param {Boolean/Object} [animate] True to animate the Component into its new position. You may also pass an + * animation configuration. + * @return {Ext.Component} this + */ + showAt: function(x, y, animate) { + var me = this; + // Not rendered, then animating to a position is meaningless, + // just set the x,y position and allow show's processing to work. + if (!me.rendered && (me.autoRender || me.floating)) { + me.x = x; + me.y = y; + return me.show(); + } + if (me.floating) { + me.setPosition(x, y, animate); + } else { + me.setPagePosition(x, y, animate); + } + return me.show(); + }, + /** + * Shows this component by the specified {@link Ext.Component Component} or {@link Ext.dom.Element Element}. + * Used when this component is {@link #cfg-floating}. + * @param {Ext.Component/Ext.dom.Element} component The {@link Ext.Component} or {@link Ext.dom.Element} to show the component by. + * @param {String} [position] Alignment position as used by {@link Ext.util.Positionable#getAlignToXY}. + * Defaults to `{@link #defaultAlign}`. See {@link #alignTo} for possible values. + * @param {Number[]} [offset] Alignment offsets as used by {@link Ext.util.Positionable#getAlignToXY}. See {@link #alignTo} for possible values. + * @return {Ext.Component} this + */ + showBy: function(component, position, offset) { + var me = this; + if (!me.floating) { + Ext.log.warn('Using showBy on a non-floating component'); + } + if (me.floating && component) { + me._lastAlignTarget = component; + me._lastAlignToPos = position || me.defaultAlign; + me._lastAlignToOffsets = offset || me.alignOffset; + me.show(); + } + return me; + }, + suspendLayouts: function() { + var me = this; + if (!me.rendered) { + return; + } + if (++me.layoutSuspendCount === 1) { + me.suspendLayout = true; + } + }, + /** + * Toggles the specified CSS class on this component (removes it if it already exists, + * otherwise adds it). + * @param {String} className The CSS class to toggle. + * @param {Boolean} [state] If specified as `true`, causes the class to be added. If + * specified as `false`, causes the class to be removed. + * @return {Ext.Component} Returns the Component to allow method chaining. + * @chainable + */ + toggleCls: function(className, state) { + if (state === undefined) { + state = !this.hasCls(className); + } + return this[state ? 'addCls' : 'removeCls'](className); + }, + unitizeBox: function(box) { + return Ext.Element.unitizeBox(box); + }, + /** + * Removes the mask applied by {@link #mask} + */ + unmask: function() { + (this.getMaskTarget() || this.el).unmask(); + this.setMasked(false); + }, + unregisterFloatingItem: function(cmp) { + var me = this; + if (me.floatingDescendants) { + me.floatingDescendants.unregister(cmp); + } + }, + /** + * Navigates up the ownership hierarchy searching for an ancestor Container which matches any passed selector or component. + * + * *Important.* There is not a universal upwards navigation pointer. There are several upwards relationships + * such as the {@link Ext.button.Button button} which activates a {@link Ext.button.Button#cfg-menu menu}, or the + * {@link Ext.menu.Item menu item} which activated a {@link Ext.menu.Item#cfg-menu submenu}, or the + * {@link Ext.grid.column.Column column header} which activated the column menu. + * + * These differences are abstracted away by this method. + * + * Example: + * + * var owningTabPanel = grid.up('tabpanel'); + * + * @param {String/Ext.Component} [selector] The selector component or actual component to test. If not passed the immediate owner/activator is returned. + * @param {String/Number/Ext.Component} [limit] This may be a selector upon which to stop the upward scan, or a limit of the number of steps, or Component reference to stop on. + * @return {Ext.container.Container} The matching ancestor Container (or `undefined` if no match was found). + */ + up: function(selector, limit) { + var result = this.getRefOwner(), + limitSelector = typeof limit === 'string', + limitCount = typeof limit === 'number', + limitComponent = limit && limit.isComponent, + steps = 0; + if (selector) { + for (; result; result = result.getRefOwner()) { + if (result.destroyed) { + return null; + } + steps++; + if (selector.isComponent) { + if (result === selector) { + return result; + } + } else { + if (Ext.ComponentQuery.is(result, selector)) { + return result; + } + } + // Stop when we hit the limit selector + if (limitSelector && result.is(limit)) { + return; + } + if (limitCount && steps === limit) { + return; + } + if (limitComponent && result === limit) { + return; + } + } + } + return result; + }, + /** + * Update the content area of a component. + * @param {String/Object} htmlOrData If this component has been configured with a + * template via the tpl config then it will use this argument as data to populate the + * template. If this component was not configured with a template, the components + * content area will be updated via Ext.Element update. + * @param {Boolean} [loadScripts=false] Only legitimate when using the `html` + * configuration. Causes embedded script tags to be executed. Inline source will be executed + * with this Component as the scope (`this` reference). + * @param {Function} [callback] Only legitimate when using the `html` configuration. + * Callback to execute when scripts have finished loading. + * @param {Object} [scriptScope=`this`] The scope (`this` reference) in which to + * execute *inline* script elements content. Scripts with a `src` attribute cannot + * be executed with this scope. + * + * @since 3.4.0 + */ + update: function(htmlOrData, loadScripts, callback, scriptScope) { + var me = this, + isData = (me.tpl && !Ext.isString(htmlOrData)), + container = me.ownerFocusableContainer, + sizeModel, doLayout, el; + if (isData) { + me.data = (htmlOrData && htmlOrData.isEntity) ? htmlOrData.getData(true) : htmlOrData; + } else { + me.html = Ext.isObject(htmlOrData) ? Ext.DomHelper.markup(htmlOrData) : htmlOrData; + } + if (me.rendered) { + sizeModel = me.getSizeModel(); + doLayout = sizeModel.width.shrinkWrap || sizeModel.height.shrinkWrap; + if (me.isContainer) { + el = me.layout.getRenderTarget(); + // If we are a non-empty container being updated with raw content we have to lay out + doLayout = doLayout || me.items.items.length > 0; + } else { + el = me.getTargetEl(); + } + if (isData) { + me.tpl[me.tplWriteMode](el, me.data || {}); + } else { + el.setHtml(me.html, loadScripts, callback, scriptScope || me); + } + if (doLayout) { + me.updateLayout(); + } + if (container && !container.onFocusableChildUpdate.$nullFn) { + container.onFocusableChildUpdate(me); + } + } + }, + /** + * Update the content area of a component. + * @param {String/Object} html If this component has been configured with a + * template via the tpl config then it will use this argument as data to populate the + * template. If this component was not configured with a template, the components + * content area will be updated via Ext.Element update. + * @param {Boolean} [loadScripts=false] Only legitimate when using the `html` + * configuration. Causes embedded script tags to be executed. Inline source will be executed + * with this Component as the scope (`this` reference). + * @param {Function} [callback] Only legitimate when using the `html` configuration. + * Callback to execute when scripts have finished loading. + * @param {Object} [scriptScope='this'] The scope (`this` reference) in which to + * execute *inline* script elements content. Scripts with a `src` attribute cannot + * be executed with this scope. + * + * @since 3.4.0 + */ + setHtml: function(html, loadScripts, callback, scriptScope) { + this.update(html, loadScripts, null, scriptScope); + }, + applyData: function(data) { + // Don't return data here, update will set this.data + this.update(data); + }, + /** + * Sets the current box measurements of the component's underlying element. + * @param {Object} box An object in the format {x, y, width, height} + * @return {Ext.Component} this + */ + updateBox: function(box) { + this.setSize(box.width, box.height); + this.setPagePosition(box.x, box.y); + return this; + }, + _asLayoutRoot: { + isRoot: true + }, + _notAsLayoutRoot: { + isRoot: false + }, + /** + * Updates this component's layout. If this update affects this components {@link #ownerCt}, + * that component's `updateLayout` method will be called to perform the layout instead. + * Otherwise, just this component (and its child items) will layout. + * + * @param {Object} [options] An object with layout options. + * @param {Boolean} options.defer `true` if this layout should be deferred. + * @param {Boolean} options.isRoot `true` if this layout should be the root of the layout. + */ + updateLayout: function(options) { + var me = this, + defer, + lastBox = me.lastBox, + isRoot = options && options.isRoot, + context = options && options.context; + if (lastBox) { + // remember that this component's last layout result is invalid and must be + // recalculated + lastBox.invalid = true; + } + if (!me.rendered || me.isDetached || me.layoutSuspendCount || me.suspendLayout) { + return; + } + if (me.hidden) { + Ext.Component.cancelLayout(me); + } else if (typeof isRoot !== 'boolean') { + isRoot = me.isLayoutRoot(); + } + // if we aren't the root, see if our ownerLayout will handle it... + if (isRoot || !me.ownerLayout || !me.ownerLayout.onContentChange(me, context)) { + // either we are the root or our ownerLayout doesn't care + if (!me.isLayoutSuspended()) { + // we aren't suspended (knew that), but neither is any of our ownerCt's... + defer = (options && options.hasOwnProperty('defer')) ? options.defer : me.deferLayouts; + Ext.Component.updateLayout(me, defer); + } + } + }, + updateMaxHeight: function(maxHeight, oldMaxHeight) { + this.changeConstraint(maxHeight, oldMaxHeight, 'min', 'max-height', 'height'); + }, + updateMaxWidth: function(maxWidth, oldMaxWidth) { + this.changeConstraint(maxWidth, oldMaxWidth, 'min', 'max-width', 'width'); + }, + updateMinHeight: function(minHeight, oldMinHeight) { + this.changeConstraint(minHeight, oldMinHeight, 'max', 'min-height', 'height'); + }, + updateMinWidth: function(minWidth, oldMinWidth) { + this.changeConstraint(minWidth, oldMinWidth, 'max', 'min-width', 'width'); + }, + updateTouchAction: function(touchAction) { + var name, childEl, value, hasRootActions; + for (name in touchAction) { + childEl = this[name]; + value = touchAction[name]; + if (childEl && childEl.isElement) { + childEl.setTouchAction(value); + } else { + hasRootActions = true; + } + } + if (hasRootActions) { + this.el.setTouchAction(touchAction); + } + }, + // *********************************************************************************** + // End Component methods + // *********************************************************************************** + // + // + // *********************************************************************************** + // Begin Positionable methods + // *********************************************************************************** + getAnchorToXY: function(el, anchor, local, mySize) { + return el.getAnchorXY(anchor, local, mySize); + }, + getBorderPadding: function() { + return this.el.getBorderPadding(); + }, + getLocalX: function() { + return this.el.getLocalX(); + }, + getLocalXY: function() { + return this.el.getLocalXY(); + }, + getLocalY: function() { + return this.el.getLocalY(); + }, + getX: function() { + return this.el.getX(); + }, + getXY: function() { + return this.el.getXY(); + }, + getY: function() { + return this.el.getY(); + }, + setLocalX: function(x) { + this.el.setLocalX(x); + }, + setLocalXY: function(x, y) { + this.el.setLocalXY(x, y); + }, + setLocalY: function(y) { + this.el.setLocalY(y); + }, + setX: function(x, animate) { + this.el.setX(x, animate); + }, + setXY: function(xy, animate) { + this.el.setXY(xy, animate); + }, + setY: function(y, animate) { + this.el.setY(y, animate); + }, + // *********************************************************************************** + // End Positionable methods + // *********************************************************************************** + // + privates: { + addOverCls: function() { + var me = this; + if (!me.disabled) { + me.el.addCls(me.overCls); + } + }, + /** + * Method which adds a specified UI to the components element. + * @private + */ + addUIToElement: function() { + var me = this, + baseClsUI = me.baseCls + '-' + me.ui, + childEls, childElName, el, suffix; + me.addCls(baseClsUI); + if (me.rendered && me.frame && !Ext.supports.CSS3BorderRadius) { + // Loop through each frame element, and if they are defined add the ui: + baseClsUI += '-'; + childEls = me.getChildEls(); + for (childElName in childEls) { + suffix = childEls[childElName].frame; + if (suffix && suffix !== true) { + el = me[childElName]; + if (el) { + el.addCls(baseClsUI + suffix); + } + } + } + } + }, + /** + * @private + */ + changeConstraint: function(newValue, oldValue, constrainMethod, styleName, sizeName) { + var me = this, + size = me[sizeName]; + if (newValue != null && typeof size === 'number') { + me[sizeName] = Math[constrainMethod](size, newValue); + } + if (me.liquidLayout) { + // components that use liquidLayout need their size constraints set in the dom + if (newValue != null) { + me.setStyle(styleName, newValue + 'px'); + } else if (oldValue) { + me.setStyle(styleName, ''); + } + } + if (me.rendered) { + me.updateLayout(); + } + }, + /** + * @param {String/Object} plugin string or config object containing a ptype property. + * + * Constructs a plugin according to the passed config object/ptype string. + * + * Ensures that the constructed plugin always has a `cmp` reference back to this component. + * The setting up of this is done in PluginManager. The PluginManager ensures that a reference to this + * component is passed to the constructor. It also ensures that the plugin's `setCmp` method (if any) is called. + * @private + */ + constructPlugin: function(plugin) { + var me = this, + PM = Ext.plugin.Manager; + // ptype only, pass as the defultType + if (typeof plugin === 'string') { + plugin = PM.create({}, plugin, me); + } else // Object (either config with ptype or an instantiated plugin) + { + plugin = PM.create(plugin, null, me); + } + return plugin; + }, + /** + * Returns an array of fully constructed plugin instances. This converts any configs into their + * appropriate instances. + * + * It does not mutate the plugins array. It creates a new array. + * @private + */ + constructPlugins: function() { + var me = this, + plugins = me.plugins, + result, i, len; + if (plugins) { + me.plugins = result = Ext.plugin.Abstract.decode(plugins, 'ptype'); + // The processed flag indicates that the plugins have been constructed. This is usually done + // at construction time, so if at initComponent time, there is a non-zero array of plugins which + // does NOT have the processed flag, it needs to be processed again. + result.processed = true; + for (i = 0 , len = result.length; i < len; i++) { + // this just returns already-constructed plugin instances... + result[i] = me.constructPlugin(result[i]); + } + } + me.pluginsInitialized = true; + return result; + }, + detachFromBody: function() { + // Also see reattachToBody + var me = this; + if (!me.isDetached) { + Ext.getDetachedBody().appendChild(me.el, true); + Ext.Component.cancelLayout(me); + me.isDetached = true; + } + }, + doAddListener: function(ename, fn, scope, options, order, caller, manager) { + var me = this, + listeners, option, eventOptions, elementName, element, delegate; + if (Ext.isObject(fn) || (options && options.element)) { + if (options.element) { + elementName = options.element; + listeners = {}; + listeners[ename] = fn; + if (scope) { + listeners.scope = scope; + } + eventOptions = me.$elementEventOptions; + for (option in options) { + if (eventOptions[option]) { + listeners[option] = options[option]; + } + } + } else { + listeners = fn; + elementName = ename; + } + element = me[elementName]; + if (element && element.isObservable) { + // can be any kind of observable, not just element + me.mon(element, listeners); + } else { + me.afterRenderEvents = me.afterRenderEvents || {}; + if (!me.afterRenderEvents[elementName]) { + me.afterRenderEvents[elementName] = []; + } + me.afterRenderEvents[elementName].push(listeners); + } + return; + } + if (options) { + delegate = options.delegate; + if (delegate) { + me.mixins.componentDelegation.addDelegatedListener.call(me, ename, fn, scope, options, order, caller, manager); + return; + } + } + me.mixins.observable.doAddListener.call(me, ename, fn, scope, options, order, caller, manager); + }, + doRemoveListener: function(eventName, fn, scope) { + var me = this; + me.mixins.observable.doRemoveListener.call(me, eventName, fn, scope); + me.mixins.componentDelegation.removeDelegatedListener.call(me, eventName, fn, scope); + }, + /** + * This method fires an event on `Ext.GlobalEvents` allowing interested parties to know + * of certain critical events for this component. This is done globally because the + * (few) listeners can immediately receive the event rather than bubbling the event + * only to reach the top and have no listeners. + * + * The main usage for these events is to do with floating components. For example, the + * load mask is a floating component. The component it is masking may be inside several + * containers. As such, they need to know when component is hidden, either directly, or + * via a parent container being hidden. To do this they subscribe to these events and + * filter out the appropriate container. + * + * This functionality is contained in Component (as opposed to Container) because a + * Component can be the ownerCt for a floating component (loadmask), and the loadmask + * needs to know when its owner is shown/hidden so that its hidden state can be + * synchronized. + * + * @param {String} eventName The event name. + * @since 4.2.0 + * @private + */ + fireHierarchyEvent: function(eventName) { + var globalEvents = Ext.GlobalEvents; + if (globalEvents.hasListeners[eventName]) { + globalEvents.fireEvent(eventName, this); + } + }, + getActionEl: function() { + return this.el; + }, + /** + * @private + */ + getAutoId: function() { + this.autoGenId = true; + return ++Ext.Component.AUTO_ID; + }, + /** + * @private + */ + getContentTarget: function() { + return this.el; + }, + getDragEl: function() { + return this.el; + }, + /** + * Get an el for overflowing, defaults to the target el + * @private + */ + getOverflowEl: function() { + return this.getTargetEl(); + }, + /** + * @private + * Returns the CSS style object which will set the Component's scroll styles. + * This must be applied to the {@link #getTargetEl target element}. + */ + getOverflowStyle: function() { + var me = this, + scroller = me.getScrollable(), + flags = me._scrollFlags, + x, y, scrollFlags; + if (scroller) { + x = scroller.getX(); + if (x === true) { + x = 'auto'; + } + y = scroller.getY(); + if (y === true) { + y = 'auto'; + } + scrollFlags = flags[x][y]; + } else { + scrollFlags = flags.none; + } + me.scrollFlags = scrollFlags; + return { + overflowX: scrollFlags.overflowX, + overflowY: scrollFlags.overflowY + }; + }, + /** + * Returns an array of current fully constructed plugin instances. + * @private + */ + getPlugins: function() { + var plugins = this.plugins; + plugins = (plugins && plugins.processed) ? plugins : this.constructPlugins(); + return plugins || null; + }, + getProxy: function() { + var me = this, + target; + if (!me.proxy) { + target = Ext.getBody(); + me.proxy = me.el.createProxy(Ext.baseCSSPrefix + 'proxy-el', target, true); + } + return me.proxy; + }, + /** + * This is used to determine where to insert the 'html', 'contentEl' and 'items' in this component. + * @private + */ + getTargetEl: function() { + return this.frameBody || this.el; + }, + /** + * @private + * Needed for when widget is rendered into a grid cell. The class to add to the cell element. + */ + getTdCls: function() { + return Ext.baseCSSPrefix + this.getTdType() + '-' + this.ui + '-cell'; + }, + /** + * @private + * Partner method to {@link #getTdCls}. + * + * Returns the base type for the component. Defaults to return `this.xtype`, but + * All derived classes of {@link Ext.form.field.Text TextField} can return the type 'textfield', + * and all derived classes of {@link Ext.button.Button Button} can return the type 'button' + */ + getTdType: function() { + return this.xtype; + }, + /** + * @private + */ + getTpl: function(name) { + Ext.log.warn('getTpl is deprecated, use lookupTpl.'); + return this.lookupTpl(name); + }, + initCls: function() { + var me = this, + cls = [ + me.baseCls + ], + targetCls = me.getComponentLayout().targetCls; + if (targetCls) { + cls.push(targetCls); + } + if (Ext.isDefined(me.cmpCls)) { + if (Ext.isDefined(Ext.global.console)) { + Ext.global.console.warn('Ext.Component: cmpCls has been deprecated. Please use componentCls.'); + } + me.componentCls = me.cmpCls; + delete me.cmpCls; + } + if (me.componentCls) { + cls.push(me.componentCls); + } else { + me.componentCls = me.baseCls; + } + return cls; + }, + initDraggable: function() { + var me = this, + // If we are resizable, and the resizer had to wrap this Component's el (e.g. an Img) + // Then we have to create a pseudo-Component out of the resizer to drag that, + // otherwise, we just drag this Component + dragTarget = (me.resizer && me.resizer.el !== me.el) ? me.resizerComponent = new Ext.Component({ + el: me.resizer.el, + rendered: true, + container: me.container + }) : me, + ddConfig = Ext.applyIf({ + el: dragTarget.getDragEl(), + constrainTo: (me.constrain || me.draggable.constrain) ? (me.constrainTo || (me.floatParent ? me.floatParent.getTargetEl() : me.container)) : undefined + }, me.draggable); + // Add extra configs if Component is specified to be constrained + if (me.constrain || me.constrainDelegate) { + ddConfig.constrain = me.constrain; + ddConfig.constrainDelegate = me.constrainDelegate; + } + me.dd = new Ext.util.ComponentDragger(dragTarget, ddConfig); + }, + /** + * Initializes padding by applying it to the target element, or if the layout manages + * padding ensures that the padding on the target element is "0". + * @private + */ + initPadding: function(targetEl) { + var me = this, + padding = me.padding; + if (padding != null) { + if (me.layout && me.layout.managePadding && me.contentPaddingProperty === 'padding') { + // If the container layout manages padding, or if a touch scroller is in + // use, the padding will be applied to an inner layout element, or the + // touch scroller element. This is done as a workaround for the browser bug + // where right and/or bottom padding is lost when the element has overflow. + // The assumed intent is for the configured padding to override any padding + // that is applied to the target element via style sheet rules. It is + // therefore necessary to set the target element's padding to "0". + targetEl.setStyle('padding', 0); + } else { + // Convert the padding, margin and border properties from a space separated string + // into a proper style string + targetEl.setStyle('padding', this.unitizeBox((padding === true) ? 5 : padding)); + } + } + }, + /** + * @private + */ + initPlugin: function(plugin) { + plugin.init(this); + return plugin; + }, + initResizable: function(resizable) { + var me = this; + resizable = Ext.apply({ + target: me, + dynamic: false, + constrainTo: (me.constrain || (resizable && resizable.constrain)) ? (me.constrainTo || (me.floatParent ? me.floatParent.getTargetEl() : me.container)) : undefined, + handles: me.resizeHandles + }, resizable); + resizable.target = me; + me.resizer = new Ext.resizer.Resizer(resizable); + }, + /** + * Applies padding, margin, border, top, left, height, and width configs to the + * appropriate elements. + * @private + */ + initStyles: function(targetEl) { + var me = this, + margin = me.margin, + border = me.border, + cls = me.cls, + style = me.style, + x = me.x, + y = me.y, + liquidLayout = me.liquidLayout, + width, height; + me.initPadding(targetEl); + if (margin != null) { + targetEl.setStyle('margin', this.unitizeBox((margin === true) ? 5 : margin)); + } + if (border != null) { + me.setBorder(border, targetEl); + } + // initComponent, beforeRender, or event handlers may have set the style or cls property since the protoEl was set up + // so we must apply styles and classes here too. + if (cls && cls !== me.initialCls) { + targetEl.addCls(cls); + me.cls = me.initialCls = null; + } + if (style && style !== me.initialStyle) { + targetEl.setStyle(style); + me.style = me.initialStyle = null; + } + if (x != null) { + targetEl.setStyle(me.horizontalPosProp, (typeof x === 'number') ? (x + 'px') : x); + } + if (y != null) { + targetEl.setStyle('top', (typeof y === 'number') ? (y + 'px') : y); + } + if (!me.ownerCt || me.floating) { + if (Ext.scopeCss) { + targetEl.addCls(me.rootCls); + } + targetEl.addCls(me.borderBoxCls); + } + // Framed components need their width/height to apply to the frame, which is + // best handled in layout at present. The exception to this rule is component + // that use liquidLayout and so cannot rely on the layout to set their size. + if (liquidLayout || !me.getFrameInfo()) { + width = me.width; + height = me.height; + // If we're using the content box model, we also cannot assign numeric initial sizes since we do not know the border widths to subtract + if (width != null) { + if (typeof width === 'number') { + targetEl.setStyle('width', width + 'px'); + } else { + targetEl.setStyle('width', width); + } + } + if (height != null) { + if (typeof height === 'number') { + targetEl.setStyle('height', height + 'px'); + } else { + targetEl.setStyle('height', height); + } + } + } + }, + // Utility method to determine if a Component is floating, and has an owning Container whose coordinate system + // it must be positioned in when using setPosition. + isContainedFloater: function() { + return (this.floating && this.floatParent); + }, + isDescendant: function(ancestor) { + if (ancestor.isContainer) { + for (var c = this.ownerCt; c; c = c.ownerCt) { + if (c === ancestor) { + return true; + } + } + } + return false; + }, + /** + * @private + * Returns `true` if the passed element is within the container tree of this component. + * + * For example if a menu's submenu contains an {@link Ext.form.field.Date}, that top level + * menu owns the elements of the date picker. Using this method, you can tell if an event took place + * within a certain component tree. + */ + owns: function(element) { + var result = false, + cmp; + if (element.isEvent) { + element = element.target; + } else if (element.isElement) { + element = element.dom; + } + cmp = Ext.Component.fromElement(element); + if (cmp) { + result = (cmp === this) || (!!cmp.up(this)); + } + return result; + }, + parseBox: function(box) { + return Ext.Element.parseBox(box); + }, + reattachToBody: function() { + // Also see detachFromBody + this.isDetached = false; + }, + removeManagedListenerItem: function(isClear, managedListener, item, ename, fn, scope) { + var me = this, + element = managedListener.options ? managedListener.options.element : null; + if (element) { + element = me[element]; + if (element && element.un) { + if (isClear || (managedListener.item === item && managedListener.ename === ename && (!fn || managedListener.fn === fn) && (!scope || managedListener.scope === scope))) { + element.un(managedListener.ename, managedListener.fn, managedListener.scope); + if (!isClear) { + Ext.Array.remove(me.managedListeners, managedListener); + } + } + } + } else { + return me.mixins.observable.removeManagedListenerItem.apply(me, arguments); + } + }, + removeOverCls: function() { + this.el.removeCls(this.overCls); + }, + removePlugin: function(plugin) { + Ext.Array.remove(this.plugins, plugin); + plugin.destroy(); + }, + /** + * Method which removes a specified UI from the components element. + * @private + */ + removeUIFromElement: function() { + var me = this, + baseClsUI = me.baseCls + '-' + me.ui, + childEls, childElName, el, suffix; + me.removeCls(baseClsUI); + if (me.rendered && me.frame && !Ext.supports.CSS3BorderRadius) { + // Loop through each frame element, and if they are defined remove the ui: + baseClsUI += '-'; + childEls = me.getChildEls(); + for (childElName in childEls) { + suffix = childEls[childElName].frame; + if (suffix && suffix !== true) { + el = me[childElName]; + if (el) { + el.removeCls(baseClsUI + suffix); + } + } + } + } + }, + /** + * @private + */ + setComponentLayout: function(layout) { + var currentLayout = this.componentLayout; + if (currentLayout && currentLayout.isLayout && currentLayout !== layout) { + currentLayout.setOwner(null); + } + this.componentLayout = layout; + layout.setOwner(this); + }, + setHiddenState: function(hidden) { + var me = this, + inheritedState = me.getInherited(), + zIndexManager = me.zIndexManager; + me.hidden = hidden; + if (hidden) { + inheritedState.hidden = true; + } else { + delete inheritedState.hidden; + } + // Ensure any ZIndexManager knowns about visibility state change to keep its filtering correct + if (zIndexManager) { + zIndexManager.onComponentShowHide(me); + } + }, + setupProtoEl: function() { + var cls = this.initCls(); + this.protoEl.addCls(cls); + }, + wrapPrimaryEl: function(dom) { + var me = this, + el = me.el; + if (!el || !el.isElement) { + // allow subclass override to instantiate the element + me.el = Ext.get(dom); + } + if (me.floating) { + this.mixins.floating.constructor.call(this); + } + } + }, + // private + deprecated: { + 5: { + methods: { + /** + * @method addClass + * @inheritdoc Ext.Component#addCls + * @deprecated 4.1 Use {@link #addCls} instead. + * @since 2.3.0 + */ + addClass: 'addCls', + /** + * @method doComponentLayout + * This method needs to be called whenever you change something on this component that + * requires the Component's layout to be recalculated. + * @return {Ext.Component} this + * @deprecated 4.1 Use {@link Ext.Component#method-updateLayout} instead. + */ + doComponentLayout: function() { + this.updateLayout(); + return this; + }, + /** + * @method removeClass + * @inheritdoc Ext.Component#removeCls + * @deprecated 4.1 Use {@link #addCls} instead. + * @since 2.3.0 + */ + removeClass: 'removeCls', + /** + * @method forceComponentLayout + * @inheritdoc Ext.Component#updateLayout + * @deprecated 4.1 Use {@link Ext.Component#method-updateLayout} instead. + */ + forceComponentLayout: 'updateLayout', + /** + * @method setDocked + * @inheritdoc Ext.Component#setDock + * @deprecated 5.0 Use {@link #setDock} instead. + */ + setDocked: 'setDock' + } + } + } +}, function(Component) { + var prototype = Component.prototype; + // event options for listeners that use the "element" event options must also include + // event options from Ext.Element + (prototype.$elementEventOptions = Ext.Object.chain(Ext.Element.prototype.$eventOptions)).element = 1; + (prototype.$eventOptions = Ext.Object.chain(prototype.$eventOptions)).delegate = 1; + Component.createAlias({ + on: 'addListener', + prev: 'previousSibling', + next: 'nextSibling' + }); + /** + * @method resumeLayouts + * @inheritdoc Ext.Component#static-method-resumeLayouts + * @member Ext + */ + Ext.resumeLayouts = function(flush) { + Component.resumeLayouts(flush); + }; + /** + * @method suspendLayouts + * @inheritdoc Ext.Component#static-method-suspendLayouts + * @member Ext + */ + Ext.suspendLayouts = function() { + Component.suspendLayouts(); + }; + /** + * @method batchLayouts + * Utility wrapper that suspends layouts of all components for the duration of a given + * function. + * @param {Function} fn The function to execute. + * @param {Object} [scope] The scope (`this` reference) in which the specified function + * is executed. + * @member Ext + */ + Ext.batchLayouts = function(fn, scope) { + Component.suspendLayouts(); + // Invoke the function + // note: try/finally works in IE8 standards mode + try { + fn.call(scope); + } finally { + Component.resumeLayouts(true); + } + }; + /** + * @method setGlyphFontFamily + * Sets the default font-family to use for components that support a `glyph` config. + * @param {String} fontFamily The name of the font-family + * @member Ext + */ + Ext.setGlyphFontFamily = function(fontFamily) { + Ext._glyphFontFamily = fontFamily; + }; + // These are legacy names which are now subsumed by Ext.GlobalEvents + Component.hierarchyEventSource = prototype.hierarchyEventSource = Ext.GlobalEvents; + // High Contrast mode in Windows disables background images and usually + // causes much pain by this. We feature detect it early and add this class + // to allow potential workarounds. + Ext.onReady(function() { + if (Ext.supports.HighContrastMode) { + Ext.getBody().addCls(Component.ariaHighContrastModeCls); + } + }); +}); +/* TODO + * + * ## Child Sessions + * + * By default, sessions created in child components are called "child sessions". + * All data and edits are copied from the parent session in to the child session. + * These changes can be written back to the parent session much like a session + * can save its data to a server. + * + * Ext.create({ + * xtype: 'window', + * modal: true, + * + * // Creates a new session for this Window but that session is linked + * // to a parent session (probably from the application's Viewport). + * // + * session: true, + * + * items: [{ + * ... + * },{ + * xtype: 'button', + * text: 'OK', + * listeners: { + * click: function () { + * // Get the Session this component has inherited (from + * // the Window) and save it back to the parent session. + * // + * this.lookupSession().save(); + * } + * } + * }] + * }); + * + * ### Isolated Sessions + * + * This connection of a child session to its parent session is determined by the + * `{@link Ext.data.Session#isolated isolated}` config. If `isolated` is + * set to `true` then this session will not copy anything from a higher level + * session and will instead do its own communication with the server. + * + * Ext.create({ + * xtype: 'window', + * modal: true, + * + * // Creates a new session for this Window that is isolated from any + * // other sessions. All data for this session will be fetched from + * // the server and ultimately saved back to the server. + * // + * session: { + * isolated: true + * }, + * + * items: [{ + * ... + * },{ + * xtype: 'button', + * text: 'OK', + * listeners: { + * click: function () { + * // Get the Session this component has inherited (from + * // the Window) and save it back to the server. + * // + * this.lookupSession().save(); + * } + * } + * }] + * }); + */ + +/** + * @class Ext.mixin.Focusable + */ +Ext.define('Ext.overrides.mixin.Focusable', { + override: 'Ext.Component', + /** + * @cfg {String} [focusCls='focus'] CSS class suffix that will be used to + * compose the CSS class name that will be added to Component's {@link #focusClsEl}, + * and removed when Component blurs. + * + * **Note** that this is not a full CSS class name; this suffix will be combined + * with component's UI class via {@link #addClsWithUI} and {@link #removeClsWithUI} methods. + */ + focusCls: 'focus', + /** + * Try to focus this component. + * + * If this component is disabled, a close relation will be targeted for focus instead + * to keep focus localized for keyboard users. + * @param {Mixed} [selectText] If applicable, `true` to also select all the text in this component, or an array consisting of start and end (defaults to start) position of selection. + * @param {Boolean/Number} [delay] Delay the focus this number of milliseconds (true for 10 milliseconds). + * @param {Function} [callback] Only needed if the `delay` parameter is used. A function to call upon focus. + * @param {Function} [scope] Only needed if the `delay` parameter is used. The scope (`this` reference) in which to execute the callback. + * @return {Ext.Component} The focused Component. Usually `this` Component. Some Containers may + * delegate focus to a descendant Component ({@link Ext.window.Window Window}s can do this through their + * {@link Ext.window.Window#defaultFocus defaultFocus} config option. If this component is disabled, a closely + * related component will be focused and that will be returned. + */ + focus: function(selectText, delay, callback, scope) { + var me = this, + containerScrollTop; + if ((!me.focusable && !me.isContainer) || me.destroyed || me.destroying) { + return me; + } + // If delay is wanted, queue a call to this function. + if (delay) { + me.getFocusTask().delay(Ext.isNumber(delay) ? delay : 10, me.focus, me, [ + selectText, + false, + callback, + scope + ]); + return me; + } + // An immediate focus call must cancel any outstanding delayed focus calls. + me.cancelFocus(); + if (me.floating && me.container && me.container.dom) { + containerScrollTop = me.container.dom.scrollTop; + } + // Core Focusable method will return true if focusing was attempted + if (me.mixins.focusable.focus.apply(me, arguments) !== false) { + if (callback) { + Ext.callback(callback, scope); + } + // Focusing a floating Component brings it to the front of its stack. + // this is performed by its zIndexManager. Pass preventFocus true to avoid recursion. + if (me.floating && containerScrollTop !== undefined) { + me.container.dom.scrollTop = containerScrollTop; + } + } + return me; + }, + /** + * Cancel any deferred focus on this component + * @protected + */ + cancelFocus: function() { + var me = this, + task = me.getFocusTask(); + if (task) { + task.cancel(); + } + }, + /** + * @method + * Template method to do any pre-blur processing. + * @protected + * @param {Ext.event.Event} e The event object + */ + beforeBlur: Ext.emptyFn, + /** + * @method + * Template method to do any post-blur processing. + * @protected + * @param {Ext.event.Event} e The event object + */ + postBlur: Ext.emptyFn, + /** + * @method + * Template method to do any pre-focus processing. + * @protected + * @param {Ext.event.Event} e The event object + */ + beforeFocus: Ext.emptyFn, + /** + * @method + * Template method to do any post-focus processing. + * @protected + * @param {Ext.event.Event} e The event object + */ + postFocus: Ext.emptyFn, + onFocusEnter: function(e) { + var me = this; + if (me.destroying || me.destroyed) { + return; + } + // Focusing must being a floating component to the front. + // Only bring to front if this component is not the manager's + // topmost component (may be a result of focusOnToFront). + if (me.floating && me !== me.zIndexManager.getActive()) { + me.toFront(true); + } + me.callParent([ + e + ]); + }, + destroyFocusable: function() { + var me = this; + // Calling cancelFocus() will assign focusTask property, + // which we don't want during destruction + if (me.focusTask) { + me.focusTask.stop(me.focus, me); + } + me.callParent(); + }, + privates: { + addFocusCls: function(e) { + var me = this, + focusCls = me.focusCls, + el; + if (focusCls) { + el = me.getFocusClsEl(e); + if (el) { + el.addCls(me.addClsWithUI(focusCls, true)); + } + } + }, + removeFocusCls: function(e) { + var me = this, + focusCls = me.focusCls, + el; + if (focusCls) { + el = me.getFocusClsEl(e); + if (el) { + el.removeCls(me.removeClsWithUI(focusCls, true)); + } + } + }, + /** + * @private + */ + getFocusTask: function() { + if (!this.focusTask) { + this.focusTask = Ext.focusTask; + } + return this.focusTask; + }, + updateMaskState: function(state, mask) { + var me = this, + ariaEl = me.ariaEl.dom, + value; + if (state) { + me.disableTabbing(); + me.setMasked(true); + if (ariaEl) { + ariaEl.setAttribute('aria-busy', 'true'); + // It is possible that ariaEl already has aria-describedby attribute; + // in that case we need to save it to restore later. + value = ariaEl.getAttribute('aria-describedby'); + if (value) { + me._savedAriaDescribedBy = value; + } + ariaEl.setAttribute('aria-describedby', mask.ariaEl.id); + } + } else { + me.enableTabbing(); + me.setMasked(false); + if (ariaEl) { + ariaEl.removeAttribute('aria-busy'); + value = ariaEl.getAttribute('aria-describedby'); + ariaEl.removeAttribute('aria-describedby'); + if (value === mask.ariaEl.id && me._savedAriaDescribedBy) { + ariaEl.setAttribute('aria-describedby', me._savedAriaDescribedBy); + delete me._savedAriaDescribedBy; + } + } + } + } + } +}, function() { + // One global DelayedTask to assign focus + // So that the last focus call wins. + if (!Ext.focusTask) { + Ext.focusTask = new Ext.util.DelayedTask(); + } +}); + +/** + * This override provides extra, border layout specific methods for `Ext.Component`. The + * `Ext.layout.container.Border` class requires this override so that the added functions + * are only included in a build when `border` layout is used. + */ +Ext.define('Ext.layout.container.border.Region', { + override: 'Ext.Component', + /** + * This method is called by the `Ext.layout.container.Border` class when instances are + * added as regions to the layout. Since it is valid to add any component to a border + * layout as a region, this method must be added to `Ext.Component` but is only ever + * called when that component is owned by a `border` layout. + * @private + */ + initBorderRegion: function() { + var me = this; + if (!me._borderRegionInited) { + me._borderRegionInited = true; + // Now that border regions can have dynamic region/weight, these need to be + // saved to state as they change: + me.addStateEvents([ + 'changeregion', + 'changeweight' + ]); + // We override getState on the instance for a couple reasons. Firstly, since + // there are very few border regions in an application, the overhead here is + // not a concern. Secondly, if this method were on the prototype it would + // impact all components. + Ext.override(me, { + getState: function() { + var state = me.callParent(); + // Now that border regions can have dynamic region/weight, these need to be saved + // to state: + state = me.addPropertyToState(state, 'region'); + state = me.addPropertyToState(state, 'weight'); + return state; + } + }); + } + }, + /** + * Returns the owning container if that container uses `border` layout. Otherwise + * this method returns `null`. + * @return {Ext.container.Container} The owning border container or `null`. + * @private + */ + getOwningBorderContainer: function() { + var layout = this.getOwningBorderLayout(); + return layout && layout.owner; + }, + /** + * Returns the owning `border` (`Ext.layout.container.Border`) instance if there is + * one. Otherwise this method returns `null`. + * @return {Ext.layout.container.Border} The owning border layout or `null`. + * @private + */ + getOwningBorderLayout: function() { + // the ownerLayot (if set) may or may not be a border layout + var layout = this.ownerLayout; + return (layout && layout.isBorderLayout) ? layout : null; + }, + /** + * This method changes the `region` config property for this border region. This is + * only valid if this component is in a `border` layout (`Ext.layout.container.Border`). + * @param {String} region The new `region` value (`"north"`, `"south"`, `"east"` or + * `"west"`). + * @return {String} The previous value of the `region` property. + */ + setRegion: function(region) { + var me = this, + borderLayout, + old = me.region; + if (typeof region !== 'string') { + // This method used to be basically the same as setBox, so check for an + // accidental use of the old signature. + Ext.raise('Use setBox to set the size or position of a component.'); + } + if (region !== old) { + borderLayout = me.getOwningBorderLayout(); + if (borderLayout) { + var regionFlags = borderLayout.regionFlags[region], + placeholder = me.placeholder, + splitter = me.splitter, + owner = borderLayout.owner, + regionMeta = borderLayout.regionMeta, + collapsed = me.collapsed || me.floated, + delta, items, index; + if (me.fireEventArgs('beforechangeregion', [ + me, + region + ]) === false) { + return old; + } + Ext.suspendLayouts(); + me.region = region; + Ext.apply(me, regionFlags); + if (me.updateCollapseTool) { + me.updateCollapseTool(); + } + if (splitter) { + // splitter.region = region; -- we don't set "region" on splitters! + Ext.apply(splitter, regionFlags); + splitter.updateOrientation(); + items = owner.items; + index = items.indexOf(me); + if (index >= 0) { + delta = regionMeta[region].splitterDelta; + if (items.getAt(index + delta) !== splitter) { + // splitter is not where we expect it, so move it there + items.remove(splitter); + index = items.indexOf(me); + // could have changed + if (delta > 0) { + ++index; + } + // else, insert at index and splitter will be before the item + items.insert(index, splitter); + } + } + } + // Now that the splitter is in the right place in me.items, + // the layout will fix up the DOM childNode to be at the same + // index as well. + if (placeholder) { + // The collapsed item is potentially remembering wrong things (for + // example, if it was collapsed as a West region and changed to be + // North). The only simple answer here is to expand/collapse the + // item (w/o animation). + if (collapsed) { + me.expand(false); + } + owner.remove(placeholder); + me.placeholder = null; + // force creation of a new placeholder + if (collapsed) { + me.collapse(null, false); + } + } + owner.updateLayout(); + Ext.resumeLayouts(true); + me.fireEventArgs('changeregion', [ + me, + old + ]); + } else { + me.region = region; + } + } + // maybe not added yet + return old; + }, + /** + * Sets the `weight` config property for this component. This is only valid if this + * component is in a `border` layout (`Ext.layout.container.Border`). + * @param {Number} weight The new `weight` value. + * @return {Number} The previous value of the `weight` property. + */ + setWeight: function(weight) { + var me = this, + ownerCt = me.getOwningBorderContainer(), + placeholder = me.placeholder, + old = me.weight; + if (weight !== old) { + if (me.fireEventArgs('beforechangeweight', [ + me, + weight + ]) !== false) { + me.weight = weight; + if (placeholder) { + placeholder.weight = weight; + } + if (ownerCt) { + ownerCt.updateLayout(); + } + me.fireEventArgs('changeweight', [ + me, + old + ]); + } + } + return old; + } +}, function(Component) { + var proto = Component.prototype; + // Aliases for v4 compat + proto.setBorderRegion = proto.setRegion; + proto.setRegionWeight = proto.setWeight; +}); + +Ext.define('Ext.overrides.app.domain.Component', { + override: 'Ext.app.domain.Component', + requires: [ + 'Ext.Component' + ] +}, function(ComponentDomain) { + // The core Component domain monitors events on the Ext.Widget class + // in Ext Components are not widgets so we need to monitor Ext.Component as well. + ComponentDomain.monitor(Ext.Component); +}); + +/** + * This class manages event dispatching for Controllers. The details of connecting classes + * to this dispatching mechanism is delegated to {@link Ext.app.EventDomain} instances. + * + * @private + */ +Ext.define('Ext.app.EventBus', { + singleton: true, + requires: [ + 'Ext.app.domain.Component' + ], + constructor: function() { + var me = this, + domains = Ext.app.EventDomain.instances; + me.callParent(); + me.domains = domains; + me.bus = domains.component.bus; + }, + // compat + /** + * Adds a set of component event listeners for a controller. To work with event domains + * other than component, see {@link #listen}. + * + * @param {Object} selectors Config object containing selectors and listeners. + * @param {Ext.app.BaseController} controller The listening controller instance. + */ + control: function(selectors, controller) { + return this.domains.component.listen(selectors, controller); + }, + /** + * Adds a set of event domain listeners for a controller. For more information on event + * domains, see {@link Ext.app.EventDomain} and {@link Ext.app.BaseController}. + * + * @param {Object} to Config object containing domains, selectors and listeners. + * @param {Ext.app.BaseController} controller The listening controller instance. + */ + listen: function(to, controller) { + var domains = this.domains, + domain; + for (domain in to) { + if (to.hasOwnProperty(domain)) { + domains[domain].listen(to[domain], controller); + } + } + }, + /** + * Removes all of a controller's attached listeners. + * + * @param {String/Ext.app.BaseController} controllerId The id or the controller instance. + */ + unlisten: function(controllerId) { + var domains = Ext.app.EventDomain.instances, + domain; + for (domain in domains) { + domains[domain].unlisten(controllerId); + } + } +}); + +/** + * This class implements the global event domain. This domain represents event fired from + * {@link Ext.GlobalEvents} Observable instance. No selectors are supported for this domain. + * + * @private + */ +Ext.define('Ext.app.domain.Global', { + extend: 'Ext.app.EventDomain', + requires: [ + 'Ext.GlobalEvents' + ], + singleton: true, + type: 'global', + constructor: function() { + var me = this; + me.callParent(); + me.monitor(Ext.GlobalEvents); + }, + /** + * This method adds listeners on behalf of a controller. Since Global domain does not + * support selectors, we skip this layer and just accept an object keyed by events. + * For example: + * + * domain.listen({ + * idle: function() { ... }, + * afterlayout: { + * fn: function() { ... }, + * delay: 10 + * } + * }); + * + * @param {Object} listeners Config object containing listeners. + * @param {Object} controller A controller to force execution scope on + * + * @private + */ + listen: function(listeners, controller) { + this.callParent([ + { + global: listeners + }, + controller + ]); + }, + match: Ext.returnTrue +}); + +/** + * Class that can manage the execution of route handlers. All {@link #befores} handlers + * will be executed prior to the {@link #actions} handlers. If at any point this `Action` + * class is stopped, no other handler (before or action) will be executed. + */ +Ext.define('Ext.route.Action', { + config: { + /** + * @cfg {Function[]} actions + * The action handlers to execute in response to the route executing. + * The individual functions will be executed with the scope of the class + * that connected the route and the arguments will be the configured URL + * parameters in order they appear in the token. + * + * See {@link #befores} also. + */ + actions: null, + /** + * @cfg {Function[]} befores + * The before handlers to execute prior to the {@link #actions} handlers. + * The individual functions will be executed with the scope of the class + * that connected the route and the arguments will be the configured URL + * parameters in the order they appear in the token plus this `Action` instance + * as the last argument. + * + * **IMPORTANT** A before function must have a resolution. You can do this + * by executing the {@link #resume} or {@link #stop} function or you can + * return a promise and resolve/reject it. + * + * var action = new Ext.route.Action({ + * before: { + * fn: function (action) { + * action.resume(); //or action.stop(); + * } + * } + * }); + * action.run(); + * + * var action = new Ext.route.Action({ + * before: { + * fn: function () { + * return new Ext.Promise(function (resolve, reject) { + * resolve(); //or reject(); + * }); + * } + * } + * }); + * action.run(); + * + * See {@link #actions} also. + */ + befores: null, + /** + * @cfg {Array} urlParams + * The URL parameters that were matched by the {@link Ext.route.Route}. + */ + urlParams: [] + }, + /** + * @property {Ext.Deferred} deferred + * The deferral object that will resolve after all functions have executed + * ({@link #befores} and {@link #actions}) or reject if any {@link #befores} + * function stops this action. + * @private + */ + /** + * @property {Boolean} [started=false] + * Whether or not this class has started executing any {@link #befores} or {@link #actions}. + * @readonly + * @protected + */ + started: false, + /** + * @property {Boolean} [stopped=false] + * Whether or not this class was stopped by a {@link #befores} function. + * @readonly + * @protected + */ + stopped: false, + constructor: function(config) { + var me = this; + me.deferred = new Ext.Deferred(); + me.resume = me.resume.bind(me); + me.stop = me.stop.bind(me); + me.initConfig(config); + me.callParent([ + config + ]); + }, + applyActions: function(actions) { + if (actions) { + actions = Ext.Array.from(actions); + } + return actions; + }, + applyBefores: function(befores) { + if (befores) { + befores = Ext.Array.from(befores); + } + return befores; + }, + destroy: function() { + this.deferred = null; + this.setBefores(null).setActions(null).setUrlParams(null); + this.callParent(); + }, + /** + * Allow further function execution of other functions if any. + * + * @return {Ext.route.Action} this + */ + resume: function() { + return this.next(); + }, + /** + * Prevent other functions from executing and resolve the {@link #deferred}. + * + * @return {Ext.route.Action} this + */ + stop: function() { + this.stopped = true; + return this.done(); + }, + /** + * Executes the next {@link #befores} or {@link #actions} function. If {@link #stopped} + * is `true` or no functions are left to execute, the {@link #done} function will be called. + * + * @private + * @return {Ext.route.Action} this + */ + next: function() { + var me = this, + actions = me.getActions(), + befores = me.getBefores(), + urlParams = me.getUrlParams().slice(), + config, ret; + if (me.stopped || (befores ? !befores.length : true) && (actions ? !actions.length : true)) { + me.done(); + } else { + if (befores && befores.length) { + config = befores.shift(); + urlParams.push(me); + ret = Ext.callback(config.fn, config.scope, urlParams); + if (ret && ret.then) { + ret.then(function(arg) { + me.resume(arg); + }, function(arg) { + me.stop(arg); + }); + } + } else if (actions && actions.length) { + config = actions.shift(); + Ext.callback(config.fn, config.scope, urlParams); + me.next(); + } else { + //needed? + me.next(); + } + } + return me; + }, + /** + * Starts the execution of {@link #befores} and/or {@link #actions} functions. + * + * @return {Ext.promise.Promise} + */ + run: function() { + var deferred = this.deferred; + if (!this.started) { + this.next(); + this.started = true; + } + return deferred.promise; + }, + /** + * When no {@link #befores} or {@link #actions} functions are left to execute + * or {@link #stopped} is `true`, this function will be executed to resolve + * or reject the {@link #deferred} object. + * + * @private + * @return {Ext.route.Action} this + */ + done: function() { + var deferred = this.deferred; + if (this.stopped) { + deferred.reject(); + } else { + deferred.resolve(); + } + this.destroy(); + return this; + }, + /** + * Add a function to the {@link #befores} stack. + * + * action.before(function() {}, this); + * + * By default, the function will be added to the end of the {@link #befores} stack. If + * instead the function should be placed at the beginning of the stack, you can pass + * `true` as the first argument: + * + * action.before(true, function() {}, this); + * + * @param {Boolean} [first=false] Pass `true` to add the function to the beginning of the + * {@link #befores} stack instead of the end. + * @param {Function/String} fn The function to add to the {@link #befores}. + * @param {Object} [scope] The scope of the function to execute with. This is normally + * the class that is adding the function to the before stack. + * @return {Ext.route.Action} this + */ + before: function(first, fn, scope) { + if (!Ext.isBoolean(first)) { + scope = fn; + fn = first; + first = false; + } + var befores = this.getBefores(), + config = { + fn: fn, + scope: scope + }; + if (this.destroyed) { + Ext.raise('This action has has already resolved and therefore will never execute this function.'); + return; + } + if (befores) { + if (first) { + befores.unshift(config); + } else { + befores.push(config); + } + } else { + this.setBefores(config); + } + return this; + }, + /** + * Add a function to the {@link #actions} stack. + * + * action.action(function() {}, this); + * + * By default, the function will be added to the end of the {@link #actions} stack. If + * instead the function should be placed at the beginning of the stack, you can pass + * `true` as the first argument: + * + * action.action(true, function() {}, this); + * + * @param {Boolean} [first=false] Pass `true` to add the function to the beginning of the + * {@link #befores} stack. + * @param {Function/String} fn The function to add to the {@link #actions}. + * @param {Object} [scope] The scope of the function to execute with. This is normally + * the class that is adding the function to the action stack. + * @return {Ext.route.Action} this + */ + action: function(first, fn, scope) { + if (!Ext.isBoolean(first)) { + scope = fn; + fn = first; + first = false; + } + var actions = this.getActions(), + config = { + fn: fn, + scope: scope + }; + if (this.destroyed) { + Ext.raise('This action has has already resolved and therefore will never execute this function.'); + return; + } + if (actions) { + if (first) { + actions.unshift(config); + } else { + actions.push(config); + } + } else { + this.setActions(config); + } + return this; + }, + /** + * Execute functions when this action has been resolved or rejected. + * + * @param {Function} resolve The function to execute when this action has been resolved. + * @param {Function} reject The function to execute when a before function stopped this action. + * @return {Ext.Promise} + */ + then: function(resolve, reject) { + if (this.destroyed) { + Ext.raise('This action has has already resolved and therefore will never execute either function.'); + return; + } + return this.deferred.then(resolve, reject); + } +}); + +/** + * Enables reactive actions to handle changes in the hash by using the + * {@link Ext.route.Mixin#routes routes} configuration in a controller. + * An example configuration would be: + * + * Ext.define('MyApp.view.main.MainController', { + * extend: 'Ext.app.ViewController', + * alias: 'controller.app-main', + * + * routes: { + * 'user/:id': 'onUser' + * }, + * + * onUser: function (id) { + * // ... + * } + * }); + * + * The `routes` object can also receive an object to further configure + * the route, for example you can configure a `before` action that will + * be executed before the `action` or can cancel the route execution: + * + * Ext.define('MyApp.view.main.MainController', { + * extend: 'Ext.app.ViewController', + * alias: 'controller.app-main', + * + * routes: { + * 'user/:id': { + * action: 'onUser', + * before: 'onBeforeUser' + * } + * }, + * + * onBeforeUser: function (id) { + * return new Ext.Promise(function (resolve, reject) { + * Ext.Ajax + * .request({ + * url: '/check/permission', + * params: { + * route: 'user', + * meta: { + * id: id + * } + * } + * }) + * .then(resolve, reject); + * }); + * }, + * + * onUser: function (id) { + * // ... + * } + * }); + */ +Ext.define('Ext.route.Route', { + requires: [ + 'Ext.route.Action' + ], + /** + * @event beforeroute + * @member Ext.GlobalEvents + * + * Fires when a route is about to be executed. This allows pre-processing to add additional + * {@link Ext.route.Action#before before} or {@link Ext.route.Action#action action} handlers + * when the {@link Ext.route.Action Action} is run. + * + * The route can be prevented from executing by returning `false` in a listener + * or executing the {@link Ext.route.Action#stop stop} method on the action. + * + * @param {Ext.route.Route} route The route being executed. + * @param {Ext.route.Action} action The action that will be run. + */ + config: { + /** + * @cfg {String} name The name of this route. The name can be used when using + * {@link Ext.route.Mixin#redirectTo}. + */ + name: null, + /** + * @cfg {String} url (required) The url regex to match against. + */ + url: null, + /** + * @cfg {Boolean} [allowInactive=false] `true` to allow this route to be triggered on + * a controller that is not active. + */ + allowInactive: false, + /** + * @cfg {Boolean} [caseInsensitive=false] `true` to allow the tokens to be matched with + * case-insensitive. + */ + caseInsensitive: false, + /** + * @private + * @cfg {Object[]} [handler=[]] The array of connected handlers to this route. Each handler + * must defined a `scope` and can define an `action`, `before` and/or `exit` handler: + * + * handlers: [{ + * action: function() { + * //... + * }, + * scope: {} + * }, { + * action: function() { + * //... + * }, + * before: function() { + * //... + * }, + * scope: {} + * }, { + * exit: function() { + * //... + * }, + * scope: {} + * }] + * + * The `action`, `before` and `exit` handlers can be a string that will be resolved + * from the `scope`: + * + * handlers: [{ + * action: 'onAction', + * before: 'onBefore', + * exit: 'onExit', + * scope: { + * onAction: function () { + * //... + * }, + * onBefore: function () { + * //... + * }, + * onExit: function () { + * //... + * } + * } + * }] + */ + handlers: [] + }, + /** + * @cfg {Object} conditions Optional set of conditions for each token in the url + * string. Each key should be one of the tokens, each value should be a regex that the + * token should accept. For example, if you have a Route with a url like + * `"files/:fileName"` and you want it to match urls like "files/someImage.jpg" then + * you can set these conditions to allow the :fileName token to accept strings + * containing a period ("."): + * + * conditions: { + * ':fileName': "[0-9a-zA-Z\.]+" + * } + */ + /** + * @property {String} [defaultMatcher='([%a-zA-Z0-9\\-\\_\\s,]+)'] The default RegExp string + * to use to match parameters with. + */ + defaultMatcher: '([%a-zA-Z0-9\\-\\_\\s,]+)', + /** + * @private + * @property {RegExp} matcherRegex A regular expression to match the token to the configured {@link #url}. + */ + /** + * @private + * @property {RegExp} paramMatchingRegex A regular expression to check if there are parameters in the configured {@link #url}. + */ + paramMatchingRegex: /:([0-9A-Za-z\_]*)/g, + /** + * @private + * @property {Array} paramsInMatchString An array of parameters in the configured {@link #url}. + */ + /** + * @protected + * @property {Boolean} [isRoute=true] + */ + isRoute: true, + constructor: function(config) { + var me = this, + url; + this.initConfig(config); + Ext.apply(me, config, { + conditions: {} + }); + url = me.getUrl(); + me.paramsInMatchString = url.match(me.paramMatchingRegex) || []; + me.matcherRegex = me.createMatcherRegex(url); + }, + /** + * Attempts to recognize a given url string and return a meta data object including + * any URL parameter matches. + * + * @param {String} url The url to recognize. + * @return {Object/Boolean} The matched data, or `false` if no match. + */ + recognize: function(url) { + var me = this, + recognized = me.recognizes(url), + matches, urlParams; + if (url === me.lastToken) { + //url matched the lastToken + return true; + } + if (recognized) { + matches = me.matchesFor(url); + urlParams = url.match(me.matcherRegex); + urlParams.shift(); + return Ext.applyIf(matches, { + historyUrl: url, + urlParams: urlParams + }); + } + return false; + }, + /** + * Returns true if this {@link Ext.route.Route} matches the given url string. + * + * @param {String} url The url to test. + * @return {Boolean} `true` if this {@link Ext.route.Route} recognizes the url. + */ + recognizes: function(url) { + return this.matcherRegex.test(url); + }, + /** + * The method to execute the action using the configured before function which will + * kick off the actual {@link #actions} on the {@link #controller}. + * + * @param token + * @param {Object} argConfig The object from the {@link Ext.route.Route}'s + * recognize method call. + * @return {Ext.promise.Promise} + */ + execute: function(token, argConfig) { + var me = this, + allowInactive = me.getAllowInactive(), + handlers = me.getHandlers(), + queue = Ext.route.Router.getQueueRoutes(), + length = handlers.length, + befores = [], + actions = [], + urlParams = (argConfig && argConfig.urlParams) || [], + i, handler, scope, action, promises; + me.lastToken = token; + if (!queue) { + promises = []; + } + return new Ext.Promise(function(resolve, reject) { + for (i = 0; i < length; i++) { + handler = handlers[i]; + scope = handler.scope; + if (!allowInactive && scope.isActive && !scope.isActive()) { + + continue; + } + if (queue) { + if (handler.before) { + befores.push({ + fn: handler.before, + scope: scope + }); + } + if (handler.action) { + actions.push({ + fn: handler.action, + scope: scope + }); + } + } else { + action = { + urlParams: urlParams + }; + if (handler.before) { + action.befores = { + fn: handler.before, + scope: scope + }; + } + if (handler.action) { + action.actions = { + fn: handler.action, + scope: scope + }; + } + action = new Ext.route.Action(action); + if (Ext.fireEvent('beforeroute', action, me) === false) { + action.destroy(); + } else { + promises.push(action.run()); + } + } + } + if (queue) { + action = new Ext.route.Action({ + actions: actions, + befores: befores, + urlParams: urlParams + }); + if (Ext.fireEvent('beforeroute', action, me) === false) { + action.destroy(); + reject(); + } else { + action.run().then(resolve, reject); + } + } else { + Ext.Promise.all(promises).then(resolve, reject); + } + }); + }, + /** + * Returns a hash of matching url segments for the given url. + * + * @param {String} url The url to extract matches for + * @return {Object} matching url segments + */ + matchesFor: function(url) { + var params = {}, + keys = this.paramsInMatchString, + values = url.match(this.matcherRegex), + length = keys.length, + i; + //first value is the entire match so reject + values.shift(); + for (i = 0; i < length; i++) { + params[keys[i].replace(':', '')] = values[i]; + } + return params; + }, + /** + * Takes the configured url string including wildcards and returns a regex that can be + * used to match against a url. + * + * @param {String} url The url string. + * @return {RegExp} The matcher regex. + */ + createMatcherRegex: function(url) { + // Converts a route string into an array of symbols starting with a colon. e.g. + // ":controller/:action/:id" => [':controller', ':action', ':id'] + var paramsInMatchString = this.paramsInMatchString, + conditions = this.conditions, + defaultMatcher = this.defaultMatcher, + length = paramsInMatchString.length, + modifiers = this.getCaseInsensitive() ? 'i' : '', + i, params, matcher; + if (url === '*') { + // handle wildcard routes, won't have conditions + url = url.replace('*', '\\*'); + } else { + for (i = 0; i < length; i++) { + params = paramsInMatchString[i]; + matcher = conditions[params] || defaultMatcher; + url = url.replace(new RegExp(params), matcher); + } + } + //we want to match the whole string, so include the anchors + return new RegExp('^' + url + '$', modifiers); + }, + /* + * Adds a handler to the {@link #handlers} stack. + * + * @param {Object} handler An object to describe the handler. A handler should define a `fn` + * and `scope`. If the `fn` is a String, the function will be resolved from the `scope`. + * @return {Ext.route.Route} this + */ + addHandler: function(handler) { + var handlers = this.getHandlers(); + handlers.push(handler); + return this; + }, + /** + * Removes a handler from th {@link #handlers} stack. This normally happens when + * destroying a class instance. + * + * @param {Object/Ext.Base} scope The class instance to match handlers with. + * @param {Object} config An optional object to describe which handlers to remove. + * This can be used to remove all handlers with a certain `before` or `action`. + * @return {Ext.route.Route} this + */ + removeHandler: function(scope, config) { + var handlers = this.getHandlers(), + length = handlers.length, + newHandlers = [], + i, handler; + for (i = 0; i < length; i++) { + handler = handlers[i]; + if (handler.scope === scope) { + if (!config || (Ext.isDefined(config.action) ? handler.action === config.action : true && Ext.isDefined(config.before) ? handler.before === config.before : true)) { + + continue; + } + } + newHandlers.push(handler); + } + this.setHandlers(newHandlers); + return this; + } +}); + +/** + * History management component that allows you to register arbitrary tokens that signify application + * history state on navigation actions. You can then handle the history {@link #change} event in order + * to reset your application UI to the appropriate state when the user navigates forward or backward through + * the browser history stack. + * + * ## Initializing + * + * The {@link #init} method of the History object must be called before using History. This sets up the internal + * state and must be the first thing called before using History. + */ +Ext.define('Ext.util.History', { + singleton: true, + alternateClassName: 'Ext.History', + mixins: { + observable: 'Ext.util.Observable' + }, + /** + * @property + * True to use `window.top.location.hash` or false to use `window.location.hash`. Must be set before {@link #init} is called + * because the `hashchange` event listener is added to the window at initialization time. + */ + useTopWindow: false, + /** + * @property {Boolean} hashbang If set to `true`, when a hash is set, the hash will be prefixed + * with an exclamation making it a hash bang instead of just a hash. + * + * Ext.util.History.add('foo'); // will result in #foo + * + * Ext.util.History.hashbang = true; + * Ext.util.History.add('bar'); // will result in #!bar + */ + /** + * @property {String} currentToken The current token. + * @private + */ + /** + * @event ready + * Fires when the Ext.util.History singleton has been initialized and is ready for use. + * @param {Ext.util.History} history The Ext.util.History singleton. + */ + /** + * @event change + * Fires when navigation back or forwards within the local page's history occurs. + * @param {String} token An identifier associated with the page state at that point in its history. + */ + hashRe: /^(#?!?)/, + constructor: function() { + var me = this; + me.ready = false; + me.currentToken = null; + me.mixins.observable.constructor.call(me); + }, + /** + * Gets the actual hash from the url. This shouldn't need to be used directly but use the + * {@link #getToken} method instead. + * + * @return {String} The hash from the window object. + * @private + */ + getHash: function() { + return this.win.location.hash.replace(this.hashRe, ''); + }, + /** + * Updates the hash on the window. This shouldn't need to be used directly but use the + * {@link #add} method instead. + * + * @param {String} hash The hash to use + * @param {Boolean} replace If `true`, the hash passed in will replace the current resource + * by using the `location.replace()` API. + * @private + */ + setHash: function(hash, replace) { + var me = this, + hashRe = me.hashRe, + loc = me.win.location; + // may or may not already be prefixed with # or #! already + hash = hash.replace(hashRe, me.hashbang ? '#!' : '#'); + try { + if (replace) { + loc.replace(hash); + } else { + loc.hash = hash; + } + //need to make sure currentToken is not prefixed + me.currentToken = hash.replace(hashRe, ''); + } catch (e) {} + }, + // IE can give Access Denied (esp. in popup windows) + /** + * Handles when the hash in the URL has been updated. Will also fired the change event. + * + * @param {String} token The token that was changed to + * @private + */ + handleStateChange: function(token) { + // browser won't have # here but may have ! + token = token.replace(this.hashRe, ''); + this.fireEvent('change', this.currentToken = token); + }, + /** + * Bootstraps the initialization the location.hash. + * @private + */ + startUp: function() { + var me = this; + me.currentToken = me.getHash(); + Ext.get(me.win).on('hashchange', me.onHashChange, me); + me.ready = true; + me.fireEvent('ready', me); + }, + onHashChange: function() { + var me = this, + newHash = me.getHash(); + if (newHash !== me.hash) { + me.hash = newHash; + me.handleStateChange(newHash); + } + }, + /** + * Initializes the global History instance. + * @param {Function} [onReady] A callback function that will be called once the history + * component is fully initialized. + * @param {Object} [scope] The scope (`this` reference) in which the callback is executed. + * Defaults to the browser window. + */ + init: function(onReady, scope) { + var me = this; + if (me.ready) { + Ext.callback(onReady, scope, [ + me + ]); + return; + } + if (!Ext.isReady) { + Ext.onInternalReady(function() { + me.init(onReady, scope); + }); + return; + } + me.win = me.useTopWindow ? window.top : window; + me.hash = me.getHash(); + if (onReady) { + me.on('ready', onReady, scope, { + single: true + }); + } + me.startUp(); + }, + /** + * Add a new token to the history stack. This can be any arbitrary value, although it would + * commonly be the concatenation of a component id and another id marking the specific history + * state of that component. Example usage: + * + * // Handle tab changes on a TabPanel + * tabPanel.on('tabchange', function(tabPanel, tab){ + * Ext.History.add(tabPanel.id + ':' + tab.id); + * }); + * + * @param {String} token The value that defines a particular application-specific history state + * @param {Boolean} [preventDuplicates=true] When true, if the passed token matches the current token + * it will not save a new history step. Set to false if the same state can be saved more than once + * at the same history stack location. + * + * @return {Boolean} Whether the token was set in the case if the current token matches the token + * passed. + */ + add: function(token, preventDuplicates) { + var me = this, + set = false; + if (preventDuplicates === false || me.getToken() !== token) { + me.setHash(token); + set = true; + } + return set; + }, + /** + * Replaces the current resource in history. + * + * @param {String} token The value that will replace the current resource in the history state. + * @param {Boolean} [preventDuplicates=true] When `true`, if the passed token matches the current token + * it will not save a new history step. Set to `false` if the same state can be saved more than once + * at the same history stack location. + * + * @return {Boolean} Whether the token was set in the case if the current token matches the token + * passed. + */ + replace: function(token, preventDuplicates) { + var me = this, + set = false; + if (preventDuplicates === false || me.getToken() !== token) { + this.setHash(token, true); + set = true; + } + return set; + }, + /** + * Programmatically steps back one step in browser history (equivalent to the user pressing the Back button). + */ + back: function() { + this.win.history.go(-1); + }, + /** + * Programmatically steps forward one step in browser history (equivalent to the user pressing the Forward button). + */ + forward: function() { + this.win.history.go(1); + }, + /** + * Retrieves the currently-active history token. + * @return {String} The token + */ + getToken: function() { + return this.ready ? this.currentToken : this.getHash(); + } +}); + +/** + * The Router is an ordered set of {@link Ext.route.Route} definitions that decode a + * url into a controller function to execute. Each `route` defines a type of url to match, + * along with the controller function to call if it is matched. The Router uses the + * {@link Ext.util.History} singleton to find out when the browser's url has changed. + * + * Routes are almost always defined inside a {@link Ext.Controller Controller}, as + * opposed to on the Router itself. End-developers should not usually need to interact + * directly with the Router as the Controllers manage everything automatically. See the + * {@link Ext.Controller Controller documentation} for more information on specifying + * routes. + */ +Ext.define('Ext.route.Router', { + singleton: true, + requires: [ + 'Ext.route.Action', + 'Ext.route.Route', + 'Ext.util.History' + ], + /** + * @event beforeroutes + * @member Ext.GlobalEvents + * + * Fires when the hash has changed and before any routes are executed. This allows + * pre-processing to add additional {@link Ext.route.Action#before before} or + * {@link Ext.route.Action#action action} handlers when the + * {@link Ext.route.Action Action} is run. + * + * Route execution can be prevented by returning `false` in the listener + * or executing the {@link Ext.route.Action#stop stop} method on the action. + * + * @param {Ext.route.Action} action An action that will be executed + * prior to any route execution. + * @param {String[]} tokens An array of individual tokens in the hash. + */ + /** + * @event routereject + * @member Ext.GlobalEvents + * + * Fires when a route was rejected from either a before action, {@link Ext.GlobalEvents#beforeroutes} event + * or {@link Ext.GlobalEvents#beforeroute} event. + * + * @param {Ext.route.Route} route The route which had it's execution rejected. + */ + config: { + /** + * @cfg {Boolean} hashBang Sets {@link Ext.util.History#hashbang} to enable/disable + * hashbang support. + */ + hashbang: null, + /** + * @cfg {String} [multipleToken=|] The token to split the routes to support multiple routes. + */ + multipleToken: '|', + /** + * @cfg {Boolean} [queueRoutes=true] `true` to queue routes to be executed one after the + * other, false to execute routes immediately. + */ + queueRoutes: true + }, + /** + * @property {Object} routes The connected {@link Ext.route.Route} + * instances. + */ + /** + * @property {Boolean} isSuspended `true` if the router is currently suspended. + */ + constructor: function() { + var History = Ext.util.History; + if (!History.ready) { + History.init(); + } + History.on('change', this.onStateChange, this); + this.initConfig(); + this.clear(); + }, + updateHashbang: function(hashbang) { + Ext.util.History.hashbang = hashbang; + }, + /** + * React to a token + * + * @private + * @param {String} token The token to react to. + */ + onStateChange: function(token) { + var me = this, + tokens = token.split(me.getMultipleToken()), + queue, i, length; + if (me.isSuspended) { + queue = me.suspendedQueue; + i = 0; + length = tokens.length; + if (queue) { + for (; i < length; i++) { + token = tokens[i]; + //shouldn't keep track of duplicates + if (!Ext.Array.contains(queue, token)) { + queue.push(token); + } + } + } + } else { + me.handleBefore(tokens); + } + }, + /** + * Fires the {@link Ext.GlobalEvents#beforeroutes} event and if + * `false` is returned can prevent any routes from executing. + * + * @private + * @param {String[]} tokens The individual tokens that were split from the hash + * using {@link #multipleToken}. + */ + handleBefore: function(tokens) { + var me = this, + action = new Ext.route.Action(); + if (Ext.fireEvent('beforeroutes', action, tokens) === false) { + action.destroy(); + } else { + action.run().then(me.handleBeforeRoute.bind(me, tokens), Ext.emptyFn); + } + }, + /** + * If a wildcard route was connected, that route needs to execute prior + * to any other route. + * + * @private + * @param {String[]} tokens The individual tokens that were split from the hash + * using {@link #multipleToken}. + */ + handleBeforeRoute: function(tokens) { + var me = this, + beforeRoute = me.getByName('*'); + if (beforeRoute) { + beforeRoute.execute().then(me.doRun.bind(me, tokens), Ext.emptyFn); + } else { + //no befores, go ahead with route determination + me.doRun(tokens); + } + }, + /** + * Find routes that recognize one of the tokens in the document fragment + * and then exeucte the routes. + * + * @private + * @param {String[]} tokens The individual tokens that were split from the hash + * using {@link #multipleToken}. + */ + doRun: function(tokens) { + var me = this, + app = me.application, + routes = me.routes, + i = 0, + length = tokens.length, + matched = {}, + unmatched = [], + token, found, name, route, recognize; + for (; i < length; i++) { + token = tokens[i]; + found = false; + for (name in routes) { + route = routes[name]; + recognize = route.recognize(token); + if (recognize) { + found = true; + if (recognize !== true) { + // The document fragment may have changed but the token + // part that the route recognized did not change. Therefore + // is was matched but we should not execute the route again. + route.execute(token, recognize).then(null, Ext.bind(me.onRouteRejection, me, [ + route + ])); + } + Ext.Array.remove(unmatched, route); + if (!matched[name]) { + matched[name] = 1; + } + } else if (!matched[name]) { + unmatched.push(route); + } + } + if (!found) { + if (app) { + //backwards compat + app.fireEvent('unmatchedroute', token); + } + Ext.fireEvent('unmatchedroute', token); + } + } + i = 0; + length = unmatched.length; + for (; i < length; i++) { + route = unmatched[i]; + // Need to reset route's `lastToken` so that when a token + // is added to the document fragment it will not be falsely + // matched. + route.lastToken = null; + } + }, + /** + * @private + * Called when a route was rejected. + */ + onRouteRejection: function(route) { + Ext.fireEvent('routereject', route); + }, + /** + * Create the {@link Ext.route.Route} instance and connect to the + * {@link Ext.route.Router} singleton. + * + * @param {String} url The url to recognize. + * @param {String} config The config on the controller to execute when the url is + * matched. + * @param {Ext.Base} instance The class instance associated with the + * {@link Ext.route.Route} + */ + connect: function(url, config, instance) { + var routes = this.routes, + name = config.name || url, + route, name; + if (url[0] === '!') { + if (!Ext.util.History.hashbang) { + Ext.log({ + level: 'error', + msg: 'Route found with "!" ("' + url + '"). Should use new hashbang functionality instead. ' + 'Please see the router guide for more: https://docs.sencha.com/extjs/' + Ext.getVersion().version + '/guides/application_architecture/router.html' + }); + } + url = url.substr(1); + this.setHashbang(true); + } + if (Ext.isString(config)) { + config = { + action: config, + scope: instance + }; + } else { + config.scope = instance; + } + route = routes[name]; + if (!route) { + route = routes[name] = new Ext.route.Route({ + conditions: config.conditions || {}, + name: name, + url: url + }); + } + route.addHandler(config); + }, + /** + * Disconnects all route handlers for a class instance. + * + * @param {Ext.Base} instance The class instance to disconnect route handlers from. + * @param {Object} config An optional config object to match a handler for. This will check + * all route handlers connected to the instance for match based on the action and before + * configurations. + */ + disconnect: function(instance, config) { + var routes = this.routes, + route, name; + if (config) { + route = this.getByName(config.name || config.url); + if (route) { + route.removeHandler(instance, config); + } + } else { + for (name in routes) { + route = routes[name]; + route.removeHandler(instance); + } + } + }, + /** + * Recognizes a url string connected to the Router, return the controller/action pair + * plus any additional config associated with it. + * + * @param {String} url The url to recognize. + * @return {Object/Boolean} If the url was recognized, the controller and action to + * call, else `false`. + */ + recognize: function(url) { + var routes = this.routes, + matches = [], + name, arr, i, length, route, urlParams; + for (name in routes) { + arr = routes[name]; + length = arr && arr.length; + if (length) { + i = 0; + for (; i < length; i++) { + route = arr[i]; + urlParams = route.recognize(url); + if (urlParams) { + matches.push({ + route: route, + urlParams: urlParams + }); + } + } + } + } + return matches.length ? matches : false; + }, + /** + * Convenience method which just calls the supplied function with the + * {@link Ext.route.Router} singleton. Example usage: + * + * Ext.route.Router.draw(function(map) { + * map.connect('activate/:token', {controller: 'users', action: 'activate'}); + * map.connect('home', {controller: 'index', action: 'home'}); + * }); + * + * @param {Function} fn The function to call + */ + draw: function(fn) { + fn.call(this, this); + }, + /** + * Clear all the recognized routes. + */ + clear: function() { + this.routes = {}; + }, + /** + * Resets the connected routes' last token they were executed on. + * @param {String} [token] If passed, only clear matching routes. + * @private + */ + clearLastTokens: function(token) { + var routes = this.routes, + name, route; + for (name in routes) { + route = routes[name]; + if (!token || route.recognize(token)) { + route.lastToken = null; + } + } + }, + /** + * Gets all routes by {@link Ext.route.Route#name}. + * + * @return {Ext.route.Route[]} If no routes found, `undefined` will be returned otherwise + * the array of {@link Ext.route.Route Routes} will be returned. + */ + getByName: function(name) { + var routes = this.routes; + if (routes) { + return routes[name]; + } + }, + /** + * Suspends the handling of tokens (see {@link #resume}). + * + * @param {Boolean} [trackTokens] `false` to prevent any tokens to be + * queued while being suspended. + */ + suspend: function(trackTokens) { + this.isSuspended = true; + if (!this.suspendedQueue && trackTokens !== false) { + this.suspendedQueue = []; + } + }, + /** + * Resumes the execution of routes (see {@link #suspend}). + * + * @param {Boolean} [discardQueue] `true` to prevent any previously queued + * tokens from being enacted on. + */ + resume: function(discardQueue) { + var me = this, + queue = me.suspendedQueue, + token; + if (me.isSuspended) { + me.isSuspended = false; + me.suspendedQueue = null; + if (!discardQueue && queue) { + token = queue.join(me.getMultipleToken()); + me.onStateChange(token); + } + } + } +}); + +/** + * A mixin to allow any class to configure and listen to routes and also change the hash. + */ +Ext.define('Ext.route.Mixin', { + extend: 'Ext.Mixin', + requires: [ + 'Ext.route.Router' + ], + mixinConfig: { + id: 'routerable', + before: { + destroy: 'destroyRouterable' + } + }, + config: { + /** + * @cfg {Object} routes + * @accessor + * + * An object of routes to handle hash changes. A route can be defined in a simple way: + * + * routes: { + * 'foo/bar': 'handleFoo', + * 'user/:id': 'showUser' + * } + * + * Where the property is the hash (which can accept a parameter defined by a colon) and the value + * is the method on the controller to execute. The parameters will get sent in the action method. + * + * If no routes match a given hash, an {@link Ext.GlobalEvents#unmatchedroute} event will be fired. + * This can be listened to in four ways: + * + * Ext.on('unmatchedroute', function(token) {}); + * + * Ext.define('MyApp.controller.Foo', { + * extend: 'Ext.app.Controller', + * + * listen: { + * global: { + * unmatchedroute: 'onUnmatchedRoute' + * } + * }, + * + * onUnmatchedRoute: function(token) {} + * }); + * + * Ext.application({ + * name: 'MyApp', + * + * listen: { + * global: { + * unmatchedroute: 'onUnmatchedRoute' + * } + * }, + * + * onUnmatchedRoute: function(token) {} + * }); + * + * Ext.application({ + * name: 'MyApp', + * + * listeners: { + * unmatchedroute: 'onUnmatchedRoute' + * }, + * + * onUnmatchedRoute: function(token) {} + * }); + * + * There is also a complex means of defining a route where you can use a before action and even + * specify your own RegEx for the parameter: + * + * routes: { + * 'foo/bar': { + * action: 'handleFoo', + * before: 'beforeHandleFoo' + * }, + * 'user/:id': { + * action: 'showUser', + * before: 'beforeShowUser', + * conditions: { + * ':id': '([0-9]+)' + * } + * } + * } + * + * This will only match if the `id` parameter is a number. + * + * The before action allows you to cancel an action. Every before action will get passed an `action` argument with + * a `resume` and `stop` methods as the last argument of the method and you *MUST* execute either method: + * + * beforeHandleFoo: function (action) { + * //some logic here + * + * //this will allow the handleFoo action to be executed + * action.resume(); + * }, + * handleFoo: function () { + * //will get executed due to true being passed in callback in beforeHandleFoo + * }, + * beforeShowUser: function (id, action) { + * //allows for async process like an Ajax + * Ext.Ajax.request({ + * url: 'foo.php', + * success: function () { + * //will not allow the showUser method to be executed but will continue other queued actions. + * action.stop(); + * }, + * failure: function () { + * //will not allow the showUser method to be executed and will not allow other queued actions to be executed. + * action.stop(true); + * } + * }); + * }, + * showUser: function (id) { + * //will not get executed due to false being passed in callback in beforeShowUser + * } + * + * You **MUST** execute the `{@link Ext.route.Action#resume resume}` or `{@link Ext.route.Action#stop stop}` method on + * the `action` argument. Executing `action.resume();` will continue the action, `action.stop();` + * will prevent further execution. + * + * The default RegEx that will be used is `([%a-zA-Z0-9\\-\\_\\s,]+)` but you can specify any + * that may suit what you need to accomplish. An example of an advanced condition may be to make + * a parameter optional and case-insensitive: + * + * routes: { + * 'user:id': { + * action: 'showUser', + * before: 'beforeShowUser', + * conditions: { + * ':id': '(?:(?:\/){1}([%a-z0-9_,\s\-]+))?' + * } + * } + * } + * + * Each route can be named; this allows for the route to be looked up by name instead of url. By default, the route's name + * will be the url you configure but you can provide the `{@link Ext.route.Route#name name}` config to override the default: + * + * routes: { + * 'user:id': { + * action: 'showUser', + * before: 'beforeShowUser', + * name: 'user', + * conditions: { + * ':id': '(?:(?:\/){1}([%a-z0-9_,\s\-]+))?' + * } + * } + * } + * + * The `user:id` route can not be looked up via the `user` name which is useful when using `{@link #redirectTo}`. + * + * A wildcard route can also be defined which works exactly like any other route but will always execute before any + * other route. To specify a wildcard route, use the `*` as the url: + * + * routes: { + * '*': 'onToken' + * } + * + * Since a wildcard route will execute before any other route, it can delay the execution of other routes allowing for + * such things like a user session to be retrieved: + * + * routes: { + * '*': { + * before: 'onBeforeToken' + * } + * }, + * + * onBeforeToken: function () { + * return Ext.Ajax.request({ + * url: '/user/session' + * }); + * } + * + * In the above example, no other route will execute unless that {@link Ext.Ajax#request request} returns successfully. + * + * You can also use a wildcard route if you need to defer routes until a store has been loaded when an application first starts up: + * + * routes: { + * '*': { + * before: 'onBeforeToken' + * } + * }, + * + * onBeforeToken: function (action) { + * var store = Ext.getStore('Settings'); + * + * if (store.loaded) { + * action.resume(); + * } else { + * store.on('load', action.resume, action, { single: true }); + * } + * } + */ + routes: null + }, + destroyRouterable: function() { + Ext.route.Router.disconnect(this); + }, + updateRoutes: function(routes, oldRoutes) { + var me = this, + Router = Ext.route.Router, + url, config, method; + if (oldRoutes) { + for (url in oldRoutes) { + config = oldRoutes[url]; + if (Ext.isString(config)) { + config = { + action: config, + name: url + }; + } + Router.disconnect(me, config); + } + } + if (routes) { + for (url in routes) { + config = routes[url]; + if (Ext.isString(config)) { + config = { + action: config + }; + } + method = config.action; + //connect the route config to the Router + Router.connect(url, config, me); + } + } + }, + /** + * Update the hash. By default, it will not execute the routes if the current token and the + * token passed are the same. + * + * @param {String/Number/Object/Ext.data.Model} hash The hash to redirect to. The hash can be of several + * values: + * - **String** The hash to exactly be set to. + * - **Number** If `1` is passed, {@link Ext.util.History#forward forward} function will be executed. If + * `-1` is passed, {@link Ext.util.History#bck back} function will be executed. + * - **Ext.data.Model** If a model instance is passed, the Model's {@link Ext.data.Model#toUrl toUrl} function + * will be executed to convert it into a String value to set the hash to. + * - **Object** An Object can be passed to control individual tokens in the full hash. They key should be + * an associated {@link Ext.route.Route Route}'s {@link Ext.route.Route#name name} and the value should be + * the value of that token in the complete hash. For example, if you have two routes configured, each token in the + * hash that can be matched for each route can be individually controlled: + * + * routes: { + * 'foo/bar': 'onFooBar', + * 'baz/:id': { + * action: 'onBaz', + * name: 'baz' + * } + * } + * + * If you pass in a hash of `#foo/bar|baz/1`, each route will execute in response. If you want to change only the `baz` + * route but leave the `foo/bar` route in the hash, you can pass only the `baz` key in an object: + * + * this.redirectTo({ + * baz : 'baz/5' + * }); + * + * and the resulting hash will be `#foo/bar/|baz/5` and only the `baz` route will execute in reaction but the `foo/bar` will + * not react since it's associated token in the hash remained the same. If you wanted to update the `baz` route and remove + * `foo/bar` from the hash, you can set the value to `null`: + * + * this.redirectTo({ + * 'foo/bar': null, + * baz: 'baz/3' + * }); + * + * and the resulting hash will be `#baz/3`. Like before, the `baz` route will execute in reaction. + * + * @param {Object} opt An optional `Object` describing how to enact the hash being passed in. Valid options are: + * + * - `force` Even if the hash will not change, setting this to `true` will force the {@link Ext.route.Router Router} to react. + * - `replace` When set to `true`, this will replace the current resource in the history stack with the hash being set. + * + * For backwards compatibility, if `true` is passed instead of an `Object`, this will set the `force` option to `true`. + * + * @return {Boolean} Will return `true` if the token was updated. + */ + redirectTo: function(hash, opt) { + var me = this, + currentHash = Ext.util.History.getToken(), + Router = Ext.route.Router, + delimiter = Router.getMultipleToken(), + tokens = currentHash ? currentHash.split(delimiter) : [], + length = tokens.length, + force, i, name, obj, route, token, match; + if (hash === -1) { + return Ext.util.History.back(); + } else if (hash === 1) { + return Ext.util.History.forward(); + } else if (hash.isModel) { + hash = hash.toUrl(); + } else if (Ext.isObject(hash)) { + //Passing an object attempts to replace a token in the hash. + for (name in hash) { + obj = hash[name]; + if (!Ext.isObject(obj)) { + obj = { + token: obj + }; + } + if (length) { + route = Router.getByName(name); + if (route) { + match = false; + for (i = 0; i < length; i++) { + token = tokens[i]; + if (route.matcherRegex.test(token)) { + match = true; + if (obj.token) { + //a token was found in the hash, replace it + if (obj.fn && obj.fn.call(this, token, tokens, obj) === false) { + //if the fn returned false, skip update + + continue; + } + tokens[i] = obj.token; + if (obj.force) { + //clear lastToken to force recognition + route.lastToken = null; + } + } else { + //remove token + tokens.splice(i, 1); + i--; + length--; + //reset lastToken + route.lastToken = null; + } + } + } + if (obj && obj.token && !match) { + //a token was not found in the hash, push to the end + tokens.push(obj.token); + } + } + } else if (obj && obj.token) { + //there is no current hash, push to the end + tokens.push(obj.token); + } + } + hash = tokens.join(delimiter); + } + if (opt === true) { + //for backwards compatibility + force = opt; + opt = null; + } else if (opt) { + force = opt.force; + } + length = tokens.length; + if (force && length) { + for (i = 0; i < length; i++) { + token = tokens[i]; + Router.clearLastTokens(token); + } + } + if (currentHash === hash) { + if (force) { + //hash won't change, trigger handling anyway + Router.onStateChange(hash); + } + //hash isn't going to change, return false + return false; + } + if (opt && opt.replace) { + Ext.util.History.replace(hash); + } else { + Ext.util.History.add(hash); + } + return true; + }, + privates: { + afterClassMixedIn: function(targetClass) { + var proto = targetClass.prototype, + routes = proto.routes; + if (routes) { + delete proto.routes; + targetClass.getConfigurator().add({ + routes: routes + }); + } + } + } +}); + +/** + * @protected + * @class Ext.app.BaseController + * Base class for Controllers. + * + */ +Ext.define('Ext.app.BaseController', { + requires: [ + 'Ext.app.EventBus', + 'Ext.app.domain.Global' + ], + uses: [ + 'Ext.app.domain.Controller' + ], + mixins: [ + 'Ext.mixin.Observable', + 'Ext.route.Mixin' + ], + isController: true, + config: { + /** + * @cfg {String} id The id of this controller. You can use this id when dispatching. + * + * For an example of dispatching, see the examples under the + * {@link Ext.app.Controller#cfg-listen listen} config. + * + * If an id is not explicitly set, it will default to the controller's full classname. + * + * @accessor + */ + id: undefined, + /** + * @cfg {Object} control + * @accessor + * + * Adds listeners to components selected via {@link Ext.ComponentQuery}. Accepts an + * object containing component paths mapped to a hash of listener functions. + * The function value may also be a string matching the name of a method on the + * controller. + * + * In the following example the `updateUser` function is mapped to to the `click` + * event on a button component, which is a child of the `useredit` component. + * + * Ext.define('MyApp.controller.Users', { + * extend: 'Ext.app.Controller', + * + * control: { + * 'useredit button[action=save]': { + * click: 'updateUser' + * } + * }, + * + * updateUser: function(button) { + * console.log('clicked the Save button'); + * } + * }); + * + * The method you pass to the listener will automatically be resolved on the controller. + * In this case, the `updateUser` method that will get executed on the `button` `click` + * event will resolve to the `updateUser` method on the controller, + * + * See {@link Ext.ComponentQuery} for more information on component selectors. + */ + control: null, + /** + * @cfg {Object} listen + * @accessor + * + * Adds listeners to different event sources (also called "event domains"). The + * primary event domain is that of components, but there are also other event domains: + * {@link Ext.app.domain.Global Global} domain that intercepts events fired from + * {@link Ext.GlobalEvents} Observable instance, + * {@link Ext.app.domain.Controller Controller} domain can be used to listen to events + * fired by other Controllers, {@link Ext.app.domain.Store Store} domain gives access to + * Store events, and {@link Ext.app.domain.Direct Direct} domain can be used with + * Ext Direct Providers to listen to their events. + * + * To listen to "bar" events fired by a controller with id="foo": + * + * Ext.define('AM.controller.Users', { + * extend: 'Ext.app.Controller', + * + * listen: { + * controller: { + * '#foo': { + * bar: 'onFooBar' + * } + * } + * } + * }); + * + * To listen to "bar" events fired by any controller, and "baz" events + * fired by Store with storeId="baz": + * + * Ext.define('AM.controller.Users', { + * extend: 'Ext.app.Controller', + * + * listen: { + * controller: { + * '*': { + * bar: 'onAnyControllerBar' + * } + * }, + * store: { + * '#baz': { + * baz: 'onStoreBaz' + * } + * } + * } + * }); + * + * To listen to "idle" events fired by {@link Ext.GlobalEvents} when other event + * processing is complete and Ext JS is about to return control to the browser: + * + * Ext.define('AM.controller.Users', { + * extend: 'Ext.app.Controller', + * + * listen: { + * global: { // Global events are always fired + * idle: 'onIdle' // from the same object, so there + * } // are no selectors + * } + * }); + * + * As this relates to components, the following example: + * + * Ext.define('AM.controller.Users', { + * extend: 'Ext.app.Controller', + * + * listen: { + * component: { + * 'useredit button[action=save]': { + * click: 'updateUser' + * } + * } + * } + * }); + * + * Is equivalent to: + * + * Ext.define('AM.controller.Users', { + * extend: 'Ext.app.Controller', + * + * control: { + * 'useredit button[action=save]': { + * click: 'updateUser' + * } + * } + * }); + * + * Of course, these can all be combined in a single call and used instead of + * `control`, like so: + * + * Ext.define('AM.controller.Users', { + * extend: 'Ext.app.Controller', + * + * listen: { + * global: { + * idle: 'onIdle' + * }, + * controller: { + * '*': { + * foobar: 'onAnyFooBar' + * }, + * '#foo': { + * bar: 'onFooBar' + * } + * }, + * component: { + * 'useredit button[action=save]': { + * click: 'updateUser' + * } + * }, + * store: { + * '#qux': { + * load: 'onQuxLoad' + * } + * } + * } + * }); + */ + listen: null + }, + /** + * Creates new Controller. + * + * @param {Object} [config] Configuration object. + */ + constructor: function(config) { + var me = this; + // In versions prior to 5.1, this constructor used to call the Ext.util.Observable + // constructor (which applied the config properties directly to the instance) + // AND it used to call initConfig as well. Since the constructor of + // Ext.mixin.Observable calls initConfig, but does not apply the properties to + // the instance, we do that here for backward compatibility. + Ext.apply(me, config); + // The control and listen properties are also methods so we need to delete them + // from the instance after applying the config object. + delete me.control; + delete me.listen; + me.eventbus = Ext.app.EventBus; + //need to have eventbus property set before we initialize the config + me.mixins.observable.constructor.call(me, config); + }, + updateId: function(id) { + this.id = id; + }, + applyListen: function(listen) { + if (Ext.isObject(listen)) { + listen = Ext.clone(listen); + } + return listen; + }, + applyControl: function(control) { + if (Ext.isObject(control)) { + control = Ext.clone(control); + } + return control; + }, + /** + * @param {Object} control The object to pass to the {@link #method-control} method + * @private + */ + updateControl: function(control) { + this.getId(); + if (control) { + this.control(control); + } + }, + /** + * @param {Object} listen The object to pass to the {@link #method-listen} method + * @private + */ + updateListen: function(listen) { + this.getId(); + if (listen) { + this.listen(listen); + } + }, + isActive: function() { + return true; + }, + /** + * Adds listeners to components selected via {@link Ext.ComponentQuery}. Accepts an + * object containing component paths mapped to a hash of listener functions. + * + * In the following example the `updateUser` function is mapped to to the `click` + * event on a button component, which is a child of the `useredit` component. + * + * Ext.define('AM.controller.Users', { + * init: function() { + * this.control({ + * 'useredit button[action=save]': { + * click: this.updateUser + * } + * }); + * }, + * + * updateUser: function(button) { + * console.log('clicked the Save button'); + * } + * }); + * + * Or alternatively one call `control` with two arguments: + * + * this.control('useredit button[action=save]', { + * click: this.updateUser + * }); + * + * See {@link Ext.ComponentQuery} for more information on component selectors. + * + * @param {String/Object} selectors If a String, the second argument is used as the + * listeners, otherwise an object of selectors -> listeners is assumed + * @param {Object} [listeners] Config for listeners. + * @param {Ext.app.BaseController} [controller] (private) + */ + control: function(selectors, listeners, controller) { + var me = this, + ctrl = controller, + obj; + if (Ext.isString(selectors)) { + obj = {}; + obj[selectors] = listeners; + } else { + obj = selectors; + ctrl = listeners; + } + me.eventbus.control(obj, ctrl || me); + }, + /** + * Adds listeners to different event sources (also called "event domains"). The + * primary event domain is that of components, but there are also other event domains: + * {@link Ext.app.domain.Global Global} domain that intercepts events fired from + * {@link Ext.GlobalEvents} Observable instance, {@link Ext.app.domain.Controller Controller} + * domain can be used to listen to events fired by other Controllers, + * {@link Ext.app.domain.Store Store} domain gives access to Store events, and + * {@link Ext.app.domain.Direct Direct} domain can be used with Ext Direct Providers + * to listen to their events. + * + * To listen to "bar" events fired by a controller with id="foo": + * + * Ext.define('AM.controller.Users', { + * init: function() { + * this.listen({ + * controller: { + * '#foo': { + * bar: this.onFooBar + * } + * } + * }); + * }, + * ... + * }); + * + * To listen to "bar" events fired by any controller, and "baz" events + * fired by Store with storeId="baz": + * + * Ext.define('AM.controller.Users', { + * init: function() { + * this.listen({ + * controller: { + * '*': { + * bar: this.onAnyControllerBar + * } + * }, + * store: { + * '#baz': { + * baz: this.onStoreBaz + * } + * } + * }); + * }, + * ... + * }); + * + * To listen to "idle" events fired by {@link Ext.GlobalEvents} when other event + * processing is complete and Ext JS is about to return control to the browser: + * + * Ext.define('AM.controller.Users', { + * init: function() { + * this.listen({ + * global: { // Global events are always fired + * idle: this.onIdle // from the same object, so there + * } // are no selectors + * }); + * } + * }); + * + * As this relates to components, the following example: + * + * Ext.define('AM.controller.Users', { + * init: function() { + * this.listen({ + * component: { + * 'useredit button[action=save]': { + * click: this.updateUser + * } + * } + * }); + * }, + * ... + * }); + * + * Is equivalent to: + * + * Ext.define('AM.controller.Users', { + * init: function() { + * this.control({ + * 'useredit button[action=save]': { + * click: this.updateUser + * } + * }); + * }, + * ... + * }); + * + * Of course, these can all be combined in a single call and used instead of + * `control`, like so: + * + * Ext.define('AM.controller.Users', { + * init: function() { + * this.listen({ + * global: { + * idle: this.onIdle + * }, + * controller: { + * '*': { + * foobar: this.onAnyFooBar + * }, + * '#foo': { + * bar: this.onFooBar + * } + * }, + * component: { + * 'useredit button[action=save]': { + * click: this.updateUser + * } + * }, + * store: { + * '#qux': { + * load: this.onQuxLoad + * } + * } + * }); + * }, + * ... + * }); + * + * @param {Object} to Config object containing domains, selectors and listeners. + * @param {Ext.app.Controller} [controller] The controller to add the listeners to. Defaults to the current controller. + */ + listen: function(to, controller) { + this.eventbus.listen(to, controller || this); + }, + destroy: function() { + var me = this, + bus = me.eventbus; + if (bus) { + bus.unlisten(me); + me.eventbus = null; + } + me.callParent(); + } +}); + +/** + * @private + * @class Ext.app.Util + */ +Ext.define('Ext.app.Util', {}, function() { + Ext.apply(Ext.app, { + namespaces: { + Ext: {} + }, + /** + * Adds namespace(s) to known list. + * @private + * + * @param {String/String[]} namespace + */ + addNamespaces: function(namespace) { + var namespaces = Ext.app.namespaces, + i, l; + if (!Ext.isArray(namespace)) { + namespace = [ + namespace + ]; + } + for (i = 0 , l = namespace.length; i < l; i++) { + namespaces[namespace[i]] = true; + } + }, + /** + * Clear all namespaces from known list. + * @private + */ + clearNamespaces: function() { + Ext.app.namespaces = {}; + }, + /** + * Get namespace prefix for a class name. + * @private + * @param {String} className + * + * @return {String} Namespace prefix if it's known, otherwise undefined + */ + getNamespace: function(className) { + var namespaces = Ext.apply({}, Ext.ClassManager.paths, Ext.app.namespaces), + deepestPrefix = '', + prefix; + for (prefix in namespaces) { + if (namespaces.hasOwnProperty(prefix) && prefix.length > deepestPrefix.length && (prefix + '.' === className.substring(0, prefix.length + 1))) { + deepestPrefix = prefix; + } + } + return deepestPrefix === '' ? undefined : deepestPrefix; + }, + /** + * Sets up paths based on the `appFolder` and `paths` configs. + * @param {String} appName The application name (root namespace). + * @param {String} appFolder The folder for app sources ("app" by default). + * @param {Object} paths A set of namespace to path mappings. + * @private + * @since 6.0.0 + */ + setupPaths: function(appName, appFolder, paths) { + var manifestPaths = Ext.manifest, + ns; + // Ignore appFolder:null + if (appName && appFolder !== null) { + manifestPaths = manifestPaths && manifestPaths.paths; + // If the manifest has paths, only honor appFolder if defined. If the + // manifest has no paths (old school mode), then we want to default an + // unspecified appFolder value to "app". Sencha Cmd will pass in paths + // to configure the loader via the "paths" property of the manifest so + // we don't want to try and be "helpful" in that case. + if (!manifestPaths || appFolder !== undefined) { + Ext.Loader.setPath(appName, (appFolder === undefined) ? 'app' : appFolder); + } + } + if (paths) { + for (ns in paths) { + if (paths.hasOwnProperty(ns)) { + Ext.Loader.setPath(ns, paths[ns]); + } + } + } + } + }); + /** + * @method getNamespace + * @member Ext + * @param {String} className + * + * @return {String} Namespace prefix if it's known, otherwise undefined + */ + Ext.getNamespace = Ext.app.getNamespace; +}); + +/** + * Maintains an additional key map for an `Ext.util.Collection`. Instances of this class + * are seldom created manually. Rather they are created by the `Ext.util.Collection' when + * given an `extraKeys` config. + * + * @since 5.0.0 + */ +Ext.define('Ext.util.CollectionKey', { + mixins: [ + 'Ext.mixin.Identifiable' + ], + isCollectionKey: true, + observerPriority: -200, + config: { + collection: null, + /** + * @cfg {Function/String} [keyFn] + * A function to retrieve the key of an item in the collection. This can be normal + * function that takes an item and returns the key or it can be the name of the + * method to call on an item to get the key. + * + * For example: + * + * new Ext.util.Collection({ + * keys: { + * byName: { + * keyFn: 'getName' // each item has a "getName" method + * } + * } + * }); + * + * Or equivalently: + * + * new Ext.util.Collection({ + * keys: { + * byName: { + * keyFn: function (item) { + * return item.getName(); + * } + * } + * } + * }); + * + * @since 5.0.0 + */ + keyFn: null, + /** + * @cfg {String} property + * The name of the property on each item that is its key. + * + * new Ext.util.Collection({ + * keys: { + * byName: 'name' + * } + * }); + * + * Or equivalently: + * + * new Ext.util.Collection({ + * keys: { + * byName: { + * property: 'name' + * } + * } + * }); + * + * var item = collection.byName.get('fooname'); + */ + property: null, + /** + * @cfg {String} rootProperty + * The name of the sub-object property on each item that is its key. This value + * overrides `{@link Ext.util.Collection#rootProperty}`. + * + * new Ext.util.Collection({ + * keys: { + * byName: { + * property: 'name', + * rootProperty: 'data' + * } + * } + * }); + * + * var item = collection.byName.get('fooname'); + */ + rootProperty: null, + unique: true + }, + /** + * This property is used to know when this `Index` is in sync with the `Collection`. + * When the two are synchronized, their `generation` values match. + * @private + * @readonly + * @since 5.0.0 + */ + generation: 0, + /** + * @property {Object} map + * An object used as map to get an object based on its key. + * @since 5.0.0 + * @private + */ + map: null, + /** + * @property {Number} mapRebuilds + * The number of times the `map` has been rebuilt. This is for diagnostic use. + * @private + * @readonly + */ + mapRebuilds: 0, + /** + * @property {String} name + * This property is set by `Ext.util.Collection` when added via `extraKeys`. + * @readonly + */ + constructor: function(config) { + this.initConfig(config); + if (!Ext.isFunction(this.getKey)) { + Ext.raise('CollectionKey requires a keyFn or property config'); + } + }, + /** + * Returns the item or, if not `unique` possibly array of items that have the given + * key. + * @param {Mixed} key The key that will match the `keyFn` return value or value of + * the specified `property`. + * @return {Object} + */ + get: function(key) { + var map = this.map || this.getMap(); + return map[key] || null; + }, + /** + * @private + * Clears this index; + * + * Called by {@link Ext.util.Collection#clear} when the collection is cleared. + */ + clear: function() { + this.map = null; + }, + getRootProperty: function() { + var me = this, + root = this.callParent(); + return root !== null ? root : me.getCollection().getRootProperty(); + }, + /** + * Returns the index of the item with the given key in the collection. If this is not + * a `unique` result, the index of the first item in the collection with the matching + * key. + * + * To iterate the indices of all items with a matching (not `unique`) key: + * + * for (index = collection.byName.indexOf('foo'); + * index >= 0; + * index = collection.byName.indexOf('foo', index)) { + * // process item at "index" + * } + * + * @param {Mixed} key The key that will match the `keyFn` return value or value of + * the specified `property`. + * @param {Number} [startAt=-1] The index at which to start. Only occurrences beyond + * this index are returned. + * @return {Number} The index of the first item with the given `key` beyond the given + * `startAt` index or -1 if there are no such items. + */ + indexOf: function(key, startAt) { + var map = this.map || this.getMap(), + item = map[key], + collection = this.getCollection(), + length = collection.length, + i, index, items, n; + if (!item) { + return -1; + } + if (startAt === undefined) { + startAt = -1; + } + if (item instanceof Array) { + items = item; + index = length; + // greater than any actual indexOf + for (n = items.length; n-- > 0; ) { + i = collection.indexOf(items[n]); + if (i < index && i > startAt) { + index = i; + } + } + if (index === length) { + return -1; + } + } else { + index = collection.indexOf(item); + } + return (index > startAt) ? index : -1; + }, + /** + * Change the key for an existing item in the collection. If the old key does not + * exist this call does nothing. + * @param {Object} item The item whose key has changed. + * @param {String} oldKey The old key for the `item`. + * @since 5.0.0 + */ + updateKey: function(item, oldKey) { + var me = this, + map = me.map, + bucket, index; + if (map) { + bucket = map[oldKey]; + if (bucket instanceof Array) { + index = Ext.Array.indexOf(bucket, item); + if (index >= 0) { + if (bucket.length > 2) { + bucket.splice(index, 1); + } else { + // If there is an array of 2 items, replace the array with the + // one remaining item. Since index then is either 0 or 1, the + // index of the other item is easy. + map[oldKey] = bucket[1 - index]; + } + } + } + // "1 - 0" = 1, "1 - 1" = 0 + else if (bucket) { + if (me.getUnique() && bucket !== item) { + Ext.raise('Incorrect oldKey "' + oldKey + '" for item with newKey "' + me.getKey(item) + '"'); + } + delete map[oldKey]; + } + me.add([ + item + ]); + } + }, + //------------------------------------------------------------------------- + // Calls from our Collection: + onCollectionAdd: function(collection, add) { + if (this.map) { + this.add(add.items); + } + }, + onCollectionItemChange: function(collection, details) { + this.map = null; + }, + onCollectionRefresh: function() { + this.map = null; + }, + onCollectionRemove: function(collection, remove) { + var me = this, + map = me.map, + items = remove.items, + length = items.length, + i, item, key; + if (map) { + if (me.getUnique() && length < collection.length / 2) { + for (i = 0; i < length; ++i) { + key = me.getKey(item = items[i]); + delete map[key]; + } + } else { + me.map = null; + } + } + }, + //------------------------------------------------------------------------- + // Private + add: function(items) { + var me = this, + map = me.map, + bucket, i, item, key, length, unique; + length = items.length; + unique = me.getUnique(); + for (i = 0; i < length; ++i) { + key = me.getKey(item = items[i]); + if (unique || !(key in map)) { + map[key] = item; + } else { + if (!((bucket = map[key]) instanceof Array)) { + map[key] = bucket = [ + bucket + ]; + } + bucket.push(item); + } + } + }, + applyKeyFn: function(keyFn) { + if (Ext.isString(keyFn)) { + this.getKey = function(item) { + return item[keyFn](); + }; + } else { + this.getKey = keyFn; + } + }, + updateProperty: function(property) { + var root = this.getRootProperty(); + this.getKey = function(item) { + return (root ? item[root] : item)[property]; + }; + }, + getMap: function() { + var me = this, + map = me.map; + if (!map) { + me.map = map = {}; + me.keysByItemKey = {}; + ++me.mapRebuilds; + me.add(me.getCollection().items); + } + return map; + }, + updateCollection: function(collection, oldCollection) { + if (collection) { + collection.addObserver(this); + } + if (oldCollection) { + oldCollection.removeObserver(this); + } + }, + clone: function() { + return new Ext.util.CollectionKey(this.getCurrentConfig()); + }, + destroy: function() { + this.clear(); + this.getCollection().removeObserver(this); + this.destroyed = true; + } +}); + +/** + * Represents a grouping of items. The grouper works in a similar fashion as the + * `Ext.util.Sorter` except that groups must be able to extract a value by which all items + * in the group can be collected. By default this is derived from the `property` config + * but can be customized using the `groupFn` if necessary. + * + * All items with the same group value compare as equal. If the group values do not compare + * equally, the sort can be controlled further by setting `sortProperty` or `sorterFn`. + */ +Ext.define('Ext.util.Grouper', { + extend: 'Ext.util.Sorter', + isGrouper: true, + config: { + /** + * @cfg {Function} groupFn This function is called for each item in the collection + * to determine the group to which it belongs. By default the `property` value is + * used to group items. + * @cfg {Object} groupFn.item The current item from the collection. + * @cfg {String} groupFn.return The group identifier for the item. + */ + groupFn: null, + /** + * @cfg {String} property The field by which records are grouped. Groups are + * sorted alphabetically by group value as the default. To sort groups by a different + * property, use the {@link #sortProperty} configuration. + */ + /** + * @cfg {String} sortProperty You can set this configuration if you want the groups + * to be sorted on something other then the group string returned by the `groupFn`. + * This serves the same role as `property` on a normal `Ext.util.Sorter`. + */ + sortProperty: null + }, + constructor: function(config) { + if (config) { + if (config.getGroupString) { + Ext.raise("Cannot set getGroupString - use groupFn instead"); + } + } + this.callParent(arguments); + }, + /** + * Returns the value for grouping to be used. + * @param {Ext.data.Model} item The Model instance + * @return {String} + */ + getGroupString: function(item) { + var group = this._groupFn(item); + return (group != null) ? String(group) : ''; + }, + sortFn: function(item1, item2) { + var me = this, + lhs = me._groupFn(item1), + rhs = me._groupFn(item2), + property = me._sortProperty, + // Sorter's sortFn uses "_property" + root = me._root, + sorterFn = me._sorterFn, + transform = me._transform; + // Items with the same groupFn result must be equal... otherwise we sort them + // by sorterFn or sortProperty. + if (lhs === rhs) { + return 0; + } + if (property || sorterFn) { + if (sorterFn) { + return sorterFn.call(this, item1, item2); + } + if (root) { + item1 = item1[root]; + item2 = item2[root]; + } + lhs = item1[property]; + rhs = item2[property]; + if (transform) { + lhs = transform(lhs); + rhs = transform(rhs); + } + } + return (lhs > rhs) ? 1 : (lhs < rhs ? -1 : 0); + }, + standardGroupFn: function(item) { + var root = this._root; + return (root ? item[root] : item)[this._property]; + }, + updateSorterFn: function() {}, + // don't callParent here - we don't want to smash sortFn w/sorterFn + updateProperty: function() { + // we don't callParent since that is related to sorterFn smashing sortFn + if (!this.getGroupFn()) { + this.setGroupFn(this.standardGroupFn); + } + } +}); + +/** + * This class manages uniquely keyed objects such as {@link Ext.data.Model records} or + * {@link Ext.Component components}. + * + * ## Keys + * + * Unlike `Ext.util.MixedCollection` this class can only manage objects whose key can be + * extracted from the instance. That is, this class does not support "external" keys. This + * makes this class more efficient because it does not need to track keys in parallel with + * items. It also means key-to-item lookup will be optimal and never need to perform a + * linear search. + * + * ### Extra Keys + * + * In some cases items may need to be looked up by multiple property values. To enable this + * there is the `extraKeys` config. + * + * For example, to quickly look up items by their "name" property: + * + * var collection = new Ext.util.Collection({ + * extraKeys: { + * byName: 'name' // based on "name" property of each item + * } + * }); + * + * ## Ranges + * + * When methods accept index arguments to indicate a range of items, these are either an + * index and a number of items or a "begin" and "end" index. + * + * In the case of "begin" and "end", the "end" is the first item outside the range. This + * definition makes it simple to expression empty ranges because "length = end - begin". + * + * ### Negative Indices + * + * When an item index is provided, negative values are treated as offsets from the end of + * the collection. In other words the follow are equivalent: + * + * +---+---+---+---+---+---+ + * | | | | | | | + * +---+---+---+---+---+---+ + * 0 1 2 3 4 5 + * -6 -5 -4 -3 -2 -1 + * + * ## Legacy Classes + * + * The legacy classes `Ext.util.MixedCollection' and `Ext.util.AbstractMixedCollection` + * may be needed if external keys are required, but for all other situations this class + * should be used instead. + */ +Ext.define('Ext.util.Collection', { + mixins: [ + 'Ext.mixin.Observable' + ], + requires: [ + 'Ext.util.CollectionKey', + 'Ext.util.Filter', + 'Ext.util.Sorter', + 'Ext.util.Grouper' + ], + uses: [ + 'Ext.util.SorterCollection', + 'Ext.util.FilterCollection', + 'Ext.util.GroupCollection' + ], + /** + * @property {Boolean} isCollection + * `true` in this class to identify an object as an instantiated Collection, or subclass + * thereof. + * @readonly + */ + isCollection: true, + config: { + autoFilter: true, + /** + * @cfg {Boolean} [autoSort=true] `true` to maintain sorted order when items + * are added regardless of requested insertion point, or when an item mutation + * results in a new sort position. + * + * This does not affect a filtered Collection's reaction to mutations of the source + * Collection. If sorters are present when the source Collection is mutated, this Collection's + * sort order will always be maintained. + * @private + */ + autoSort: true, + /** + * @cfg {Boolean} [autoGroup=true] `true` to sort by the grouper + * @private + */ + autoGroup: true, + /** + * @cfg {Function} decoder + * A function that can convert newly added items to a proper type before being + * added to this collection. + */ + decoder: null, + /** + * @cfg {Object} extraKeys + * One or more `Ext.util.CollectionKey` configuration objects or key properties. + * Each property of the given object is the name of the `CollectionKey` instance + * that is stored on this collection. The value of each property configures the + * `CollectionKey` instance. + * + * var collection = new Ext.util.Collection({ + * extraKeys: { + * byName: 'name' // based on "name" property of each item + * } + * }); + * + * Or equivalently: + * + * var collection = new Ext.util.Collection({ + * extraKeys: { + * byName: { + * property: 'name' + * } + * } + * }); + * + * To provide a custom key extraction function instead: + * + * var collection = new Ext.util.Collection({ + * extraKeys: { + * byName: { + * keyFn: function (item) { + * return item.name; + * } + * } + * } + * }); + * + * Or to call a key getter method from each item: + * + * var collection = new Ext.util.Collection({ + * extraKeys: { + * byName: { + * keyFn: 'getName' + * } + * } + * }); + * + * To use the above: + * + * var item = collection.byName.get('somename'); + * + * **NOTE** Either a `property` or `keyFn` must be be specified to define each + * key. + * @since 5.0.0 + */ + extraKeys: null, + /** + * @cfg {Array/Ext.util.FilterCollection} filters + * The collection of {@link Ext.util.Filter Filters} for this collection. At the + * time a collection is created `filters` can be specified as a unit. After that + * time the normal `setFilters` method can also be given a set of replacement + * filters for the collection. + * + * Individual filters can be specified as an `Ext.util.Filter` instance, a config + * object for `Ext.util.Filter` or simply a function that will be wrapped in a + * instance with its {@link Ext.util.Filter#filterFn filterFn} set. + * + * For fine grain control of the filters collection, call `getFilters` to return + * the `Ext.util.Collection` instance that holds this collection's filters. + * + * var collection = new Ext.util.Collection(); + * var filters = collection.getFilters(); // an Ext.util.FilterCollection + * + * function legalAge (item) { + * return item.age >= 21; + * } + * + * filters.add(legalAge); + * + * //... + * + * filters.remove(legalAge); + * + * Any changes to the `filters` collection will cause this collection to adjust + * its items accordingly (if `autoFilter` is `true`). + * @since 5.0.0 + */ + filters: null, + /** + * @cfg {Object} grouper + * A configuration object for this collection's {@link Ext.util.Grouper grouper}. + * + * For example, to group items by the first letter of the last name: + * + * var collection = new Ext.util.Collection({ + * grouper: { + * groupFn: function (item) { + * return item.lastName.substring(0, 1); + * } + * } + * }); + */ + grouper: null, + /** + * @cfg {Ext.util.GroupCollection} groups + * The collection of to hold each group container. This collection is created and + * removed dynamically based on `grouper`. Application code should only need to + * call `getGroups` to retrieve the collection and not `setGroups`. + */ + groups: null, + /** + * @cfg {Object} groupConfig + * A default configuration to be passed to any groups created by the + * {@link Ext.util.GroupCollection}. See {@link #groups}. + * + * @private + * @since 6.5.0 + */ + groupConfig: null, + /** + * @cfg {String} rootProperty + * The root property to use for aggregation, filtering and sorting. By default + * this is `null` but when containing things like {@link Ext.data.Model records} + * this config would likely be set to "data" so that property names are applied + * to the fields of each record. + */ + rootProperty: null, + /** + * @cfg {Array/Ext.util.SorterCollection} sorters + * Array of {@link Ext.util.Sorter sorters} for this collection. At the time a + * collection is created the `sorters` can be specified as a unit. After that time + * the normal `setSorters` method can be also be given a set of replacement + * sorters. + * + * Individual sorters can be specified as an `Ext.util.Sorter` instance, a config + * object for `Ext.util.Sorter` or simply the name of a property by which to sort. + * + * An alternative way to extend the sorters is to call the `sort` method and pass + * a property or sorter config to add to the sorters. + * + * For fine grain control of the sorters collection, call `getSorters` to return + * the `Ext.util.Collection` instance that holds this collection's sorters. + * + * var collection = new Ext.util.Collection(); + * var sorters = collection.getSorters(); // an Ext.util.SorterCollection + * + * sorters.add('name'); + * + * //... + * + * sorters.remove('name'); + * + * Any changes to the `sorters` collection will cause this collection to adjust + * its items accordingly (if `autoSort` is `true`). + * + * @since 5.0.0 + */ + sorters: null, + /** + * @cfg {Number} [multiSortLimit=3] + * The maximum number of sorters which may be applied to this Sortable when using + * the "multi" insertion position when adding sorters. + * + * New sorters added using the "multi" insertion position are inserted at the top + * of the sorters list becoming the new primary sort key. + * + * If the sorters collection has grown to longer then **`multiSortLimit`**, then + * the it is trimmed. + */ + multiSortLimit: 3, + /** + * @cfg {String} defaultSortDirection + * The default sort direction to use if one is not specified. + */ + defaultSortDirection: 'ASC', + /** + * @cfg {Ext.util.Collection} source + * The base `Collection`. This collection contains the items to which filters + * are applied to populate this collection. In this configuration, only the + * root `source` collection can have items truly added or removed. + * @since 5.0.0 + */ + source: null, + /** + * @cfg {Boolean} trackGroups + * `true` to track individual groups in a Ext.util.GroupCollection + * @private + */ + trackGroups: true + }, + /** + * @property {Number} generation + * Mutation counter which is incremented when the collection changes. + * @readonly + * @since 5.0.0 + */ + generation: 0, + /** + * @property {Object} indices + * An object used as map to get the index of an item. + * @private + * @since 5.0.0 + */ + indices: null, + /** + * @property {Number} indexRebuilds + * The number of times the `indices` have been rebuilt. This is for diagnostic use. + * @private + * @readonly + * @since 5.0.0 + */ + indexRebuilds: 0, + /** + * @property {Number} updating + * A counter that is increased by `beginUpdate` and decreased by `endUpdate`. When + * this transitions from 0 to 1 the `{@link #event-beginupdate beginupdate}` event is + * fired. When it transitions back from 1 to 0 the `{@link #event-endupdate endupdate}` + * event is fired. + * @readonly + * @since 5.0.0 + */ + updating: 0, + /** + * @property {Boolean} grouped + * A read-only flag indicating if this object is grouped. + * @readonly + */ + grouped: false, + /** + * @property {Boolean} sorted + * A read-only flag indicating if this object is sorted. This flag may not be correct + * during an update of the sorter collection but will be correct before `onSortChange` + * is called. This flag is `true` if `grouped` is `true` because the collection is at + * least sorted by the `grouper`. + * @readonly + */ + sorted: false, + /** + * @property {Boolean} filtered + * A read-only flag indicating if this object is filtered. + * @readonly + */ + filtered: false, + /** + * @private + * Priority that is used for endupdate listeners on the filters and sorters. + * set to a very high priority so that our processing of these events takes place prior + * to user code - data must already be filtered/sorted when the user's handler runs + */ + $endUpdatePriority: 1001, + /** + * @private + * `true` to destroy the sorter collection on destroy. + */ + manageSorters: true, + /** + * @event add + * Fires after items have been added to the collection. + * + * All `{@link #event-add add}` and `{@link #event-remove remove}` events occur between + * `{@link #event-beginupdate beginupdate}` and `{@link #event-endupdate endupdate}` + * events so it is best to do only the minimal amount of work in response to these + * events and move the more expensive side-effects to an `endupdate` listener. + * + * @param {Ext.util.Collection} collection The collection being modified. + * + * @param {Object} details An object describing the addition. + * + * @param {Number} details.at The index in the collection where the add occurred. + * + * @param {Object} details.atItem The item after which the new items were inserted or + * `null` if at the beginning of the collection. + * + * @param {Object[]} details.items The items that are now added to the collection. + * + * @param {Array} [details.keys] If available this array holds the keys (extracted by + * `getKey`) for each item in the `items` array. + * + * @param {Object} [details.next] If more `{@link #event-add add}` events are in queue + * to be delivered this is a reference to the `details` instance for the next + * `{@link #event-add add}` event. This will only be the case when the collection is + * sorted as the new items often need to be inserted at multiple locations to maintain + * the sort. In this case, all of the new items have already been added not just those + * described by the first `{@link #event-add add}` event. + * + * @param {Object} [details.replaced] If this addition has a corresponding set of + * `{@link #event-remove remove}` events this reference holds the `details` object for + * the first `remove` event. That `details` object may have a `next` property if there + * are multiple associated `remove` events. + * + * @since 5.0.0 + */ + /** + * @event beginupdate + * Fired before changes are made to the collection. This event fires when the + * `beginUpdate` method is called and the counter it manages transitions from 0 to 1. + * + * All `{@link #event-add add}` and `{@link #event-remove remove}` events occur between + * `{@link #event-beginupdate beginupdate}` and `{@link #event-endupdate endupdate}` + * events so it is best to do only the minimal amount of work in response to these + * events and move the more expensive side-effects to an `endupdate` listener. + * + * @param {Ext.util.Collection} collection The collection being modified. + * + * @since 5.0.0 + */ + /** + * @event endupdate + * Fired after changes are made to the collection. This event fires when the `endUpdate` + * method is called and the counter it manages transitions from 1 to 0. + * + * All `{@link #event-add add}` and `{@link #event-remove remove}` events occur between + * `{@link #event-beginupdate beginupdate}` and `{@link #event-endupdate endupdate}` + * events so it is best to do only the minimal amount of work in response to these + * events and move the more expensive side-effects to an `endupdate` listener. + * + * @param {Ext.util.Collection} collection The collection being modified. + * + * @since 5.0.0 + */ + /** + * @event beforeitemchange + * This event fires before an item change is reflected in the collection. This event + * is always followed by an `itemchange` event and, depending on the change, possibly + * an `add`, `remove` and/or `updatekey` event. + * + * @param {Ext.util.Collection} collection The collection being modified. + * + * @param {Object} details An object describing the change. + * + * @param {Object} details.item The item that has changed. + * + * @param {String} details.key The key of the item that has changed. + * + * @param {Boolean} details.filterChanged This is `true` if the filter status of the + * `item` has changed. That is, the item was previously filtered out and is no longer + * or the opposite. + * + * @param {Ext.util.Group} details.group The group containing the `item`. **(since 6.5.1)** + * + * @param {Boolean} details.groupChanged This is `true` if the item is moving between + * groups. See also the `group` and `oldGroup` properties. **(since 6.5.1)** + * + * @param {Boolean} details.keyChanged This is `true` if the item has changed keys. If + * so, check `oldKey` for the old key. An `updatekey` event will follow. + * + * @param {Boolean} details.indexChanged This is `true` if the item needs to move to + * a new index in the collection due to sorting. The index can be seen in `index`. + * The old index is in `oldIndex`. + * + * @param {String[]} [details.modified] If known this property holds the array of names + * of the modified properties of the item. + * + * @param {Boolean} [details.filtered] This value is `true` if the item will be filtered + * out of the collection. + * + * @param {Number} [details.index] The new index in the collection for the item if + * the item is being moved (see `indexChanged`). If the item is being removed due to + * filtering, this will be -1. + * + * @param {Ext.util.Group} details.oldGroup The group that previously contained the + * `item`. **(since 6.5.1)** + * + * @param {Number} [details.oldIndex] The old index in the collection for the item if + * the item is being moved (see `indexChanged`). If the item was being removed due to + * filtering, this will be -1. + * + * @param {Object} [details.oldKey] The old key for the `item` if the item's key has + * changed (see `keyChanged`). + * + * @param {Boolean} [details.wasFiltered] This value is `true` if the item was filtered + * out of the collection. + * + * @since 5.0.0 + */ + /** + * @event itemchange + * This event fires after an item change is reflected in the collection. This event + * always follows a `beforeitemchange` event and its corresponding `add`, `remove` + * and/or `updatekey` events. + * + * @param {Ext.util.Collection} collection The collection being modified. + * + * @param {Object} details An object describing the change. + * + * @param {Object} details.item The item that has changed. + * + * @param {String} details.key The key of the item that has changed. + * + * @param {Boolean} details.filterChanged This is `true` if the filter status of the + * `item` has changed. That is, the item was previously filtered out and is no longer + * or the opposite. + * + * @param {Ext.util.Group} details.group The group containing the `item`. **(since 6.5.1)** + * + * @param {Boolean} details.groupChanged This is `true` if the item is moving between + * groups. See also the `group` and `oldGroup` properties. **(since 6.5.1)** + * + * @param {Object} details.keyChanged This is `true` if the item has changed keys. If + * so, check `oldKey` for the old key. An `updatekey` event will have been sent. + * + * @param {Boolean} details.indexChanged This is `true` if the item was moved to a + * new index in the collection due to sorting. The index can be seen in `index`. + * The old index is in `oldIndex`. + * + * @param {String[]} [details.modified] If known this property holds the array of names + * of the modified properties of the item. + * + * @param {Boolean} [details.filtered] This value is `true` if the item is filtered + * out of the collection. + * + * @param {Number} [details.index] The new index in the collection for the item if + * the item has been moved (see `indexChanged`). If the item is removed due to + * filtering, this will be -1. + * + * @param {Ext.util.Group} details.oldGroup The group that previously contained the + * `item`. **(since 6.5.1)** + * + * @param {Number} [details.oldIndex] The old index in the collection for the item if + * the item has been moved (see `indexChanged`). If the item was being removed due to + * filtering, this will be -1. + * + * @param {Object} [details.oldKey] The old key for the `item` if the item's key has + * changed (see `keyChanged`). + * + * @param {Boolean} [details.wasFiltered] This value is `true` if the item was filtered + * out of the collection. + * + * @since 5.0.0 + */ + /** + * @event refresh + * This event fires when the collection has changed entirely. This event is fired in + * cases where the collection's filter is updated or the items are sorted. While the + * items previously in the collection may remain the same, the order at a minimum has + * changed in ways that cannot be simply translated to other events. + * + * @param {Ext.util.Collection} collection The collection being modified. + */ + /** + * @event remove + * Fires after items have been removed from the collection. Some properties of this + * object may not be present if calculating them is deemed too expensive. These are + * marked as "optional". + * + * All `{@link #event-add add}` and `{@link #event-remove remove}` events occur between + * `{@link #event-beginupdate beginupdate}` and `{@link #event-endupdate endupdate}` + * events so it is best to do only the minimal amount of work in response to these + * events and move the more expensive side-effects to an `endupdate` listener. + * + * @param {Ext.util.Collection} collection The collection being modified. + * + * @param {Object} details An object describing the removal. + * + * @param {Number} details.at The index in the collection where the removal occurred. + * + * @param {Object[]} details.items The items that are now removed from the collection. + * + * @param {Array} [details.keys] If available this array holds the keys (extracted by + * `getKey`) for each item in the `items` array. + * + * @param {Object} [details.map] If available this is a map keyed by the key of each + * item in the `items` array. This will often contain all of the items being removed + * and not just the items in the range described by this event. The value held in this + * map is the item. + * + * @param {Object} [details.next] If more `{@link #event-remove remove}` events are in + * queue to be delivered this is a reference to the `details` instance for the next + * remove event. + * + * @param {Object} [details.replacement] If this removal has a corresponding + * `{@link #event-add add}` taking place this reference holds the `details` object for + * that `add` event. If the collection is sorted, the new items are pre-sorted but the + * `at` property for the `replacement` will **not** be correct. The new items will be + * added in one or more chunks at their proper index. + * + * @since 5.0.0 + */ + /** + * @event sort + * This event fires after the contents of the collection have been sorted. + * + * @param {Ext.util.Collection} collection The collection being sorted. + */ + /** + * @event beforesort + * @private + * This event fires before the contents of the collection have been sorted. + * + * @param {Ext.util.Collection} collection The collection being sorted. + * @param {Ext.util.Sorter[]} sorters Array of sorters applied to the Collection. + */ + /** + * @event updatekey + * Fires after the key for an item has changed. + * + * @param {Ext.util.Collection} collection The collection being modified. + * + * @param {Object} details An object describing the update. + * + * @param {Object} details.item The item whose key has changed. + * + * @param {Object} details.newKey The new key for the `item`. + * + * @param {Object} details.oldKey The old key for the `item`. + * + * @since 5.0.0 + */ + constructor: function(config) { + var me = this; + me.callParent([ + config + ]); + /** + * @property {Object[]} items + * An array containing the items. + * @private + * @since 5.0.0 + */ + me.items = []; + /** + * @property {Object} map + * An object used as a map to find items based on their key. + * @private + * @since 5.0.0 + */ + me.map = {}; + /** + * @property {Number} length + * The count of items in the collection. + * @readonly + * @since 5.0.0 + */ + me.length = 0; + /** + * @cfg {Function} [keyFn] + * A function to retrieve the key of an item in the collection. If provided, + * this replaces the default `getKey` method. The default `getKey` method handles + * items that have either an "id" or "_id" property or failing that a `getId` + * method to call. + * @since 5.0.0 + */ + if (config && config.keyFn) { + me.getKey = config.keyFn; + } + me.mixins.observable.constructor.call(me, config); + }, + /** + * Destroys this collection. This is only necessary if this collection uses a `source` + * collection as that relationship will keep a reference from the `source` to this + * collection and potentially leak memory. + * @since 5.0.0 + */ + destroy: function() { + var me = this, + filters = me._filters, + sorters = me._sorters, + groups = me._groups; + if (filters) { + filters.destroy(); + me._filters = null; + } + if (sorters) { + // Set to false here so updateSorters doesn't trigger + // the template methods + me.grouped = me.sorted = false; + me.setSorters(null); + if (me.manageSorters) { + sorters.destroy(); + } + } + if (groups) { + groups.destroy(); + me._groups = null; + } + me.setSource(null); + me.observers = me.items = me.map = null; + me.callParent(); + }, + /** + * Adds an item to the collection. If the item already exists or an item with the + * same key exists, the old item will be removed and the new item will be added to + * the end. + * + * This method also accepts an array of items or simply multiple items as individual + * arguments. The following 3 code sequences have the same end result: + * + * // Call add() once per item (not optimal - best avoided): + * collection.add(itemA); + * collection.add(itemB); + * collection.add(itemC); + * collection.add(itemD); + * + * // Call add() with each item as an argument: + * collection.add(itemA, itemB, itemC, itemD); + * + * // Call add() with the items as an array: + * collection.add([ itemA, itemB, itemC, itemD ]); + * + * The first form should be avoided where possible because the collection and all + * parties "watching" it will be updated 4 times. + * + * @param {Object/Object[]} item The item or items to add. + * @return {Object/Object[]} The item or items added. + * @since 5.0.0 + */ + add: function(item) { + var me = this, + items = me.decodeItems(arguments, 0), + ret = items; + if (items.length) { + me.splice(me.length, 0, items); + ret = (items.length === 1) ? items[0] : items; + } + return ret; + }, + /** + * Adds an item to the collection while removing any existing items. Similar to {@link #method-add}. + * @param {Object/Object[]} item The item or items to add. + * @return {Object/Object[]} The item or items added. + * @since 5.0.0 + */ + replaceAll: function() { + var me = this, + ret, items; + items = me.decodeItems(arguments, 0); + ret = items; + if (items.length) { + me.splice(0, me.length, items); + ret = (items.length === 1) ? items[0] : items; + } else { + me.removeAll(); + } + return ret; + }, + /** + * Returns the result of the specified aggregation operation against all items in this + * collection. + * + * This method is not typically called directly because there are convenience methods + * for each of the supported `operation` values. These are: + * + * * **average** - Returns the average value. + * * **bounds** - Returns an array of `[min, max]`. + * * **max** - Returns the maximum value or `undefined` if empty. + * * **min** - Returns the minimum value or `undefined` if empty. + * * **sum** - Returns the sum of all values. + * + * For example: + * + * result = collection.aggregate('age', 'sum'); + * + * result = collection.aggregate('age', 'sum', 2, 10); // the 8 items at index 2 + * + * To provide a custom operation function: + * + * function averageAgeOfMinors (items, values) { + * var sum = 0, + * count = 0; + * + * for (var i = 0; i < values.length; ++i) { + * if (values[i] < 18) { + * sum += values[i]; + * ++count; + * } + * } + * + * return count ? sum / count : 0; + * } + * + * result = collection.aggregate('age', averageAgeOfMinors); + * + * @param {String} property The name of the property to aggregate from each item. + * @param {String/Function} operation The operation to perform. + * @param {Array} operation.items The items on which the `operation` function is to + * operate. + * @param {Array} operation.values The values on which the `operation` function is to + * operate. + * @param {Number} [begin] The index of the first item in `items` to include in the + * aggregation. + * @param {Number} [end] The index at which to stop aggregating `items`. The item at + * this index will *not* be included in the aggregation. + * @param {Object} [scope] The `this` pointer to use if `operation` is a function. + * Defaults to this collection. + * @return {Object} + */ + aggregate: function(property, operation, begin, end, scope) { + var me = this, + args = Ext.Array.slice(arguments); + args.unshift(me.items); + return me.aggregateItems.apply(me, args); + }, + /** + * See {@link #aggregate}. The functionality is the same, however the aggregates are + * provided per group. Assumes this collection has an active {@link #grouper}. + * + * @param {String} property The name of the property to aggregate from each item. + * @param {String/Function} operation The operation to perform. + * @param {Array} operation.items The items on which the `operation` function is to + * operate. + * @param {Array} operation.values The values on which the `operation` function is to + * operate. + * @param {Object} [scope] The `this` pointer to use if `operation` is a function. + * Defaults to this collection. + * @return {Object} + */ + aggregateByGroup: function(property, operation, scope) { + var groups = this.getGroups(); + return this.aggregateGroups(groups, property, operation, scope); + }, + /** + * Returns the result of the specified aggregation operation against the given items. + * For details see `aggregate`. + * + * @param {Array} items The items to aggregate. + * @param {String} property The name of the property to aggregate from each item. + * @param {String/Function} operation The operation to perform. + * @param {Array} operation.items The items on which the `operation` function is to + * operate. + * @param {Array} operation.values The values on which the `operation` function is to + * operate. + * @param {Number} [begin] The index of the first item in `items` to include in the + * aggregation. + * @param {Number} [end] The index at which to stop aggregating `items`. The item at + * this index will *not* be included in the aggregation. + * @param {Object} [scope] The `this` pointer to use if `operation` is a function. + * Defaults to this collection. + * + * @private + * @return {Object} + */ + aggregateItems: function(items, property, operation, begin, end, scope) { + var me = this, + range = Ext.Number.clipIndices(items.length, [ + begin, + end + ]), + // Only extract items into new array if a subset is required + subsetRequested = (begin !== 0 && end !== items.length), + i, j, rangeLen, root, value, values, valueItems; + begin = range[0]; + end = range[1]; + if (!Ext.isFunction(operation)) { + operation = me._aggregators[operation]; + return operation.call(me, items, begin, end, property, me.getRootProperty()); + } + root = me.getRootProperty(); + // Preallocate values array with known set size. + // valueItems can be just the items array is a subset has not been requested + values = new Array(rangeLen); + valueItems = subsetRequested ? new Array(rangeLen) : items; + // Collect the extracted property values and the items for passing to the operation. + for (i = begin , j = 0; i < end; ++i , j++) { + if (subsetRequested) { + valueItems[j] = value = items[i]; + } + values[j] = (root ? value[root] : value)[property]; + } + return operation.call(scope || me, items, values, 0); + }, + /** + * Aggregates a set of groups. + * @param {Ext.util.GroupCollection} groups The groups + * @param {String} property The name of the property to aggregate from each item. + * @param {String/Function} operation The operation to perform. + * @param {Array} operation.values The values on which the `operation` function is to + * operate. + * @param {Array} operation.items The items on which the `operation` function is to + * operate. + * @param {Number} operation.index The index in `items` at which the `operation` + * function is to start. The `values.length` indicates the number of items involved. + * @param {Object} [scope] The `this` pointer to use if `operation` is a function. + * Defaults to this collection. + * + * @return {Object} + * @private + */ + aggregateGroups: function(groups, property, operation, scope) { + var items = groups.items, + len = items.length, + callDirect = !Ext.isFunction(operation), + out = {}, + i, group, result; + for (i = 0; i < len; ++i) { + group = items[i]; + if (!callDirect) { + result = this.aggregateItems(group.items, property, operation, null, null, scope); + } else { + result = group[operation](property); + } + out[group.getGroupKey()] = result; + } + return out; + }, + /** + * This method is called to indicate the start of multiple changes to the collection. + * Application code should seldom need to call this method as it is called internally + * when needed. If multiple collection changes are needed, consider wrapping them in + * an `update` call rather than calling `beginUpdate` directly. + * + * Internally this method increments a counter that is decremented by `endUpdate`. It + * is important, therefore, that if you call `beginUpdate` directly you match that + * call with a call to `endUpdate` or you will prevent the collection from updating + * properly. + * + * For example: + * + * var collection = new Ext.util.Collection(); + * + * collection.beginUpdate(); + * + * collection.add(item); + * // ... + * + * collection.insert(index, otherItem); + * //... + * + * collection.endUpdate(); + * + * @since 5.0.0 + */ + beginUpdate: function() { + if (!this.updating++) { + // jshint ignore:line + this.notify('beginupdate'); + } + }, + /** + * Removes all items from the collection. This is similar to `removeAll` except that + * `removeAll` fire events to inform listeners. This means that this method should be + * called only when you are sure there are no listeners. + * @since 5.0.0 + */ + clear: function() { + var me = this, + generation = me.generation, + ret = generation ? me.items : [], + extraKeys, indexName; + if (generation) { + me.items.length = me.length = 0; + me.map = {}; + me.indices = {}; + me.generation++; + // Clear any extraKey indices associated with this Collection + extraKeys = me.getExtraKeys(); + if (extraKeys) { + for (indexName in extraKeys) { + extraKeys[indexName].clear(); + } + } + } + return ret; + }, + /** + * Creates a shallow copy of this collection + * @return {Ext.util.Collection} + * @since 5.0.0 + */ + clone: function() { + var me = this, + copy = new me.self(me.initialConfig); + copy.add(me.items); + return copy; + }, + /** + * Collects unique values of a particular property in this Collection. + * @param {String} property The property to collect on + * @param {String} root (optional) 'root' property to extract the first argument from. This is used mainly when + * summing fields in records, where the fields are all stored inside the 'data' object + * @param {Boolean} [allowNull] Pass `true` to include `null`, `undefined` or empty + * string values. + * @return {Array} The unique values + * @since 5.0.0 + */ + collect: function(property, root, allowNull) { + var items = this.items, + length = items.length, + map = {}, + ret = [], + i, strValue, value; + for (i = 0; i < length; ++i) { + value = items[i]; + value = (root ? value[root] : value)[property]; + strValue = String(value); + if ((allowNull || !Ext.isEmpty(value)) && !map[strValue]) { + map[strValue] = 1; + ret.push(value); + } + } + return ret; + }, + /** + * Returns true if the collection contains the passed Object as an item. + * @param {Object} item The item to look for in the collection. + * @return {Boolean} `true` if the collection contains the item. + * @since 5.0.0 + */ + contains: function(item) { + var ret = false, + key; + if (item != null) { + key = this.getKey(item); + ret = this.map[key] === item; + } + return ret; + }, + /** + * Returns true if the collection contains all the passed items. If the first argument + * is an array, then the items in that array are checked. Otherwise, all arguments + * passed to this method are checked. + * + * @param {Object.../Object[]} items The item(s) that must be in the collection. + * @return {Boolean} `true` if the collection contains all the items. + * @since 6.5.2 + */ + containsAll: function(items) { + var all = Ext.isArray(items) ? items : arguments, + i; + for (i = all.length; i-- > 0; ) { + if (!this.contains(all[i])) { + return false; + } + } + return true; + }, + /** + * Returns true if the collection contains the passed Object as a key. + * @param {String} key The key to look for in the collection. + * @return {Boolean} True if the collection contains the Object as a key. + * @since 5.0.0 + */ + containsKey: function(key) { + return key in this.map; + }, + /** + * Creates a new collection that is a filtered subset of this collection. The filter + * passed can be a function, a simple property name and value, an `Ext.util.Filter` + * instance, an array of `Ext.util.Filter` instances. + * + * If the passed filter is a function the second argument is its "scope" (or "this" + * pointer). The function should return `true` given each item in the collection if + * that item should be included in the filtered collection. + * + * var people = new Ext.util.Collection(); + * + * people.add([ + * { id: 1, age: 25, name: 'Ed' }, + * { id: 2, age: 24, name: 'Tommy' }, + * { id: 3, age: 24, name: 'Arne' }, + * { id: 4, age: 26, name: 'Aaron' } + * ]); + * + * // Create a collection of people who are older than 24: + * var oldPeople = people.createFiltered(function (item) { + * return item.age > 24; + * }); + * + * If the passed filter is a `Ext.util.Filter` instance or array of `Ext.util.Filter` + * instances the filter(s) are used to produce the filtered collection and there are + * no further arguments. + * + * If the passed filter is a string it is understood as the name of the property by + * which to filter. The second argument is the "value" used to compare each item's + * property value. This comparison can be further tuned with the `anyMatch` and + * `caseSensitive` (optional) arguments. + * + * // Create a new Collection containing only the items where age == 24 + * var middleAged = people.createFiltered('age', 24); + * + * Alternatively you can apply `filters` to this Collection by calling `setFilters` + * or modifying the filter collection returned by `getFilters`. + * + * @param {Ext.util.Filter[]/String/Function} property A property on your objects, an + * array of {@link Ext.util.Filter Filter} objects or a filter function. + * + * @param {Object} value If `property` is a function, this argument is the "scope" + * (or "this" pointer) for the function. Otherwise this is either a `RegExp` to test + * property values or the value with which to compare. + * + * @param {Boolean} [anyMatch=false] True to match any part of the string, not just + * the beginning. + * + * @param {Boolean} [caseSensitive=false] True for case sensitive comparison. + * + * @param {Boolean} [exactMatch=false] `true` to force exact match (^ and $ characters added to the regex). + * + * @return {Ext.util.Collection} The new, filtered collection. + * + * @since 5.0.0 + */ + createFiltered: function(property, value, anyMatch, caseSensitive, exactMatch) { + var me = this, + ret = new me.self(me.initialConfig), + root = me.getRootProperty(), + items = me.items, + length, i, filters, fn, scope; + if (Ext.isFunction(property)) { + fn = property; + scope = value; + } else { + //support for the simple case of filtering by property/value + if (Ext.isString(property)) { + filters = [ + new Ext.util.Filter({ + property: property, + value: value, + root: root, + anyMatch: anyMatch, + caseSensitive: caseSensitive, + exactMatch: exactMatch + }) + ]; + } else if (property instanceof Ext.util.Filter) { + filters = [ + property + ]; + property.setRoot(root); + } else if (Ext.isArray(property)) { + filters = property.slice(0); + for (i = 0 , length = filters.length; i < length; ++i) { + filters[i].setRoot(root); + } + } + // At this point we have an array of zero or more Ext.util.Filter objects to + // filter with, so here we construct a function that combines these filters by + // ANDing them together and filter by that. + fn = Ext.util.Filter.createFilterFn(filters); + } + scope = scope || me; + for (i = 0 , length = items.length; i < length; i++) { + if (fn.call(scope, items[i])) { + ret.add(items[i]); + } + } + return ret; + }, + /** + * Filter by a function. Returns a new collection that has been filtered. + * The passed function will be called with each object in the collection. + * If the function returns true, the value is included otherwise it is filtered. + * @param {Function} fn The function to be called. + * @param {Mixed} fn.item The collection item. + * @param {String} fn.key The key of collection item. + * @param {Object} scope (optional) The scope (this reference) in + * which the function is executed. Defaults to this Collection. + * @return {Ext.util.Collection} The new filtered collection + * @deprecated 5.0.0 This method is deprecated. + */ + filterBy: function(fn, scope) { + return this.createFiltered(fn, scope); + }, + /** + * Executes the specified function once for every item in the collection. If the value + * returned by `fn` is `false` the iteration stops. In all cases, the last value that + * `fn` returns is returned by this method. + * + * @param {Function} fn The function to execute for each item. + * @param {Object} fn.item The collection item. + * @param {Number} fn.index The index of item. + * @param {Number} fn.len Total length of collection. + * @param {Object} [scope=this] The scope (`this` reference) in which the function + * is executed. Defaults to this collection. + * @since 5.0.0 + */ + each: function(fn, scope) { + var items = this.items, + len = items.length, + i, ret; + if (len) { + scope = scope || this; + items = items.slice(0); + // safe for re-entrant calls + for (i = 0; i < len; i++) { + ret = fn.call(scope, items[i], i, len); + if (ret === false) { + break; + } + } + } + return ret; + }, + /** + * Executes the specified function once for every key in the collection, passing each + * key, and its associated item as the first two parameters. If the value returned by + * `fn` is `false` the iteration stops. In all cases, the last value that `fn` returns + * is returned by this method. + * + * @param {Function} fn The function to execute for each item. + * @param {String} fn.key The key of collection item. + * @param {Object} fn.item The collection item. + * @param {Number} fn.index The index of item. + * @param {Number} fn.len Total length of collection. + * @param {Object} [scope=this] The scope (`this` reference) in which the function + * is executed. Defaults to this collection. + * @since 5.0.0 + */ + eachKey: function(fn, scope) { + var me = this, + items = me.items, + len = items.length, + i, item, key, ret; + if (len) { + scope = scope || me; + items = items.slice(0); + // safe for re-entrant calls + for (i = 0; i < len; i++) { + key = me.getKey(item = items[i]); + ret = fn.call(scope, key, item, i, len); + if (ret === false) { + break; + } + } + } + return ret; + }, + /** + * This method is called after modifications are complete on a collection. For details + * see `beginUpdate`. + * @since 5.0.0 + */ + endUpdate: function() { + if (!--this.updating) { + this.notify('endupdate'); + } + }, + /** + * Finds the first matching object in this collection by a specific property/value. + * + * @param {String} property The name of a property on your objects. + * @param {String/RegExp} value A string that the property values + * should start with or a RegExp to test against the property. + * @param {Number} [start=0] The index to start searching at. + * @param {Boolean} [startsWith=true] Pass `false` to allow a match start anywhere in + * the string. By default the `value` will match only at the start of the string. + * @param {Boolean} [endsWith=true] Pass `false` to allow the match to end before the + * end of the string. By default the `value` will match only at the end of the string. + * @param {Boolean} [ignoreCase=true] Pass `false` to make the `RegExp` case + * sensitive (removes the 'i' flag). + * @return {Object} The first item in the collection which matches the criteria or + * `null` if none was found. + * @since 5.0.0 + */ + find: function(property, value, start, startsWith, endsWith, ignoreCase) { + if (Ext.isEmpty(value, false)) { + return null; + } + var regex = Ext.String.createRegex(value, startsWith, endsWith, ignoreCase), + root = this.getRootProperty(); + return this.findBy(function(item) { + return item && regex.test((root ? item[root] : item)[property]); + }, null, start); + }, + /** + * Returns the first item in the collection which elicits a true return value from the + * passed selection function. + * @param {Function} fn The selection function to execute for each item. + * @param {Object} fn.item The collection item. + * @param {String} fn.key The key of collection item. + * @param {Object} [scope=this] The scope (`this` reference) in which the function + * is executed. Defaults to this collection. + * @param {Number} [start=0] The index at which to start searching. + * @return {Object} The first item in the collection which returned true from the selection + * function, or null if none was found. + * @since 5.0.0 + */ + findBy: function(fn, scope, start) { + var me = this, + items = me.items, + len = items.length, + i, item, key; + scope = scope || me; + for (i = start || 0; i < len; i++) { + key = me.getKey(item = items[i]); + if (fn.call(scope, item, key)) { + return items[i]; + } + } + return null; + }, + /** + * Finds the index of the first matching object in this collection by a specific + * property/value. + * + * @param {String} property The name of a property on your objects. + * @param {String/RegExp} value A string that the property values + * should start with or a RegExp to test against the property. + * @param {Number} [start=0] The index to start searching at. + * @param {Boolean} [startsWith=true] Pass `false` to allow a match start anywhere in + * the string. By default the `value` will match only at the start of the string. + * @param {Boolean} [endsWith=true] Pass `false` to allow the match to end before the + * end of the string. By default the `value` will match only at the end of the string. + * @param {Boolean} [ignoreCase=true] Pass `false` to make the `RegExp` case + * sensitive (removes the 'i' flag). + * @return {Number} The matched index or -1 if not found. + * @since 5.0.0 + */ + findIndex: function(property, value, start, startsWith, endsWith, ignoreCase) { + var item = this.find(property, value, start, startsWith, endsWith, ignoreCase); + return item ? this.indexOf(item) : -1; + }, + /** + * Find the index of the first matching object in this collection by a function. + * If the function returns `true` it is considered a match. + * @param {Function} fn The function to be called. + * @param {Object} fn.item The collection item. + * @param {String} fn.key The key of collection item. + * @param {Object} [scope=this] The scope (`this` reference) in which the function + * is executed. Defaults to this collection. + * @param {Number} [start=0] The index at which to start searching. + * @return {Number} The matched index or -1 + * @since 5.0.0 + */ + findIndexBy: function(fn, scope, start) { + var item = this.findBy(fn, scope, start); + return item ? this.indexOf(item) : -1; + }, + /** + * Returns the first item in the collection. + * @param {Boolean} [grouped] `true` to extract the first item in each group. Only applies if + * a {@link #grouper} is active in the collection. + * @return {Object} The first item in the collection. If the grouped parameter is passed, + * see {@link #aggregateByGroup} for information on the return type. + * @since 5.0.0 + */ + first: function(grouped) { + var groups = grouped ? this.getGroups() : undefined; + return groups ? this.aggregateGroups(groups, null, 'first') : this.items[0]; + }, + /** + * Returns the last item in the collection. + * @param {Boolean} [grouped] `true` to extract the first item in each group. Only applies if + * a {@link #grouper} is active in the collection. + * @return {Object} The last item in the collection. If the grouped parameter is passed, + * see {@link #aggregateByGroup} for information on the return type. + * @since 5.0.0 + */ + last: function(grouped) { + var groups = grouped ? this.getGroups() : undefined; + return groups ? this.aggregateGroups(groups, null, 'last') : this.items[this.length - 1]; + }, + /** + * Returns the item associated with the passed key. + * @param {String/Number} key The key of the item. + * @return {Object} The item associated with the passed key. + * @since 5.0.0 + */ + get: function(key) { + return this.map[key]; + }, + /** + * Returns the item at the specified index. + * @param {Number} index The index of the item. + * @return {Object} The item at the specified index. + * @since 5.0.0 + */ + getAt: function(index) { + return this.items[index]; + }, + /** + * Returns the item associated with the passed key. + * @param {String/Number} key The key of the item. + * @return {Object} The item associated with the passed key. + * @since 5.0.0 + */ + getByKey: function(key) { + return this.map[key]; + }, + /** + * Returns the number of items in the collection. + * @return {Number} the number of items in the collection. + * @since 5.0.0 + */ + getCount: function() { + return this.length; + }, + /** + * A function which will be called, passing an object belonging to this collection. + * The function should return the key by which that object will be indexed. This key + * must be unique to this item as only one item with this key will be retained. + * + * The default implementation looks basically like this (give or take special case + * handling of 0): + * + * function getKey (item) { + * return item.id || item._id || item.getId(); + * } + * + * You can provide your own implementation by passing the `keyFn` config. + * + * For example, to hold items that have a unique "name" property: + * + * var elementCollection = new Ext.util.Collection({ + * keyFn: function (item) { + * return item.name; + * } + * }); + * + * The collection can have `extraKeys` if items need to be quickly looked up by other + * (potentially non-unique) properties. + * + * @param {Object} item The item. + * @return {Object} The key for the passed item. + * @since 5.0.0 + */ + getKey: function(item) { + var id = item.id; + return (id === 0 || id) ? id : ((id = item._id) === 0 || id) ? id : item.getId(); + }, + /** + * Returns a range of items in this collection + * @param {Number} [begin=0] The index of the first item to get. + * @param {Number} [end] The ending index. The item at this index is *not* included. + * @return {Array} An array of items + * @since 5.0.0 + */ + getRange: function(begin, end) { + var items = this.items, + length = items.length, + range; + if (begin > end) { + Ext.raise('Inverted range passed to Collection.getRange: [' + begin + ',' + end + ']'); + } + if (!length) { + range = []; + } else { + range = Ext.Number.clipIndices(length, [ + begin, + end + ]); + range = items.slice(range[0], range[1]); + } + return range; + }, + /** + * @method getSource + * Returns all unfiltered items in the Collection when the Collection has been + * filtered. Returns `null` when the Collection is not filtered. + * @return {Ext.util.Collection} items All unfiltered items (or `null` when the + * Collection is not filtered) + */ + /** + * Returns an array of values for the specified (sub) property. + * + * For example, to get an array of "name" properties from a collection of records (of + * `Ext.data.Model` objects): + * + * var names = collection.getValues('name', 'data'); + * + * @param {String} property The property to collect on + * @param {String} [root] 'root' property to extract the first argument from. This is + * used mainly when operating on fields in records, where the fields are all stored + * inside the 'data' object. + * @param {Number} [start=0] The index of the first item to include. + * @param {Number} [end] The index at which to stop getting values. The value of this + * item is *not* included. + * @return {Object[]} The array of values. + * @since 5.0.0 + */ + getValues: function(property, root, start, end) { + var items = this.items, + range = Ext.Number.clipIndices(items.length, [ + start, + end + ]), + ret = [], + i, value; + for (i = range[0] , end = range[1]; i < end; ++i) { + value = items[i]; + value = (root ? value[root] : value)[property]; + ret.push(value); + } + return ret; + }, + /** + * Returns index within the collection of the passed Object. + * @param {Object} item The item to find. + * @return {Number} The index of the item or -1 if not found. + * @since 5.0.0 + */ + indexOf: function(item) { + if (!item) { + return -1; + } + var key = this.getKey(item); + return this.indexOfKey(key); + }, + /** + * Returns index within the collection of the passed key. + * @param {Object} key The key to find. + * @return {Number} The index of the item or -1 if not found. + * @since 5.0.0 + */ + indexOfKey: function(key) { + var me = this, + indices = me.indices; + if (key in me.map) { + if (!indices) { + indices = me.getIndices(); + } + return indices[key]; + } + return -1; + }, + /** + * Inserts one or more items to the collection. The `index` value is the position at + * which the first item will be placed. The items starting at that position will be + * shifted to make room. + * + * @param {Number} index The index at which to insert the item(s). + * @param {Object/Object[]} item The item or items to add. + * @return {Object/Object[]} The item or items added. + * @since 5.0.0 + */ + insert: function(index, item) { + var me = this, + items = me.decodeItems(arguments, 1), + ret = items; + if (items.length) { + me.splice(index, 0, items); + ret = (items.length === 1) ? items[0] : items; + } + return ret; + }, + /** + * This method should be called when an item in this collection has been modified. If + * the collection is sorted or filtered the result of modifying an item needs to be + * reflected in the collection. If the item's key is also being modified, it is best + * to pass the `oldKey` to this same call rather than call `updateKey` separately. + * + * @param {Object} item The item that was modified. + * @param {String[]} [modified] The names of the modified properties of the item. + * @param {String/Number} [oldKey] Passed if the item's key was also modified. + * @param {Object} meta (private) + * @since 5.0.0 + */ + itemChanged: function(item, modified, oldKey, meta) { + var me = this, + keyChanged = oldKey !== undefined, + filtered = me.filtered && me.getAutoFilter(), + filterChanged = false, + itemMovement = 0, + items = me.items, + last = me.length - 1, + sorted = me.sorted && last > 0 && me.getAutoSort(), + // one or zero items is not really sorted + // CAN be called on an empty Collection + // A TreeStore can call afterEdit on a hidden root before + // any child nodes exist in the store. + source = me.getSource(), + toRemove = 0, + itemFiltered = false, + wasFiltered = false, + details, newKey, sortFn, toAdd, index, newIndex; + // We are owned, we cannot react, inform owning collection. + if (source && !source.updating) { + me.sourceUpdating = true; + source.itemChanged(item, modified, oldKey, meta); + me.sourceUpdating = false; + } else // Root Collection has been informed. + // Change is propagating downward from root. + { + newKey = me.getKey(item); + if (filtered) { + index = me.indexOfKey(keyChanged ? oldKey : newKey); + wasFiltered = (index < 0); + itemFiltered = me.isItemFiltered(item); + filterChanged = (wasFiltered !== itemFiltered); + } + if (filterChanged) { + if (itemFiltered) { + toRemove = [ + item + ]; + newIndex = -1; + } else { + toAdd = [ + item + ]; + newIndex = me.length; + } + } + // this will be ignored if sorted + // If sorted, the newIndex must be reported correctly in the beforeitemchange and itemchange events. + // Even though splice ignores the parameter and calculates the insertion point + else if (sorted && !itemFiltered) { + // If we are sorted and there are 2 or more items make sure this item is at + // the proper index. + if (!filtered) { + // If the filter has not changed we may need to move the item but if + // there is a filter we have already determined its index. + index = me.indexOfKey(keyChanged ? oldKey : newKey); + } + sortFn = me.getSortFn(); + if (index !== -1) { + if (index && sortFn(items[index - 1], items[index]) > 0) { + // If this item is not the first and the item before it compares as + // greater-than then item needs to move left since it is less-than + // item[index - 1]. + itemMovement = -1; + // We have to bound the binarySearch or else the presence of the + // out-of-order "item" would break it. + newIndex = Ext.Array.binarySearch(items, item, 0, index, sortFn); + } else if (index < last && sortFn(items[index], items[index + 1]) > 0) { + // If this item is not the last and the item after it compares as + // less-than then item needs to move right since it is greater-than + // item[index + 1]. + itemMovement = 1; + // We have to bound the binarySearch or else the presence of the + // out-of-order "item" would break it. + newIndex = Ext.Array.binarySearch(items, item, index + 1, sortFn); + } + if (itemMovement) { + toAdd = [ + item + ]; + } + } + } + // One may be tempted to avoid this notification when none of our three vars + // are true, *but* the problem with that is that these three changes we care + // about are only what this collection cares about. Child collections or + // outside parties still need to know that the item has changed in some way. + // We do NOT adjust the newIndex reported here to allow for position *after* the item has been removed + // We report the "visual" position at which the item would be inserted as if it were new. + details = { + item: item, + key: newKey, + index: newIndex, + filterChanged: filterChanged, + keyChanged: keyChanged, + indexChanged: !!itemMovement, + filtered: itemFiltered, + oldIndex: index, + newIndex: newIndex, + wasFiltered: wasFiltered, + meta: meta + }; + if (keyChanged) { + details.oldKey = oldKey; + } + if (modified) { + details.modified = modified; + } + ++me.generation; + me.beginUpdate(); + me.notify('beforeitemchange', [ + details + ]); + if (keyChanged) { + me.updateKey(item, oldKey, details); + } + if (toAdd || toRemove) { + // In sorted mode (which is the only time we get here), newIndex is + // correct but *ignored* by splice since it has to assume that *insert* + // index values need to be determined internally. In other words, the + // first argument here is both the remove and insert index but in sorted + // mode the insert index is calculated by splice. + me.splice(newIndex, toRemove, toAdd); + } + // Ensure that the newIndex always refers to the item the insertion is *before*. + // Ensure that the oldIndex always refers to the item the insertion was *before*. + // + // Before change to "c" to "h": | Before change "i" to "d": + // | + // +---+---+---+---+---+---+ | +---+---+---+---+---+---+ + // | a | c | e | g | i | k | | | a | c | e | g | i | k | + // +---+---+---+---+---+---+ | +---+---+---+---+---+---+ + // 0 1 2 3 4 5 | 0 1 2 3 4 5 + // ^ ^ | ^ ^ + // | | | | | + // oldIndex newIndex | newIndex oldIndex + // | + // After change to "c" to "h": | After change "i" to "d": + // | + // +---+---+---+---+---+---+ | +---+---+---+---+---+---+ + // | a | e | g | h | i | k | | | a | c | d | e | g | k | + // +---+---+---+---+---+---+ | +---+---+---+---+---+---+ + // 0 1 2 3 4 5 | 0 1 2 3 4 5 + // ^ ^ | ^ ^ + // | | | | | + // oldIndex newIndex | newIndex oldIndex + // + if (itemMovement > 0) { + details.newIndex--; + } else if (itemMovement < 0) { + details.oldIndex++; + } + // Divergence depending on whether the record if filtered out at this level in a chaining hierarchy. + // Child collections of this collection will not care about filtereditemchange because the record is not in them. + // Stores however will still need to know because the record *is* in them, just filtered. + me.notify(itemFiltered ? 'filtereditemchange' : 'itemchange', [ + details + ]); + me.endUpdate(); + } + }, + /** + * Remove an item from the collection. + * @param {Object/Object[]} item The item or items to remove. + * @return {Number} The number of items removed. + * @since 5.0.0 + */ + remove: function(item) { + var me = this, + items = me.decodeRemoveItems(arguments, 0), + length = me.length; + me.splice(0, items); + return length - me.length; + }, + /** + * Remove all items in the collection. + * @return {Ext.util.Collection} This object. + * @since 5.0.0 + */ + removeAll: function() { + var me = this, + length = me.length; + if (me.generation && length) { + me.splice(0, length); + } + return me; + }, + /** + * Remove an item from a specified index in the collection. + * @param {Number} index The index within the collection of the item to remove. + * @param {Number} [count=1] The number of items to remove. + * @return {Object/Number} If `count` was 1 and the item was removed, that item is + * returned. Otherwise the number of items removed is returned. + * @since 5.0.0 + */ + removeAt: function(index, count) { + var me = this, + length = me.length, + Num = Ext.Number, + range = Num.clipIndices(length, [ + index, + (count === undefined) ? 1 : count + ], Num.Clip.COUNT), + n = range[0], + removeCount = range[1] - n, + item = (removeCount === 1) && me.getAt(n), + removed; + me.splice(n, removeCount); + removed = me.length - length; + return (item && removed) ? item : removed; + }, + /** + * Removes the item associated with the passed key from the collection. + * @param {String} key The key of the item to remove. + * @return {Object} Only returned if removing at a specified key. The item removed or + * `false` if no item was removed. + * @since 5.0.0 + */ + removeByKey: function(key) { + var item = this.getByKey(key); + if (!item || !this.remove(item)) { + return false; + } + return item; + }, + /** + * @private + * Replace an old entry with a new entry of the same key if the entry existed. + * @param {Object} item The item to insert. + * @return {Object} inserted The item inserted. + */ + replace: function(item) { + var index = this.indexOf(item); + if (index === -1) { + this.add(item); + } else { + this.insert(index, item); + } + }, + /** + * This method is basically the same as the JavaScript Array splice method. + * + * Negative indexes are interpreted starting at the end of the collection. That is, + * a value of -1 indicates the last item, or equivalent to `length - 1`. + * + * @param {Number} index The index at which to add or remove items. + * @param {Number/Object[]} toRemove The number of items to remove or an array of the + * items to remove. + * @param {Object[]} [toAdd] The items to insert at the given `index`. + * @since 5.0.0 + */ + splice: function(index, toRemove, toAdd) { + var me = this, + autoSort = me.sorted && me.getAutoSort(), + map = me.map, + items = me.items, + length = me.length, + removeItems = (toRemove instanceof Array) ? me.decodeRemoveItems(toRemove) : null, + isRemoveCount = !removeItems, + Num = Ext.Number, + range = Num.clipIndices(length, [ + index, + isRemoveCount ? toRemove : 0 + ], Num.Clip.COUNT), + begin = range[0], + end = range[1], + // Determine how many items we might actually remove: + removeCount = end - begin, + newItems = me.decodeItems(arguments, 2), + newCount = newItems ? newItems.length : 0, + addItems, newItemsMap, removeMap, + insertAt = begin, + indices = me.indices || ((newCount || removeItems) ? me.getIndices() : null), + adds = null, + removes = removeCount ? [ + begin + ] : null, + newKeys = null, + source = me.getSource(), + chunk, chunkItems, chunks, i, item, itemIndex, k, key, keys, n, duplicates, sorters; + if (source && !source.updating) { + // Modifying the content of a child collection has to be translated into a + // change of its source. Because the source has all of the items of the child + // (but likely at different indices) we can translate "index" and convert a + // "removeCount" request into a "removeItems" request. + if (isRemoveCount) { + removeItems = []; + for (i = 0; i < removeCount; ++i) { + removeItems.push(items[begin + i]); + } + } + if (begin < length) { + // Map index based on the item at that index since that item will be in + // the source collection. + i = source.indexOf(items[begin]); + } else { + // Map end of this collection to end of the source collection. + i = source.length; + } + // When we react to the source add in onCollectionAdd, we must honour this requested index. + me.requestedIndex = index; + source.splice(i, removeItems, newItems); + delete me.requestedIndex; + return me; + } + // Loop over the newItems because they could already be in the collection or may + // be replacing items in the collection that just happen to have the same key. In + // this case, those items must be removed as well. Since we need to call getKey + // on each newItem to do this we may as well keep those keys for later. + if (newCount) { + addItems = newItems; + newKeys = []; + newItemsMap = {}; + // If this collection is sorted we will eventually need to sort addItems so + // do that now so we can line up the newKeys properly. We optimize for the + // case where we have no duplicates. It would be more expensive to do this + // in two passes in an attempt to take advantage of removed duplicates. + if (autoSort) { + // We'll need the sorters later as well + sorters = me.getSorters(); + if (newCount > 1) { + if (!addItems.$cloned) { + newItems = addItems = addItems.slice(0); + } + me.sortData(addItems); + } + } + for (i = 0; i < newCount; ++i) { + key = me.getKey(item = newItems[i]); + if ((k = newItemsMap[key]) !== undefined) { + // Duplicates in the incoming newItems need to be discarded keeping the + // last of the duplicates. We add the index of the last duplicate of + // this key to the "duplicates" map. + (duplicates || (duplicates = {}))[k] = 1; + } else { + // This item's index is outside the remove range, so we need to remove + // some extra stuff. Only the first occurrence of a given key in the + // newItems needs this processing. + itemIndex = indices[key]; + if (itemIndex < begin || end <= itemIndex) { + (removes || (removes = [])).push(itemIndex); + } + } + // might be the first + newItemsMap[key] = i; + // track the last index of this key in newItems + newKeys.push(key); + } + // must correspond 1-to-1 with newItems + if (duplicates) { + keys = newKeys; + addItems = []; + newKeys = []; + addItems.$cloned = true; + for (i = 0; i < newCount; ++i) { + if (!duplicates[i]) { + item = newItems[i]; + addItems.push(item); + newKeys.push(keys[i]); + } + } + newCount = addItems.length; + } + adds = { + //at: insertAt, // must fill this in later + //next: null, // only set by spliceMerge + //replaced: null, // must fill this in later + items: addItems, + keys: newKeys + }; + } + // If we are given a set of items to remove, map them to their indices. + for (i = removeItems ? removeItems.length : 0; i-- > 0; ) { + key = me.getKey(removeItems[i]); + if ((itemIndex = indices[key]) !== undefined) { + // ignore items we don't have (probably due to filtering) + (removes || (removes = [])).push(itemIndex); + } + } + // might be the first remove + if (!adds && !removes) { + return me; + } + me.beginUpdate(); + // Now we that everything we need to remove has its index in the removes array. + // We start by sorting the array so we can coalesce the index values into chunks + // or ranges. + if (removes) { + chunk = null; + chunks = []; + removeMap = {}; + if (removes.length > 1) { + removes.sort(Ext.Array.numericSortFn); + } + // Coalesce the index array into chunks of (index, count) pairs for efficient + // removal. + for (i = 0 , n = removes.length; i < n; ++i) { + key = me.getKey(item = items[itemIndex = removes[i]]); + if (!(key in map)) { + + continue; + } + // Avoids 2nd loop of removed items but also means we won't process any + // given item twice (in case of duplicates in removeItems). + delete map[key]; + // Consider chunk = { at: 1, items: [ item1, item2 ] } + // + // +---+---+---+---+---+---+ + // | | x | x | | | | + // +---+---+---+---+---+---+ + // 0 1 2 3 4 5 + // + // If we are adding an itemIndex > 3 we need a new chunk. + // + if (!chunk || itemIndex > (chunk.at + chunkItems.length)) { + chunks.push(chunk = { + at: itemIndex, + items: (chunkItems = []), + keys: (keys = []), + map: removeMap, + next: chunk, + replacement: adds + }); + // Point "replaced" at the last chunk + if (adds) { + adds.replaced = chunk; + } + } + chunkItems.push(removeMap[key] = item); + keys.push(key); + if (itemIndex < insertAt - 1) { + // If the removal is ahead of the insertion point specified, we need + // to move the insertAt backwards. + // + // Consider the following splice: + // + // collection.splice(3, 2, [ { id: 'b' } ]); + // + // +---+---+---+---+---+---+ + // | a | b | c | x | y | d | + // +---+---+---+---+---+---+ + // 0 1 2 3 4 5 + // ^ ^ ^ + // | \ / + // replace remove + // + // The intent is to replace x and y with the new item at index=3. But + // since the new item has the same key as the item at index=1, that + // item must be replaced. The resulting collection will be: + // + // +---+---+---+---+ + // | a | c | b | d | + // +---+---+---+---+ + // 0 1 2 3 + // + --insertAt; + } + if (removeCount > 1 && itemIndex === begin) { + // To account for the given range to remove we started by putting the + // index of the first such item ("begin") in the array. When we find + // it in this loop we have to process all of the items and add them + // to the current chunk. The following trick allows us to repeat the + // loop for each item in the removeCount. + // + --removeCount; + // countdown... + removes[i--] = ++begin; + } + } + // backup and increment begin + // for (removes) + if (adds) { + adds.at = insertAt; + } + // we have the correct(ed) insertAt now + // Loop over the chunks in reverse so as to not invalidate index values on + // earlier chunks. + for (k = chunks.length; k-- > 0; ) { + chunk = chunks[k]; + i = chunk.at; + n = chunk.items.length; + if (i + n < length) { + // If we are removing the tail of the collection, we can keep the + // indices for the rest of the things... otherwise we need to zap it + // and fix up later. + me.indices = indices = null; + } + me.length = length -= n; + // We can use splice directly. The IE8 bug which Ext.Array works around + // only affects *insertion* + // http://social.msdn.microsoft.com/Forums/en-US/iewebdevelopment/thread/6e946d03-e09f-4b22-a4dd-cd5e276bf05a/ + //Ext.Array.erase(items, i, n); + items.splice(i, n); + if (indices) { + keys = chunk.keys; + for (i = 0; i < n; ++i) { + delete indices[keys[i]]; + } + } + ++me.generation; + me.notify('remove', [ + chunk + ]); + } + } + // if (removes) + if (adds) { + if (autoSort && newCount > 1 && length) { + me.spliceMerge(addItems, newKeys); + } else { + if (autoSort) { + if (newCount > 1) { + // We have multiple addItems but we are empty, so just add at 0 + insertAt = 0; + me.indices = indices = null; + } else { + // If we are adding one item we can position it properly now and + // avoid a full sort. + insertAt = sorters.findInsertionIndex(adds.items[0], items, me.getSortFn(), index); + } + } + if (insertAt === length) { + end = insertAt; + // Inser items backwards. This way, when the first item is pushed the + // array is sized to as large as we're going to need it to be. + for (i = addItems.length - 1; i >= 0; --i) { + items[end + i] = addItems[i]; + } + // The indices may have been regenerated, so we need to check if they have been + // and update them + indices = me.indices; + if (indices) { + for (i = 0; i < newCount; ++i) { + indices[newKeys[i]] = insertAt + i; + } + } + } else { + // inserting + me.indices = null; + Ext.Array.insert(items, insertAt, addItems); + } + for (i = 0; i < newCount; ++i) { + map[newKeys[i]] = addItems[i]; + } + me.length += newCount; + adds.at = insertAt; + adds.atItem = insertAt === 0 ? null : items[insertAt - 1]; + ++me.generation; + me.notify('add', [ + adds + ]); + } + } + // if (adds) + me.endUpdate(); + return me; + }, + /** + * This method calls the supplied function `fn` between `beginUpdate` and `endUpdate` + * calls. + * + * collection.update(function () { + * // Perform multiple collection updates... + * + * collection.add(item); + * // ... + * + * collection.insert(index, otherItem); + * //... + * + * collection.remove(someItem); + * }); + * + * @param {Function} fn The function to call that will modify this collection. + * @param {Ext.util.Collection} fn.collection This collection. + * @param {Object} [scope=this] The `this` pointer to use when calling `fn`. + * @return {Object} Returns the value returned from `fn` (typically `undefined`). + * @since 5.0.0 + */ + update: function(fn, scope) { + var me = this; + me.beginUpdate(); + try { + return fn.call(scope || me, me); + } catch (e) { + Ext.log.error(this.$className + ': Unhandled Exception: ', e.description || e.message); + throw e; + } finally { + me.endUpdate(); + } + }, + /** + * Change the key for an existing item in the collection. If the old key does not + * exist this call does nothing. Even so, it is highly recommended to *avoid* calling + * this method for an `item` that is not a member of this collection. + * + * @param {Object} item The item whose key has changed. The `item` should be a member + * of this collection. + * @param {String} oldKey The old key for the `item`. + * @param details + * @since 5.0.0 + */ + updateKey: function(item, oldKey, details) { + var me = this, + map = me.map, + indices = me.indices, + source = me.getSource(), + newKey; + if (source && !source.updating) { + // If we are being told of the key change and the source has the same idea + // on keying the item, push the change down instead. + source.updateKey(item, oldKey); + } else if ((newKey = me.getKey(item)) !== oldKey) { + // If the key has changed and "item" is the item mapped to the oldKey and + // there is no collision with an item with the newKey, we can proceed. + if (map[oldKey] === item && !(newKey in map)) { + delete map[oldKey]; + // We need to mark ourselves as updating so that observing collections + // don't reflect the updateKey back to us (see above check) but this is + // not really a normal update cycle so we don't call begin/endUpdate. + me.updating++; + me.generation++; + map[newKey] = item; + if (indices) { + indices[newKey] = indices[oldKey]; + delete indices[oldKey]; + } + me.notify('updatekey', [ + Ext.apply({ + item: item, + newKey: newKey, + oldKey: oldKey + }, details) + ]); + me.updating--; + } else { + // It may be that the item is (somehow) already in the map using the + // newKey or that there is no item in the map with the oldKey. These + // are not errors. + if (newKey in map && map[newKey] !== item) { + // There is a different item in the map with the newKey which is an + // error. To properly handle this, add the item instead. + Ext.raise('Duplicate newKey "' + newKey + '" for item with oldKey "' + oldKey + '"'); + } + if (oldKey in map && map[oldKey] !== item) { + // There is a different item in the map with the oldKey which is also + // an error. Do not call this method for items that are not part of + // the collection. + Ext.raise('Incorrect oldKey "' + oldKey + '" for item with newKey "' + newKey + '"'); + } + } + } + }, + findInsertIndex: function(item) { + var source = this.getSource(), + sourceItems = source.items, + i = source.indexOf(item) - 1, + sourceItem, index; + while (i > -1) { + sourceItem = sourceItems[i]; + index = this.indexOf(sourceItem); + if (index > -1) { + return index + 1; + } + --i; + } + // If we get here we didn't find any item in the parent before us, so insert + // at the start + return 0; + }, + //------------------------------------------------------------------------- + // Calls from the source Collection: + /** + * This method is called when items are added to the `source` collection. This is + * equivalent to the `{@link #event-add add}` event but is called before the `add` + * event is fired. + * @param {Ext.util.Collection} source The source collection. + * @param {Object} details The `details` of the `{@link #event-add add}` event. + * @private + * @since 5.0.0 + */ + onCollectionAdd: function(source, details) { + var me = this, + atItem = details.atItem, + items = details.items, + requestedIndex = me.requestedIndex, + filtered, index, copy, i, item, n; + // No point determining the index if we're sorted + if (!me.sorted) { + // If we have a requestedIndex, it means the add/insert was on our collection, so try + // use that specified index to do the insertion. + if (requestedIndex !== undefined) { + index = requestedIndex; + } else if (atItem) { + index = me.indexOf(atItem); + if (index === -1) { + // We can't find the reference item in our collection, which means it's probably + // filtered out, so we need to search for an appropriate index. Pass the first item + // and work back to find + index = me.findInsertIndex(items[0]); + } else { + // We also have that item in our collection, we need to insert after it, so increment + ++index; + } + } else { + // If there was no atItem, must be at the front of the collection. + // atItem is the item after which the upstream Collection inserted + // the new item(s) if null, it means at start. + index = 0; + } + } + if (me.getAutoFilter() && me.filtered) { + for (i = 0 , n = items.length; i < n; ++i) { + item = items[i]; + if (me.isItemFiltered(item)) { + // If we have an item that is filtered out of this collection, we need + // to make a copy of the items up to this point. + if (!copy) { + copy = items.slice(0, i); + } + if (!filtered) { + filtered = []; + } + filtered.push(item); + } else if (copy) { + // If we have a copy of the items, we need to put this item in that + // copy since it is not being filtered out. + copy.push(item); + } + } + } + me.splice((index < 0) ? me.length : index, 0, copy || items); + if (filtered) { + // Private for now. We may want to let any observers know we just + // added these items but got filtered out + me.notify('filteradd', [ + filtered + ]); + } + }, + /** + * This method is called when an item is modified in the `source` collection. This is + * equivalent to the `{@link #event-beforeitemchange beforeitemchange}` event but is + * called before the `beforeitemchange` event is fired. + * @param {Ext.util.Collection} source The source collection. + * @param {Object} details The `details` of the + * `{@link #event-beforeitemchange beforeitemchange}` event. + * @private + * @since 5.0.0 + */ + onCollectionBeforeItemChange: function(source, details) { + // Drop the next updatekey event + this.onCollectionUpdateKey = null; + // If this flag is true it means we're inside itemchanged, so this will be fired + // shortly, don't fire it twice + if (!this.sourceUpdating) { + this.notify('beforeitemchange', [ + details + ]); + } + }, + /** + * This method is called when the `source` collection starts updating. This is + * equivalent to the `{@link #event-beginupdate beginupdate}` event but is called + * before the `beginupdate` event is fired. + * @param {Ext.util.Collection} source The source collection. + * @private + * @since 5.0.0 + */ + onCollectionBeginUpdate: function() { + this.beginUpdate(); + }, + /** + * This method is called when the `source` collection finishes updating. This is + * equivalent to the `{@link #event-endupdate endupdate}` event but is called before + * the `endupdate` event is fired. + * @param {Ext.util.Collection} source The source collection. + * @private + * @since 5.0.0 + */ + onCollectionEndUpdate: function() { + this.endUpdate(); + }, + /** + * This method is called when an item is modified in the `source` collection. This is + * equivalent to the `{@link #event-itemchange itemchange}` event but is called before + * the `itemchange` event is fired. + * @param {Ext.util.Collection} source The source collection. + * @param {Object} details The `details` of the `{@link #event-itemchange itemchange}` + * event. + * @private + * @since 5.0.0 + */ + onCollectionItemChange: function(source, details) { + // Restore updatekey events + delete this.onCollectionUpdateKey; + this.itemChanged(details.item, details.modified, details.oldKey, details.meta); + }, + onCollectionFilteredItemChange: function() { + delete this.onCollectionUpdateKey; + }, + /** + * This method is called when the `source` collection refreshes. This is equivalent to + * the `{@link #event-refresh refresh}` event but is called before the `refresh` event + * is fired. + * @param {Ext.util.Collection} source The source collection. + * @private + * @since 5.0.0 + */ + onCollectionRefresh: function(source) { + var me = this, + map = {}, + indices = {}, + items = me.items, + sourceItems = source.items, + filterFn = me.getFilterFn(), + i, item, key, length, newLength; + // Perform a non-destructive filter of the source's items array into the + // *existing* items array because stores give away references to this + // collection's items array. + if (me.filtered && me.getAutoFilter()) { + for (i = 0 , newLength = 0 , length = sourceItems.length; i < length; i++) { + if (filterFn(sourceItems[i])) { + items[newLength++] = sourceItems[i]; + } + } + items.length = newLength; + } else { + items.length = 0; + items.push.apply(items, sourceItems); + } + if (me.sorted) { + me.sortData(items); + } + me.length = length = items.length; + me.map = map; + me.indices = indices; + for (i = 0; i < length; ++i) { + key = me.getKey(item = items[i]); + map[key] = item; + indices[key] = i; + } + ++me.generation; + me.notify('refresh'); + }, + /** + * This method is called when items are removed from the `source` collection. This is + * equivalent to the `{@link #event-remove remove}` event but is called before the + * `remove` event is fired. + * @param {Ext.util.Collection} source The source collection. + * @param {Object} details The `details` of the `remove` event. + * @private + * @since 5.0.0 + */ + onCollectionRemove: function(source, details) { + this.splice(0, details.items); + }, + /** + * @method onCollectionSort + * This method is called when the `source` collection is sorted. This is equivalent to + * the `{@link #event-sort sort}` event but is called before the `sort` event is fired. + * @param {Ext.util.Collection} source The source collection. + * @private + * @since 5.0.0 + */ + // onCollectionSort: function (source) { + // we ignore sorting of the source collection because we prefer our own order. + // }, + /** + * This method is called when key changes in the `source` collection. This is + * equivalent to the `updatekey` event but is called before the `updatekey` event is + * fired. + * @param {Ext.util.Collection} source The source collection. + * @param {Object} details The `details` of the `updatekey` event. + * @private + * @since 5.0.0 + */ + onCollectionUpdateKey: function(source, details) { + this.updateKey(details.item, details.oldKey, details); + }, + //------------------------------------------------------------------------- + // Private + /** + * @method average + * Averages property values from some or all of the items in this collection. + * + * @param {String} property The name of the property to average from each item. + * @param {Number} [begin] The index of the first item to include in the average. + * @param {Number} [end] The index at which to stop averaging `items`. The item at + * this index will *not* be included in the average. + * @return {Object} The result of averaging the specified property from the indicated + * items. + * @since 5.0.0 + */ + /** + * @method averageByGroup + * See {@link #average}. The result is partitioned by group. + * + * @param {String} property The name of the property to average from each item. + * @return {Object} The result of {@link #average}, partitioned by group. See {@link #aggregateByGroup}. + * @since 5.0.0 + */ + /** + * @method bounds + * Determines the minimum and maximum values for the specified property over some or + * all of the items in this collection. + * + * @param {String} property The name of the property from each item. + * @param {Number} [begin] The index of the first item to include in the bounds. + * @param {Number} [end] The index at which to stop in `items`. The item at this index + * will *not* be included in the bounds. + * @return {Array} An array `[min, max]` with the minimum and maximum of the specified + * property. + * @since 5.0.0 + */ + /** + * @method boundsByGroup + * See {@link #bounds}. The result is partitioned by group. + * + * @param {String} property The name of the property from each item. + * @return {Object} The result of {@link #bounds}, partitioned by group. See {@link #aggregateByGroup}. + * @since 5.0.0 + */ + /** + * @method count + * Determines the number of items in the collection. + * + * @return {Number} The number of items. + * @since 5.0.0 + */ + /** + * @method countByGroup + * See {@link #count}. The result is partitioned by group. + * + * @return {Object} The result of {@link #count}, partitioned by group. See {@link #aggregateByGroup}. + * @since 5.0.0 + */ + /** + * @method extremes + * Finds the items with the minimum and maximum for the specified property over some + * or all of the items in this collection. + * + * @param {String} property The name of the property from each item. + * @param {Number} [begin] The index of the first item to include. + * @param {Number} [end] The index at which to stop in `items`. The item at this index + * will *not* be included. + * @return {Array} An array `[minItem, maxItem]` with the items that have the minimum + * and maximum of the specified property. + * @since 5.0.0 + */ + /** + * @method extremesByGroup + * See {@link #extremes}. The result is partitioned by group. + * + * @param {String} property The name of the property from each item. + * @return {Object} The result of {@link #extremes}, partitioned by group. See {@link #aggregateByGroup}. + * @since 5.0.0 + */ + /** + * @method max + * Determines the maximum value for the specified property over some or all of the + * items in this collection. + * + * @param {String} property The name of the property from each item. + * @param {Number} [begin] The index of the first item to include in the maximum. + * @param {Number} [end] The index at which to stop in `items`. The item at this index + * will *not* be included in the maximum. + * @return {Object} The maximum of the specified property from the indicated items. + * @since 5.0.0 + */ + /** + * @method maxByGroup + * See {@link #max}. The result is partitioned by group. + * + * @param {String} property The name of the property from each item. + * @return {Object} The result of {@link #max}, partitioned by group. See {@link #aggregateByGroup}. + * @since 5.0.0 + */ + /** + * @method maxItem + * Finds the item with the maximum value for the specified property over some or all + * of the items in this collection. + * + * @param {String} property The name of the property from each item. + * @param {Number} [begin] The index of the first item to include in the maximum. + * @param {Number} [end] The index at which to stop in `items`. The item at this index + * will *not* be included in the maximum. + * @return {Object} The item with the maximum of the specified property from the + * indicated items. + * @since 5.0.0 + */ + /** + * @method maxItemByGroup + * See {@link #maxItem}. The result is partitioned by group. + * + * @param {String} property The name of the property from each item. + * @return {Object} The result of {@link #maxItem}, partitioned by group. See {@link #aggregateByGroup}. + * @since 5.0.0 + */ + /** + * @method min + * Determines the minimum value for the specified property over some or all of the + * items in this collection. + * + * @param {String} property The name of the property from each item. + * @param {Number} [begin] The index of the first item to include in the minimum. + * @param {Number} [end] The index at which to stop in `items`. The item at this index + * will *not* be included in the minimum. + * @return {Object} The minimum of the specified property from the indicated items. + * @since 5.0.0 + */ + /** + * @method minByGroup + * See {@link #min}. The result is partitioned by group. + * + * @param {String} property The name of the property from each item. + * @return {Object} The result of {@link #min}, partitioned by group. See {@link #aggregateByGroup}. + * @since 5.0.0 + */ + /** + * @method minItem + * Finds the item with the minimum value for the specified property over some or all + * of the items in this collection. + * + * @param {String} property The name of the property from each item. + * @param {Number} [begin] The index of the first item to include in the minimum. + * @param {Number} [end] The index at which to stop in `items`. The item at this index + * will *not* be included in the minimum. + * @return {Object} The item with the minimum of the specified property from the + * indicated items. + * @since 5.0.0 + */ + /** + * @method minItemByGroup + * See {@link #minItem}. The result is partitioned by group. + * + * @param {String} property The name of the property from each item. + * @return {Object} The result of {@link #minItem}, partitioned by group. See {@link #aggregateByGroup}. + * @since 5.0.0 + */ + /** + * @method sum + * Sums property values from some or all of the items in this collection. + * + * @param {String} property The name of the property to sum from each item. + * @param {Number} [begin] The index of the first item to include in the sum. + * @param {Number} [end] The index at which to stop summing `items`. The item at this + * index will *not* be included in the sum. + * @return {Object} The result of summing the specified property from the indicated + * items. + * @since 5.0.0 + */ + /** + * @method sumByGroup + * See {@link #sum}. The result is partitioned by group. + * + * @param {String} property The name of the property to sum from each item. + * @return {Object} The result of {@link #sum}, partitioned by group. See {@link #aggregateByGroup}. + * @since 5.0.0 + */ + _aggregators: { + average: function(items, begin, end, property, root) { + var n = end - begin; + return n && this._aggregators.sum.call(this, items, begin, end, property, root) / n; + }, + bounds: function(items, begin, end, property, root) { + for (var value, max, min, + i = begin; i < end; ++i) { + value = items[i]; + value = (root ? value[root] : value)[property]; + // First pass max and min are undefined and since nothing is less than + // or greater than undefined we always evaluate these "if" statements as + // true to pick up the first value as both max and min. + if (!(value < max)) { + // jshint ignore:line + max = value; + } + if (!(value > min)) { + // jshint ignore:line + min = value; + } + } + return [ + min, + max + ]; + }, + count: function(items) { + return items.length; + }, + extremes: function(items, begin, end, property, root) { + var most = null, + least = null, + i, item, max, min, value; + for (i = begin; i < end; ++i) { + item = items[i]; + value = (root ? item[root] : item)[property]; + // Same trick as "bounds" + if (!(value < max)) { + // jshint ignore:line + max = value; + most = item; + } + if (!(value > min)) { + // jshint ignore:line + min = value; + least = item; + } + } + return [ + least, + most + ]; + }, + max: function(items, begin, end, property, root) { + var b = this._aggregators.bounds.call(this, items, begin, end, property, root); + return b[1]; + }, + maxItem: function(items, begin, end, property, root) { + var b = this._aggregators.extremes.call(this, items, begin, end, property, root); + return b[1]; + }, + min: function(items, begin, end, property, root) { + var b = this._aggregators.bounds.call(this, items, begin, end, property, root); + return b[0]; + }, + minItem: function(items, begin, end, property, root) { + var b = this._aggregators.extremes.call(this, items, begin, end, property, root); + return b[0]; + }, + sum: function(items, begin, end, property, root) { + for (var value, + sum = 0, + i = begin; i < end; ++i) { + value = items[i]; + value = (root ? value[root] : value)[property]; + sum += value; + } + return sum; + } + }, + _eventToMethodMap: { + add: 'onCollectionAdd', + beforeitemchange: 'onCollectionBeforeItemChange', + beginupdate: 'onCollectionBeginUpdate', + endupdate: 'onCollectionEndUpdate', + itemchange: 'onCollectionItemChange', + filtereditemchange: 'onCollectionFilteredItemChange', + refresh: 'onCollectionRefresh', + remove: 'onCollectionRemove', + beforesort: 'beforeCollectionSort', + sort: 'onCollectionSort', + filter: 'onCollectionFilter', + filteradd: 'onCollectionFilterAdd', + updatekey: 'onCollectionUpdateKey' + }, + /** + * Adds an observing object to this collection. Observers are given first view of all + * events that we may fire. For any event an observer may implement a method whose + * name starts with "onCollection" to receive the event. The `{@link #event-add add}` + * event for example would be passed to `"onCollectionAdd"`. + * + * The only restriction to observers is that they are not allowed to add or remove + * observers from inside these methods. + * + * @param {Ext.util.Collection} observer The observer instance. + * @private + * @since 5.0.0 + */ + addObserver: function(observer) { + var me = this, + observers = me.observers; + if (!observers) { + me.observers = observers = []; + } + if (Ext.Array.contains(observers, observer)) { + Ext.Error.raise('Observer already added'); + } + // if we're in the middle of notifying, we need to clone the observers + if (me.notifying) { + me.observers = observers = observers.slice(0); + } + observers.push(observer); + if (observers.length > 1) { + // Allow observers to be inserted with a priority. + // For example GroupCollections must react to Collection mutation before views. + Ext.Array.sort(observers, me.prioritySortFn); + } + }, + prioritySortFn: function(o1, o2) { + var a = o1.observerPriority || 0, + b = o2.observerPriority || 0; + return a - b; + }, + applyExtraKeys: function(extraKeys, oldExtraKeys) { + var me = this, + ret = oldExtraKeys || {}, + config, name, value; + for (name in extraKeys) { + value = extraKeys[name]; + if (!value.isCollectionKey) { + config = { + collection: me + }; + if (Ext.isString(value)) { + config.property = value; + } else { + config = Ext.apply(config, value); + } + value = new Ext.util.CollectionKey(config); + } else { + value.setCollection(me); + } + ret[name] = me[name] = value; + value.name = name; + } + return ret; + }, + applyGrouper: function(grouper) { + if (grouper) { + grouper = this.getSorters().decodeSorter(grouper, Ext.util.Grouper); + } + return grouper; + }, + /** + * Returns the items array on which to operate. This is called to handle the two + * possible forms used by various methods that accept items: + * + * collection.add(item1, item2, item3); + * collection.add([ item1, item2, item3 ]); + * + * Things get interesting when other arguments are involved: + * + * collection.insert(index, item1, item2, item3); + * collection.insert(index, [ item1, item2, item3 ]); + * + * As well as below because we have to distinguish the one item from from the array: + * + * collection.add(item); + * collection.insert(index, item); + * + * @param {Arguments} args The arguments object from the caller. + * @param {Number} index The index in `args` (the caller's arguments) of `items`. + * @return {Object[]} The array of items on which to operate. + * @private + * @since 5.0.0 + */ + decodeItems: function(args, index) { + var me = this, + ret = (index === undefined) ? args : args[index], + cloned, decoder, i; + if (!ret || !ret.$cloned) { + cloned = args.length > index + 1 || !Ext.isIterable(ret); + if (cloned) { + ret = Ext.Array.slice(args, index); + if (ret.length === 1 && ret[0] === undefined) { + ret.length = 0; + } + } + decoder = me.getDecoder(); + if (decoder) { + if (!cloned) { + ret = ret.slice(0); + cloned = true; + } + for (i = ret.length; i-- > 0; ) { + if ((ret[i] = decoder.call(me, ret[i])) === false) { + ret.splice(i, 1); + } + } + } + if (cloned) { + ret.$cloned = true; + } + } + return ret; + }, + /** + * Returns the map of key to index for all items in this collection. This method will + * lazily populate this map on request. This map is maintained when doing so does not + * involve too much overhead. When this threshold is cross, the index map is discarded + * and must be rebuilt by calling this method. + * + * @return {Object} + * @private + * @since 5.0.0 + */ + getIndices: function() { + var me = this, + indices = me.indices, + items = me.items, + n = items.length, + i, key; + if (!indices) { + me.indices = indices = {}; + ++me.indexRebuilds; + for (i = 0; i < n; ++i) { + key = me.getKey(items[i]); + indices[key] = i; + } + } + return indices; + }, + /** + * This method wraps all fired events and gives observers first view of the change. + * + * @param {String} eventName The name of the event to fire. + * @param {Array} [args] The event arguments. This collection instance is inserted at + * the front of this array if there is any receiver for the notification. + * + * @private + * @since 5.0.0 + */ + notify: function(eventName, args) { + var me = this, + observers = me.observers, + methodName = me._eventToMethodMap[eventName], + added = 0, + index, length, method, observer; + args = args || []; + if (observers && methodName) { + me.notifying = true; + for (index = 0 , length = observers.length; index < length; ++index) { + method = (observer = observers[index])[methodName]; + if (method) { + if (!added++) { + // jshint ignore:line + args.unshift(me); + } + // put this Collection as the first argument + method.apply(observer, args); + } + } + me.notifying = false; + } + // During construction, no need to fire an event here + if (!me.hasListeners) { + return; + } + if (me.hasListeners[eventName]) { + if (!added) { + args.unshift(me); + } + // put this Collection as the first argument + me.fireEventArgs(eventName, args); + } + }, + /** + * Returns the filter function. + * @return {Function} sortFn The sort function. + */ + getFilterFn: function() { + return this.getFilters().getFilterFn(); + }, + /** + * Returns the `Ext.util.FilterCollection`. Unless `autoCreate` is explicitly passed + * as `false` this collection will be automatically created if it does not yet exist. + * @param [autoCreate=true] Pass `false` to disable auto-creation of the collection. + * @return {Ext.util.FilterCollection} The collection of filters. + */ + getFilters: function(autoCreate) { + var ret = this._filters; + if (!ret && autoCreate !== false) { + ret = new Ext.util.FilterCollection(); + this.setFilters(ret); + } + return ret; + }, + /** + * This method can be used to conveniently test whether an individual item would be + * removed due to the current filter. + * @param {Object} item The item to test. + * @return {Boolean} The value `true` if the item would be "removed" from the + * collection due to filters or `false` otherwise. + */ + isItemFiltered: function(item) { + return !this.getFilters().filterFn(item); + }, + /** + * Called after a change of the filter is complete. + * + * For example: + * + * onFilterChange: function (filters) { + * if (this.filtered) { + * // process filters + * } else { + * // no filters present + * } + * } + * + * @template + * @method + * @param {Ext.util.FilterCollection} filters The filters collection. + */ + onFilterChange: function(filters) { + var me = this, + source = me.getSource(), + extraKeys, newKeys, key; + if (!source) { + // In this method, we have changed the filter but since we don't start with + // any and we create the source collection as needed that means we are getting + // our first filter. + extraKeys = me.getExtraKeys(); + if (extraKeys) { + newKeys = {}; + for (key in extraKeys) { + newKeys[key] = extraKeys[key].clone(me); + } + } + source = new Ext.util.Collection({ + keyFn: me.getKey, + extraKeys: newKeys, + rootProperty: me.getRootProperty() + }); + if (me.length) { + source.add(me.items); + } + me.setSource(source); + me.autoSource = source; + } else { + if (source.destroyed) { + return; + } + if (source.length || me.length) { + // if both us and the source are empty then we can skip this + me.onCollectionRefresh(source); + } + } + me.notify('filter'); + }, + //------------------------------------------------------------------------- + // Private + applyFilters: function(filters, collection) { + if (!filters || filters.isFilterCollection) { + return filters; + } + if (filters) { + if (!collection) { + collection = this.getFilters(); + } + collection.splice(0, collection.length, filters); + } + return collection; + }, + updateFilters: function(newFilters, oldFilters) { + var me = this; + if (oldFilters) { + // Do not disconnect from owning Filterable because + // default options (eg _rootProperty) are read from there. + // FilterCollections are detached from the Collection when the owning Store is remoteFilter: true + // or the owning store is a TreeStore and only filters new nodes before filling a parent node. + oldFilters.un('endupdate', 'onEndUpdateFilters', me); + } + if (newFilters) { + newFilters.on({ + endupdate: 'onEndUpdateFilters', + scope: me, + priority: me.$endUpdatePriority + }); + newFilters.$filterable = me; + } + me.onEndUpdateFilters(newFilters); + }, + onEndUpdateFilters: function(filters) { + var me = this, + was = me.filtered, + is = !!filters && (filters.getFilterCount() > 0); + // booleanize filters + if (was || is) { + me.filtered = is; + me.onFilterChange(filters); + } + }, + /** + * Returns an up to date sort function. + * @return {Function} The sort function. + */ + getSortFn: function() { + return this._sortFn || this.createSortFn(); + }, + /** + * Returns the `Ext.util.SorterCollection`. Unless `autoCreate` is explicitly passed + * as `false` this collection will be automatically created if it does not yet exist. + * @param [autoCreate=true] Pass `false` to disable auto-creation of the collection. + * @return {Ext.util.SorterCollection} The collection of sorters. + */ + getSorters: function(autoCreate) { + var ret = this._sorters; + if (!ret && autoCreate !== false) { + ret = new Ext.util.SorterCollection(); + this.setSorters(ret); + } + return ret; + }, + /** + * Called after a change of the sort is complete. + * + * For example: + * + * onSortChange: function (sorters) { + * if (this.sorted) { + * // process sorters + * } else { + * // no sorters present + * } + * } + * + * @template + * @method + * @param {Ext.util.SorterCollection} sorters The sorters collection. + */ + onSortChange: function() { + if (this.sorted) { + this.sortItems(); + } + }, + /** + * Updates the sorters collection and triggers sorting of this Sortable. + * + * For example: + * + * //sort by a single field + * myStore.sort('myField', 'DESC'); + * + * //sorting by multiple fields + * myStore.sort([{ + * property : 'age', + * direction: 'ASC' + * }, { + * property : 'name', + * direction: 'DESC' + * }]); + * + * When passing a single string argument to sort, the `direction` is maintained for + * each field and is toggled automatically. So this code: + * + * store.sort('myField'); + * store.sort('myField'); + * + * Is equivalent to the following: + * + * store.sort('myField', 'ASC'); + * store.sort('myField', 'DESC'); + * + * @param {String/Function/Ext.util.Sorter[]} [property] Either the name of a property + * (such as a field of a `Ext.data.Model` in a `Store`), an array of configurations + * for `Ext.util.Sorter` instances or just a comparison function. + * @param {String} [direction] The direction by which to sort the data. This parameter + * is only valid when `property` is a String, otherwise the second parameter is the + * `mode`. + * @param {String} [mode="replace"] Where to put new sorters in the collection. This + * should be one the following values: + * + * * `**replace**` : The new sorter(s) become the sole sorter set for this Sortable. + * This is the most useful call mode to programmatically sort by multiple fields. + * + * * `**prepend**` : The new sorters are inserted as the primary sorters. The sorter + * collection length must be controlled by the developer. + * + * * `**multi**` : Similar to `**prepend**` the new sorters are inserted at the front + * of the collection of sorters. Following the insertion, however, this mode trims + * the sorter collection to enforce the `multiSortLimit` config. This is useful for + * implementing intuitive "Sort by this" user interfaces. + * + * * `**append**` : The new sorters are added at the end of the collection. + * @return {Ext.util.Collection} This instance. + */ + sort: function(property, direction, mode) { + var sorters = this.getSorters(); + sorters.addSort.apply(sorters, arguments); + return this; + }, + /** + * This method will sort an array based on the currently configured {@link #sorters}. + * @param {Array} data The array you want to have sorted. + * @return {Array} The array you passed after it is sorted. + */ + sortData: function(data) { + Ext.Array.sort(data, this.getSortFn()); + return data; + }, + /** + * Sorts the items of the collection using the supplied function. This should only be + * called for collections that have no `sorters` defined. + * @param {Function} sortFn The function by which to sort the items. + * @since 5.0.0 + */ + sortItems: function(sortFn) { + var me = this; + if (me.sorted) { + if (sortFn) { + Ext.raise('Collections with sorters cannot resorted'); + } + sortFn = me.getSortFn(); + } + me.indices = null; + me.notify('beforesort', [ + me.getSorters(false) + ]); + if (me.length) { + Ext.Array.sort(me.items, sortFn); + } + // Even if there's no data, notify interested parties. + // Eg: Stores must react and fire their refresh and sort events. + me.notify('sort'); + }, + /** + * Sorts the collection by a single sorter function + * @param {Function} sortFn The function to sort by + * @deprecated 6.5.0 This method is deprecated. + */ + sortBy: function(sortFn) { + return this.sortItems(sortFn); + }, + /** + * @private + * Can be called to find the insertion index of a passed object in this collection. + * Or can be passed an items array to search in, and may be passed a comparator + */ + findInsertionIndex: function(item, items, comparatorFn, index) { + return Ext.Array.findInsertionIndex(item, items || this.items, comparatorFn || this.getSortFn(), index); + }, + applySorters: function(sorters, collection) { + if (!sorters || sorters.isSorterCollection) { + return sorters; + } + if (sorters) { + if (!collection) { + collection = this.getSorters(); + } + collection.splice(0, collection.length, sorters); + } + return collection; + }, + createSortFn: function() { + var me = this, + grouper = me.getGrouper(), + sorters = me.getSorters(false), + sorterFn = sorters ? sorters.getSortFn() : null; + if (!grouper) { + return sorterFn; + } + return function(lhs, rhs) { + var ret = grouper.sort(lhs, rhs); + if (!ret && sorterFn) { + ret = sorterFn(lhs, rhs); + } + return ret; + }; + }, + updateGrouper: function(grouper) { + var me = this, + groups = me.getGroups(), + sorters = me.getSorters(), + populate; + me.onSorterChange(); + me.grouped = !!grouper; + if (grouper) { + if (me.getTrackGroups()) { + if (!groups) { + groups = new Ext.util.GroupCollection({ + itemRoot: me.getRootProperty(), + groupConfig: me.getGroupConfig() + }); + groups.$groupable = me; + me.setGroups(groups); + } + groups.setGrouper(grouper); + populate = true; + } + } else { + if (groups) { + me.removeObserver(groups); + groups.destroy(); + } + me.setGroups(null); + } + if (!sorters.updating) { + me.onEndUpdateSorters(sorters); + } + if (populate) { + groups.onCollectionRefresh(me); + } + }, + updateSorters: function(newSorters, oldSorters) { + var me = this; + if (oldSorters && !oldSorters.destroyed) { + // Do not disconnect from owning Filterable because + // default options (eg _rootProperty) are read from there. + // SorterCollections are detached from the Collection when the owning Store is remoteSort: true + // or the owning store is a TreeStore and only sorts new nodes before filling a parent node. + oldSorters.un('endupdate', 'onEndUpdateSorters', me); + } + if (newSorters) { + newSorters.on({ + endupdate: 'onEndUpdateSorters', + scope: me, + priority: me.$endUpdatePriority + }); + if (me.manageSorters) { + newSorters.$sortable = me; + } + } + me.onSorterChange(); + me.onEndUpdateSorters(newSorters); + }, + onSorterChange: function() { + this._sortFn = null; + }, + onEndUpdateSorters: function(sorters) { + var me = this, + was = me.sorted, + is = (me.grouped && me.getAutoGroup()) || (sorters && sorters.length > 0); + if (was || is) { + // ensure flag property is a boolean. + // sorters && (sorters.length > 0) may evaluate to null + me.sorted = !!is; + me.onSortChange(sorters); + } + }, + /** + * Removes an observing object to this collection. See `addObserver` for details. + * + * @param {Ext.util.Collection} observer The observer instance. + * @private + * @since 5.0.0 + */ + removeObserver: function(observer) { + var observers = this.observers; + if (observers) { + Ext.Array.remove(observers, observer); + } + }, + /** + * This method is what you might find in the core of a merge sort. We have an items + * array that is sorted so we sort the newItems and merge the two sorted arrays. In + * the general case, newItems will be no larger than all items so sorting it will be + * faster than simply concatenating the arrays and calling sort on it. + * + * We take advantage of the nature of this process to generate add events as ranges. + * + * @param {Object[]} newItems + * @param {Object[]} newKeys + * @private + * @since 5.0.0 + */ + spliceMerge: function(newItems, newKeys) { + var me = this, + map = me.map, + newLength = newItems.length, + oldIndex = 0, + oldItems = me.items, + oldLength = oldItems.length, + adds = [], + count = 0, + items = [], + sortFn = me.getSortFn(), + // account for grouper and sorter(s) + addItems, end, i, newItem, oldItem, newIndex; + me.items = items; + // + // oldItems + // +----+----+----+----+ + // | 15 | 25 | 35 | 45 | + // +----+----+----+----+ + // 0 1 2 3 + // + // newItems + // +----+----+----+----+----+----+ + // | 10 | 11 | 20 | 21 | 50 | 51 | + // +----+----+----+----+----+----+ + // 0 1 2 3 4 5 + // + for (newIndex = 0; newIndex < newLength; newIndex = end) { + newItem = newItems[newIndex]; + // Flush out any oldItems that are <= newItem + for (; oldIndex < oldLength; ++oldIndex) { + // Consider above arrays... + // at newIndex == 0 this loop sets oldItem but breaks immediately + // at newIndex == 2 this loop pushes 15 and breaks w/oldIndex=1 + // at newIndex == 4 this loop pushes 25, 35 and 45 and breaks w/oldIndex=4 + if (sortFn(newItem, oldItem = oldItems[oldIndex]) < 0) { + break; + } + items.push(oldItem); + } + if (oldIndex === oldLength) { + // Consider above arrays... + // at newIndex == 0 we won't come in here (oldIndex == 0) + // at newIndex == 2 we won't come in here (oldIndex == 1) + // at newIndex == 4 we come here (oldIndex == 4), push 50 & 51 and break + adds[count++] = { + at: items.length, + itemAt: items[items.length - 1], + items: (addItems = []) + }; + if (count > 1) { + adds[count - 2].next = adds[count - 1]; + } + for (; newIndex < newLength; ++newIndex) { + addItems.push(newItem = newItems[newIndex]); + items.push(newItem); + } + break; + } + // else oldItem is the item from oldItems that is > newItem + // Consider above arrays... + // at newIndex == 0 we will push 10 + // at newIndex == 2 we will push 20 + adds[count++] = { + at: items.length, + itemAt: items[items.length - 1], + items: (addItems = [ + newItem + ]) + }; + if (count > 1) { + adds[count - 2].next = adds[count - 1]; + } + items.push(newItem); + for (end = newIndex + 1; end < newLength; ++end) { + // Consider above arrays... + // at newIndex == 0 this loop pushes 11 then breaks w/end == 2 + // at newIndex == 2 this loop pushes 21 the breaks w/end == 4 + if (sortFn(newItem = newItems[end], oldItem) >= 0) { + break; + } + items.push(newItem); + addItems.push(newItem); + } + } + // if oldItems had 55 as its final element, the above loop would have pushed + // all of newItems so the outer for loop would then fall out + for (; oldIndex < oldLength; ++oldIndex) { + // In the above example, we won't come in here, but if you imagine a 55 in + // oldItems we would have oldIndex == 4 and oldLength == 5 + items.push(oldItems[oldIndex]); + } + for (i = 0; i < newLength; ++i) { + map[newKeys[i]] = newItems[i]; + } + me.length = items.length; + ++me.generation; + me.indices = null; + // Tell users of the adds in increasing index order. + for (i = 0; i < count; ++i) { + me.notify('add', [ + adds[i] + ]); + } + }, + getGroups: function() { + return this.callParent() || null; + }, + updateAutoGroup: function(autoGroup) { + var groups = this.getGroups(); + if (groups) { + groups.setAutoGroup(autoGroup); + } + // Important to call this so it can clear the .sorted flag + // as needed + this.onEndUpdateSorters(this._sorters); + }, + updateGroups: function(newGroups, oldGroups) { + if (oldGroups) { + this.removeObserver(oldGroups); + } + if (newGroups) { + this.addObserver(newGroups); + } + }, + updateSource: function(newSource, oldSource) { + var auto = this.autoSource; + if (oldSource) { + if (!oldSource.destroyed) { + oldSource.removeObserver(this); + } + if (oldSource === auto) { + auto.destroy(); + this.autoSource = null; + } + } + if (newSource) { + newSource.addObserver(this); + if (newSource.length || this.length) { + this.onCollectionRefresh(newSource); + } + } + } +}, function() { + var prototype = this.prototype; + // Minor compat method + prototype.removeAtKey = prototype.removeByKey; + /** + * This method is an alias for `decodeItems` but is called when items are being + * removed. If a `decoder` is provided it may be necessary to also override this + * method to achieve symmetry between adding and removing items. This is the case + * for `Ext.util.FilterCollection' and `Ext.util.SorterCollection' for example. + * + * @method decodeRemoveItems + * @protected + * @since 5.0.0 + */ + prototype.decodeRemoveItems = prototype.decodeItems; + Ext.Object.each(prototype._aggregators, function(name) { + prototype[name] = function(property, begin, end) { + return this.aggregate(property, name, begin, end); + }; + prototype[name + 'ByGroup'] = function(property) { + return this.aggregateByGroup(property, name); + }; + }); +}); + +/** + * This class provides access to a range of records in a {@link Ext.data.Store store}. + * Instances of this class are not created directly but are rather returned by a store's + * {@link Ext.data.AbstractStore#createActiveRange createActiveRange} method. + * + * This class is useful for buffered rendering where only a portion of the total set of + * records are needed. By passing that information to a `Range`, the access to records + * can be abstracted even across {@link Ext.data.virtual.Store virtual stores} where + * only those records needed by views are fetched from the server. + * @since 6.5.0 + */ +Ext.define('Ext.data.Range', { + requires: [ + 'Ext.util.DelayedTask' + ], + isDataRange: true, + /** + * @cfg {Number} begin + * The first record index of interest. + * + * This property is set by the `goto` method and is stored on the instance for + * readonly use. + * @readonly + */ + begin: 0, + /** + * @cfg {Number} buffer + * The buffer to execute server requests. + */ + buffer: 0, + /** + * @cfg {Number} end + * The first record beyond the range of interest. This is to make "length" of the + * range simply `end - begin`. + * + * This property is set by the `goto` method and is stored on the instance for + * readonly use. + */ + end: 0, + /** + * @property (Number} length + * The number of records in the range of `[begin, end)`. This is equal to the + * difference `end - begin`. + * + * This property is maintained by the `goto` method and is stored on the instance for + * readonly use. + * @readonly + */ + length: 0, + /** + * @property {Ext.data.Model[]} records + * The records corresponding to the `begin` and `end` of this range. For normal + * stores this is the standard array of records. + * + * For a {@link Ext.data.virtual.Store virtual store} this is a sparse object of + * available records bounded by the limits of this range. + * + * In all cases, this object is keyed by the record index and (except for the + * `length` property) should be treated as an array. + * @readonly + */ + /** + * @cfg {Ext.data.AbstractStore} store + * The associated store. This config must be supplied at construction and cannot + * be changed after that time. + * @readonly + */ + store: null, + constructor: function(config) { + var me = this, + activeRanges, store; + Ext.apply(me, config); + store = me.store; + if (!(activeRanges = store.activeRanges)) { + store.activeRanges = activeRanges = []; + } + activeRanges.push(me); + me.refresh(); + if ('begin' in config) { + me.begin = me.end = 0; + // Applied on us above, so clear it + me.goto(config.begin, config.end); + } + }, + destroy: function() { + var me = this, + store = me.store, + activeRanges = store && store.activeRanges; + Ext.destroy(me.storeListeners); + if (activeRanges) { + Ext.Array.remove(activeRanges, me); + } + me.callParent(); + }, + "goto": function(begin, end) { + var me = this, + buffer = me.buffer, + task = me.task; + me.begin = begin; + me.end = end; + me.length = end - begin; + if (buffer > 0) { + if (!task) { + me.task = task = new Ext.util.DelayedTask(me.doGoto, me); + } + task.delay(buffer); + } else { + me.doGoto(); + } + }, + privates: { + lastBegin: 0, + lastEnd: 0, + doGoto: Ext.privateFn, + refresh: function() { + this.records = this.store.getData().items; + } + } +}); + +/** + * This class accepts an object that serves as a template for creating new objects. Like + * other templates (`Ext.XTemplate`) this creation step requires a context object to give + * the template its values. + * + * For example: + * + * var tpl = new Ext.util.ObjectTemplate({ + * property: 'Hello {name}', + * data: { + * value: '{age}' + * } + * }); + * + * var obj = tpl.apply({ + * name: 'Bill', + * age: 42 + * }); + * + * // obj = { + * // property: 'Hello Bill', + * // data: { + * // value: 42 + * // } + * // } + * + * @since 5.0.0 + */ +Ext.define('Ext.util.ObjectTemplate', { + requires: [ + 'Ext.XTemplate' + ], + isObjectTemplate: true, + excludeProperties: {}, + valueRe: /^[{][a-z\.]+[}]$/i, + statics: { + /** + * Creates an `ObjectTemplate` given a config object or instance. + * @param {Object/Ext.util.ObjectTemplate} template The template object. + * @param {Object} [options] + * @return {Ext.util.ObjectTemplate} + * @since 5.0.0 + */ + create: function(template, options) { + if (!Ext.isObject(template)) { + Ext.raise('The template is not an Object'); + } + return template.isObjectTemplate ? template : new Ext.util.ObjectTemplate(template, options); + } + }, + /** + * Constructs the `ObjectTemplate`. The actual compilation of the object to a ready to + * apply form happens on the first call to `apply`. + * @param {Object} template + * @param {Object} [options] + * @since 5.0.0 + */ + constructor: function(template, options) { + Ext.apply(this, options); + this.template = template; + }, + /** + * Applies the given `context` object to this template and returns a new object with + * the appropriate pieces replaced. + * @param {Object} context The data used to populate the template. + * @return {Object} + * @since 5.0.0 + */ + apply: function(context) { + var me = this; + delete me.apply; + me.apply = me.compile(me.template); + return me.apply(context); + }, + privates: { + /** + * Compiles the given template into an `apply` method that is ready to run. This + * method is used recursively to process object properties and array elements. + * @param {Mixed} template + * @return {Function} + * @since 5.0.0 + */ + compile: function(template) { + var me = this, + exclude = me.excludeProperties, + compiled, i, len, fn; + // TODO: loops over array or objects + if (Ext.isString(template)) { + if (template.indexOf('{') < 0) { + fn = function() { + return template; + }; + } else if (me.valueRe.test(template)) { + template = template.substring(1, template.length - 1).split('.'); + fn = function(context) { + for (var v = context, + i = 0; v && i < template.length; ++i) { + v = v[template[i]]; + } + return v; + }; + } else { + template = new Ext.XTemplate(template); + fn = function(context) { + return template.apply(context); + }; + } + } else if (!template || Ext.isPrimitive(template) || Ext.isFunction(template)) { + fn = function() { + return template; + }; + } else if (template instanceof Array) { + compiled = []; + for (i = 0 , len = template.length; i < len; ++i) { + compiled[i] = me.compile(template[i]); + } + fn = function(context) { + var ret = [], + i; + for (i = 0; i < len; ++i) { + ret[i] = compiled[i](context); + } + return ret; + }; + } else { + compiled = {}; + for (i in template) { + if (!exclude[i]) { + compiled[i] = me.compile(template[i]); + } + } + fn = function(context) { + var ret = {}, + i, v; + for (i in template) { + v = exclude[i] ? template[i] : compiled[i](context); + if (v !== undefined) { + ret[i] = v; + } + } + return ret; + }; + } + return fn; + } + } +}); + +/** + * @private + */ +Ext.define('Ext.data.schema.Role', { + /** + * @property {Ext.data.schema.Association} association + * @readonly + */ + isRole: true, + /** + * @property {Boolean} left + * @readonly + */ + left: true, + /** + * @property {Boolean} owner + * @readonly + */ + owner: false, + /** + * @property {String} side + * @readonly + */ + side: 'left', + /** + * @property {Boolean} isMany + * @readonly + */ + isMany: false, + /** + * @property {Ext.Class} cls + * The `Ext.data.Model` derived class. + * @readonly + */ + /** + * @property {Ext.data.schema.Role} inverse + * @readonly + */ + /** + * @property {String} type + * The `{@link Ext.data.Model#entityName}` derived class. + * @readonly + */ + /** + * @property {String} role + * @readonly + */ + defaultReaderType: 'json', + _internalReadOptions: { + recordsOnly: true, + asRoot: true + }, + constructor: function(association, config) { + var me = this, + extra = config.extra; + Ext.apply(me, config); + if (extra) { + extra = Ext.apply({}, extra); + delete extra.type; + Ext.apply(me, extra); + delete me.extra; + } + me.association = association; + // The Association's owner property starts as either "left" or "right" (a string) + // and we promote it to a reference to the appropriate Role instance here. + if (association.owner === me.side) { + association.owner = me; + me.owner = true; + } + }, + processUpdate: function() { + Ext.raise('Only the "many" for an association may be processed. "' + this.role + '" is not valid.'); + }, + /** + * Exclude any locally modified records that don't belong in the store. Include locally + * modified records that should be in the store. Also correct any foreign keys that + * need to be updated. + * + * @param {Ext.data.Store} store The store. + * @param {Ext.data.Model} associatedEntity The entity that owns the records. + * @param {Ext.data.Model[]} records The records to check. + * @param {Ext.data.Session} session The session holding the records + * @return {Ext.data.Model[]} The corrected set of records. + * + * @private + */ + processLoad: function(store, associatedEntity, records, session) { + return records; + }, + /** + * @method + * + * Check whether a record belongs to any stores when it is added to the session. + * + * @param {Ext.data.Session} session The session + * @param {Ext.data.Model} record The model being added to the session + * @private + */ + checkMembership: Ext.emptyFn, + /** + * Adopt the associated items when a record is adopted. + * @param {Ext.data.Model} record The record being adopted. + * @param {Ext.data.Session} session The session being adopted into + * + * @private + */ + adoptAssociated: function(record, session) { + var other = this.getAssociatedItem(record); + if (other) { + session.adopt(other); + } + }, + $roleFilterId: '$associationRoleFilter', + createAssociationStore: function(session, from, records, isComplete) { + var me = this, + association = me.association, + foreignKeyName = association.getFieldName(), + isMany = association.isManyToMany, + storeConfig = me.storeConfig, + id = from.getId(), + config = { + // Always want immediate load + asynchronousLoad: false, + model: me.cls, + role: me, + session: session, + associatedEntity: from, + disableMetaChangeEvent: true, + pageSize: null, + remoteFilter: true, + trackRemoved: !session + }, + store; + if (isMany) { + // For many-to-many associations each role has a field + config.filters = [ + { + id: me.$roleFilterId, + property: me.inverse.field, + // @TODO filterProperty + value: id, + exactMatch: true + } + ]; + } else if (foreignKeyName) { + config.filters = [ + { + id: me.$roleFilterId, + property: foreignKeyName, + // @TODO filterProperty + value: id, + exactMatch: true + } + ]; + config.foreignKeyName = foreignKeyName; + } + if (storeConfig) { + Ext.apply(config, storeConfig); + } + store = Ext.Factory.store(config); + me.onStoreCreate(store, session, id); + // Want to run these in all cases for M-1, only with a session M-M + if (!isMany || session) { + store.on({ + scope: me, + add: 'onAddToMany', + remove: 'onRemoveFromMany', + clear: 'onRemoveFromMany' + }); + } + if (records) { + store.loadData(records); + } + store.complete = !!isComplete; + return store; + }, + onStoreCreate: Ext.emptyFn, + getAssociatedStore: function(inverseRecord, options, scope, records, allowInfer) { + // Consider the Comment entity with a ticketId to a Ticket entity. The Comment + // is on the left (the FK holder's side) so we are implementing the guts of + // the comments() method to load the Store of Comment entities. This trek + // begins from a Ticket (inverseRecord). + var me = this, + storeName = me.getStoreName(), + store = inverseRecord[storeName], + hadStore = store, + session = inverseRecord.session, + load = options && options.reload, + source = inverseRecord.$source, + isComplete = false, + phantom = false, + hadSourceStore, args, i, len, raw, rec, sourceStore, hadRecords, isLoading; + if (!store) { + if (session) { + // We want to check whether we can automatically get the store contents from the parent session. + // For this to occur, we need to have a parent in the session, and the store needs to be created + // and loaded with the initial dataset. + if (source) { + phantom = source.phantom; + } + if (!records && source) { + sourceStore = source[storeName]; + if (sourceStore && !sourceStore.isLoading()) { + records = []; + raw = sourceStore.getData().items; + for (i = 0 , len = raw.length; i < len; ++i) { + rec = raw[i]; + records.push(session.getRecord(rec.self, rec.id)); + } + isComplete = !!sourceStore.complete; + hadSourceStore = true; + } + } + if (!hadSourceStore) { + // We'll only hit here if we didn't have a usable source + hadRecords = !!records; + records = me.findRecords(session, inverseRecord, records, allowInfer); + if (!hadRecords && (!records || !records.length)) { + records = null; + } + isComplete = phantom || hadRecords; + } + } else { + // As long as we had the collection exist, we're complete, even if it's empty. + isComplete = !!records; + } + // If the inverse is a phantom, we can't be loading any data so we're complete + store = me.createAssociationStore(session, inverseRecord, records, isComplete || inverseRecord.phantom); + store.$source = sourceStore; + if (!records && (me.autoLoad || options)) { + load = true; + } + inverseRecord[storeName] = store; + } + if (options) { + // We need to trigger a load or the store is already loading. Defer + // callbacks until that happens + if (load || store.isLoading()) { + store.on('load', function(store, records, success, operation) { + args = [ + store, + operation + ]; + scope = scope || options.scope || inverseRecord; + if (success) { + Ext.callback(options.success, scope, args); + } else { + Ext.callback(options.failure, scope, args); + } + args.push(success); + Ext.callback(options, scope, args); + Ext.callback(options.callback, scope, args); + }, null, { + single: true + }); + } else { + // Trigger straight away + args = [ + store, + null + ]; + scope = scope || options.scope || inverseRecord; + Ext.callback(options.success, scope, args); + args.push(true); + Ext.callback(options, scope, args); + Ext.callback(options.callback, scope, args); + } + } + isLoading = store.isLoading(); + if (load) { + if (!isLoading) { + store.load(); + } + } else if (hadStore && records && !isLoading) { + store.loadData(records); + } + return store; + }, + /** + * Gets the store/record associated with this role from an existing record. + * Will only return if the value is loaded. + * + * @param {Ext.data.Model} rec The record + * + * @return {Ext.data.Model/Ext.data.Store} The associated item. `null` if not loaded. + * @private + */ + getAssociatedItem: function(rec) { + var key = this.isMany ? this.getStoreName() : this.getInstanceName(); + return rec[key] || null; + }, + onDrop: Ext.emptyFn, + onIdChanged: Ext.emptyFn, + getReaderRoot: function() { + var me = this; + return me.associationKey || (me.associationKey = me.association.schema.getNamer().readerRoot(me.role)); + }, + getReader: function() { + var me = this, + reader = me.reader, + Model = me.cls, + useSimpleAccessors = !me.associationKey, + root = this.getReaderRoot(); + if (reader && !reader.isReader) { + if (Ext.isString(reader)) { + reader = { + type: reader + }; + } + Ext.applyIf(reader, { + model: Model, + rootProperty: root, + useSimpleAccessors: useSimpleAccessors, + type: me.defaultReaderType + }); + reader = me.reader = Ext.createByAlias('reader.' + reader.type, reader); + } + return reader; + }, + getInstanceName: function() { + var me = this; + return me.instanceName || (me.instanceName = me.association.schema.getNamer().instanceName(me.role)); + }, + getOldInstanceName: function() { + return this.oldInstanceName || (this.oldInstanceName = '$old' + this.getInstanceName()); + }, + getStoreName: function() { + var me = this; + return me.storeName || (me.storeName = me.association.schema.getNamer().storeName(me.role)); + }, + constructReader: function(fromReader) { + var me = this, + reader = me.getReader(), + Model = me.cls, + useSimpleAccessors = !me.associationKey, + root = me.getReaderRoot(), + proxyReader, proxy; + // No reader supplied + if (!reader) { + proxy = Model.getProxy(); + // if the associated model has a Reader already, use that, otherwise attempt to create a sensible one + if (proxy) { + proxyReader = proxy.getReader(); + reader = new proxyReader.self(); + reader.copyFrom(proxyReader); + reader.setRootProperty(root); + } else { + reader = new fromReader.self({ + model: Model, + useSimpleAccessors: useSimpleAccessors, + rootProperty: root + }); + } + me.reader = reader; + } + return reader; + }, + read: function(record, data, fromReader, readOptions) { + var reader = this.constructReader(fromReader), + root = reader.getRoot(data); + if (root) { + return reader.readRecords(root, readOptions, this._internalReadOptions); + } + }, + getCallbackOptions: function(options, scope, defaultScope) { + if (typeof options === 'function') { + options = { + callback: options, + scope: scope || defaultScope + }; + } else if (options) { + options = Ext.apply({}, options); + options.scope = scope || options.scope || defaultScope; + } + return options; + }, + doGetFK: function(leftRecord, options, scope) { + // Consider the Department entity with a managerId to a User entity. This method + // is the guts of the getManager method that we place on the Department entity to + // acquire a User entity. We are the "manager" role and that role describes a + // User. This method is called, however, given a Department (leftRecord) as the + // start of this trek. + var me = this, + // the "manager" role + cls = me.cls, + // User + foreignKey = me.association.getFieldName(), + // "managerId" + instanceName = me.getInstanceName(), + // "manager" + rightRecord = leftRecord[instanceName], + // = department.manager + reload = options && options.reload, + done = rightRecord !== undefined && !reload, + session = leftRecord.session, + foreignKeyId, args; + if (!done) { + // We don't have the User record yet, so try to get it. + if (session) { + foreignKeyId = leftRecord.get(foreignKey); + if (foreignKeyId || foreignKeyId === 0) { + done = session.peekRecord(cls, foreignKeyId, true) && !reload; + rightRecord = session.getRecord(cls, foreignKeyId, false); + } else { + done = true; + leftRecord[instanceName] = rightRecord = null; + } + } else if (foreignKey) { + // The good news is that we do indeed have a FK so we can do a load using + // the value of the FK. + foreignKeyId = leftRecord.get(foreignKey); + if (!foreignKeyId && foreignKeyId !== 0) { + // A value of null ends that hope though... but we still need to do + // some callbacks perhaps. + done = true; + leftRecord[instanceName] = rightRecord = null; + } else { + // foreignKeyId is the managerId from the Department (record), so + // make a new User, set its idProperty and load the real record via + // User.load method. + if (!rightRecord) { + // We may be reloading, let's check if we have one. + rightRecord = cls.createWithId(foreignKeyId); + } + } + } else // we are not done in this case, so don't set "done" + { + // Without a FK value by which to request the User record, we cannot do + // anything. Declare victory and get out. + done = true; + rightRecord = null; + } + } else if (rightRecord) { + // If we're still loading, call load again which will handle the extra callbacks. + done = !rightRecord.isLoading(); + } + if (done) { + if (options) { + args = [ + rightRecord, + null + ]; + scope = scope || options.scope || leftRecord; + Ext.callback(options.success, scope, args); + args.push(true); + Ext.callback(options, scope, args); + Ext.callback(options.callback, scope, args); + } + } else { + leftRecord[instanceName] = rightRecord; + options = me.getCallbackOptions(options, scope, leftRecord); + rightRecord.load(options); + } + return rightRecord; + }, + doSetFK: function(leftRecord, rightRecord, options, scope) { + // Consider the Department entity with a managerId to a User entity. This method + // is the guts of the setManager method that we place on the Department entity to + // store the User entity. We are the "manager" role and that role describes a + // User. This method is called, however, given a Department (record) and the User + // (value). + var me = this, + foreignKey = me.association.getFieldName(), + // "managerId" + instanceName = me.getInstanceName(), + // "manager" + current = leftRecord[instanceName], + inverse = me.inverse, + inverseSetter = inverse.setterName, + // setManagerDepartment for User + session = leftRecord.session, + modified, oldInstanceName; + if (rightRecord && rightRecord.isEntity) { + if (current !== rightRecord) { + oldInstanceName = me.getOldInstanceName(); + leftRecord[oldInstanceName] = current; + leftRecord[instanceName] = rightRecord; + if (current && current.isEntity) { + current[inverse.getInstanceName()] = undefined; + } + if (foreignKey) { + leftRecord.set(foreignKey, rightRecord.getId()); + } + delete leftRecord[oldInstanceName]; + leftRecord.onAssociatedRecordSet(rightRecord, me); + if (inverseSetter) { + // Because the rightRecord has a reference back to the leftRecord + // we pass on to its setter (if there is one). We've already set + // the value on this side so we won't recurse back-and-forth. + rightRecord[inverseSetter](leftRecord); + } + } + } else { + // The value we received could just be the id of the rightRecord so we just + // need to set the FK accordingly and cleanup any cached references. + if (!foreignKey) { + Ext.raise('No foreignKey specified for "' + me.association.left.role + '" by ' + leftRecord.$className); + } + modified = (leftRecord.changingKey && !inverse.isMany) || leftRecord.set(foreignKey, rightRecord); + // set returns the modifiedFieldNames[] or null if nothing was change + if (modified && current && current.isEntity && !current.isEqual(current.getId(), rightRecord)) { + // If we just modified the FK value and it no longer matches the id of the + // record we had cached (ret), remove references from *both* sides: + leftRecord[instanceName] = undefined; + if (!inverse.isMany) { + current[inverse.getInstanceName()] = undefined; + } + } + } + if (options) { + if (Ext.isFunction(options)) { + options = { + callback: options, + scope: scope || leftRecord + }; + } + return leftRecord.save(options); + } + } +}); + +/** + * **This class is never created directly. It should be constructed through associations in `Ext.data.Model`.** + * + * Associations enable you to express relationships between different {@link Ext.data.Model Models}. Consider + * an ecommerce system where Users can place Orders - there is a one to many relationship between these Models, + * one user can have many orders (including 0 orders). Here is what a sample implementation of this association + * could look like. This example will be referred to in the following sections. + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [{ + * name: 'id', + * type: 'int' + * }, 'name'] + * }); + * + * Ext.define('Order', { + * extend: 'Ext.data.Model', + * fields: [{ + * name: 'id', + * type: 'int' + * }, { + * name: 'userId', + * type: 'int', + * reference: 'User' + * }] + * }); + * + * # Association Types + * + * Assocations can describe relationships in 3 ways: + * + * ## Many To One + * + * A single entity (`A`) has a relationship with many (`B`) entities. An example of this is + * an ecommerce system `User` can have many `Order` entities. + * + * This can be defined using `Ext.data.schema.ManyToOne` for keyed associations, or + * `Ext.data.schema.HasMany` for keyless associations. + * + * ## One To One + * + * A less common form of Many To One, a single entity (`A`) has a relationship with at most 1 entity (`B`). This is often + * used when partitioning data. For example a `User` may have a single `UserInfo` object that stores extra + * metadata about the user. + * + * This can be defined using `Ext.data.schema.OneToOne` for keyed associations, or + * `Ext.data.schema.HasOne` for keyless associations. + * + * ## Many To Many + * + * An entity (`A`) may have a have a relationship with many (`B`) entities. That (`B`) entity may also + * have a relationship with many `A` entities. For example a single `Student` can have many `Subject` entities and + * a single `Subject` can have many `Student` entities. + * + * This can be defined using `Ext.data.schema.ManyToMany`. Many To Many relationships are readonly unless used with + * a `Ext.data.Session`. + * + * + * # Keyed vs Keyless Associations + * + * Associations can be declared in 2 ways, which are outlined below. + * + * ## Keyed associations + * + * A keyed association relies on a field in the model matching the id of another model. Membership is driven by the key. + * This is the type of relationship that is typically used in a relational database. + * This is declared using the ||reference|| configuration on a model field. An example of this can be seen + * above for `User/Order`. + * + * # Keyless associations + * + * A keyless association relies on data hierarchy to determine membership. Items are members because they are + * contained by another entity. This type of relationship is common with NoSQL databases. + * formats. A simple example definition using `User/Order`: + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [{ + * name: 'id', + * type: 'int' + * }, 'name'], + * hasMany: 'Order' + * }); + * + * Ext.define('Order', { + * extend: 'Ext.data.Model', + * fields: [{ + * name: 'id', + * type: 'int' + * }] + * }); + * + * # Advantages of Associations + * Assocations make it easier to work with Models that share a connection. Some of the main functionality includes: + * + * ## Generated Accessors/Setters + * + * Associated models will automatically generate named methods that allow for accessing the associated data. + * The names for these are created using a {@link Ext.data.schema.Schema Schema}, to provide a consistent and + * predictable naming structure. + * + * Using the example code above, there will be 3 generated methods: + * + `User` will have an `orders()` function that returns a `Ext.data.Store` of`Orders`. + * + `Order` will have a `getUser` method which will return a `User` Model. + * + `Order` will have a `setUser` method that will accept a `User` model or a key value. + * + * ## Nested Loading + * + * Nested loading is the ability to load hierarchical associated data from a remote source within a single request. + * In the following example, each `User` in the `users` store has an `orders` store. Each `orders` store is populated + * with `Order` models read from the request. Each `Order` model also has a reference back to the appropriate `User`. + * + * // Sample JSON data returned by /Users + * [{ + * "id": 1, + * "name": "User Foo", + * "orders": [{ + * "id": 101, + * "userId": 1 + * }, { + * "id": 102, + * "userId": 1 + * }, { + * "id": 103, + * "userId": 1 + * }] + * }, { + * "id": 2, + * "name": "User Bar", + * "orders": [{ + * "id": 201, + * "userId": 2 + * }, { + * "id": 202, + * "userId": 2 + * }] + * }] + * + * // Application code + * var users = new Ext.data.Store({ + * model: 'User', + * proxy: { + * type: 'ajax', + * url: '/Users' + * } + * }); + * users.load(function() { + * var user1 = users.first(), + * user2 = users.last(), + * orders1 = user1.orders(), + * orders2 = user2.orders(); + * + * // 3 orders, same reference back to user1 + * console.log(orders1.getCount(), orders1.first().getUser() === user1); + * // 2 orders, same reference back to user2 + * console.log(orders2.getCount(), orders2.first().getUser() === user2); + * }); + * + * ## Binding + * + * Data binding using {@link Ext.app.ViewModel ViewModels} have functionality to be able to recognize + * associated data as part of a bind statement. For example: + * + `{user.orders}` binds to the orders store for a user. + * + `{order.user.name}` binds to the name of the user taken from the order. + * + * + * # Association Concepts + * + * ## Roles + * + * The role is used to determine generated names for an association. By default, the role is generated from + * either the field name (in a keyed association) or the model name. This naming follows a pattern defined by + * the `Ext.data.schema.Namer`. To change a specific instance, an explicit role can be specified: + * + * Ext.define('Thread', { + * extend: 'Ext.data.Model', + * fields: ['id', 'title'] + * }); + * + * Ext.define('Post', { + * extend: 'Ext.data.Model', + * fields: ['id', 'content', { + * name: 'threadId', + * reference: { + * type: 'Thread', + * role: 'discussion', + * inverse: 'comments' + * + * } + * }] + * }); + * + * In the above example, the `Thread` will be decorated with a `comments` method that returns the store. + * The `Post` will be decorated with `getDiscussion/setDiscussion` methods. + * + * ## Generated Methods + * + * Associations generate methods to allow reading and manipulation on associated data. + * + * On records that have a "to many" relationship, a single methods that returns a `Ext.data.Store` is created. + * See {@link #storeGetter}. On records that have a "to one" relationship, 2 methods are generated, a + * {@link #recordGetter getter} and a {@link #recordSetter setter}. + * + * ## Reflexive + * + * Associations are reflexive. By declaring one "side" of the relationship, the other is automatically setup. In + * the example below, there is no code in the `Thread` entity regarding the association, however by virtue of the + * declaration in post, `Thread` is decorated with the appropriate infrastructure to participate in the association. + * + * Ext.define('Thread', { + * extend: 'Ext.data.Model', + * fields: ['id', 'title'] + * }); + * + * Ext.define('Post', { + * extend: 'Ext.data.Model', + * fields: ['id', 'content', { + * name: 'threadId', + * reference: 'Thread' + * }] + * }); + * + * ## Naming + * + * Referring to model names in associations depends on their {@link Ext.data.Model#entityName}. See + * the "Relative Naming" section in the `Ext.data.schema.Schema` documentation. + */ +Ext.define('Ext.data.schema.Association', { + requires: [ + 'Ext.data.schema.Role' + ], + isOneToOne: false, + isManyToOne: false, + isManyToMany: false, + /** + * @cfg {String} associationKey + * The name of the property in the data to read the association from. Defaults to the + * name of the associated model. + */ + /** + * @method storeGetter + * ** This is not a real method, it is placeholder documentation for a generated method on a `Ext.data.Model`. ** + * + * Gets a store configured with the model of the "many" record. + * @param {Object/Function} [options] The options for the getter, or a callback function to execute. If specified as + * a function, it will act as the `callback` option. + * + * @param {Boolean} [options.reload] `true` to force the store to reload from the server. + * + * @param {Object} [options.scope] The `this` reference for the callback. Defaults to the record. + * + * @param {Function} [options.success] A function to execute when the store loads successfully. + * If the store has already loaded, this will be called immediately and the `Operation` will be `null`. + * The success is passed the following parameters: + * @param {Ext.data.Store} [options.success.store] The store. + * @param {Ext.data.operation.Operation} [options.success.operation] The operation. `null` if no load occurred. + * + * @param {Function} [options.failure] A function to execute when the store load fails. + * If the store has already loaded, this will not be called. + * The failure is passed the following parameters: + * @param {Ext.data.Store} [options.failure.store] The store. + * @param {Ext.data.operation.Operation} [options.failure.operation] The operation + * + * @param {Function} [options.callback] A function to execute when the store loads, whether it is successful + * or failed. If the store has already loaded, this will be called immediately and the `Operation` will be `null`. + * The callback is passed the following parameters: + * @param {Ext.data.Store} [options.callback.store] The store. + * @param {Ext.data.operation.Operation} [options.callback.operation] The operation. `null` if no load occurred. + * @param {Boolean} [options.callback.success] `true` if the load was successful. If already loaded this + * will always be true. + * + * @param {Object} [scope] The `this` reference for the callback. Defaults to the record. + * + * @return {Ext.data.Store} The store. + */ + /** + * @method recordGetter + * ** This is not a real method, it is placeholder documentation for a generated method on a `Ext.data.Model`. ** + * + * Gets a model of the "one" type. + * @param {Object/Function} [options] The options for the getter, or a callback function to execute. If specified as + * a function, it will act as the `callback` option. + * + * @param {Boolean} [options.reload] `true` to force the record to reload from the server. + * + * @param {Object} [options.scope] The `this` reference for the callback. Defaults to the record. + * + * @param {Function} [options.success] A function to execute when the record loads successfully. + * If the record has already loaded, this will be called immediately and the `Operation` will be `null`. + * The success is passed the following parameters: + * @param {Ext.data.Model} [options.success.record] The record. + * @param {Ext.data.operation.Operation} [options.success.operation] The operation. `null` if no load occurred. + * + * @param {Function} [options.failure] A function to execute when the record load fails. + * If the record has already loaded, this will not be called. + * The failure is passed the following parameters: + * @param {Ext.data.Model} [options.failure.record] The record. + * @param {Ext.data.operation.Operation} [options.failure.operation] The operation + * + * @param {Function} [options.callback] A function to execute when the record loads, whether it is successful + * or failed. If the record has already loaded, this will be called immediately and the `Operation` will be `null`. + * The callback is passed the following parameters: + * @param {Ext.data.Model} [options.callback.record] The record. + * @param {Ext.data.operation.Operation} [options.callback.operation] The operation. `null` if no load occurred. + * @param {Boolean} [options.callback.success] `true` if the load was successful. If already loaded this + * will always be true. + * + * @param {Object} [scope] The `this` reference for the callback. Defaults to the record. + * @return {Ext.data.Model} The record. `null` if the reference has been previously specified as empty. + */ + /** + * @method recordSetter ** This is not a real method, it is placeholder documentation for a generated method on a `Ext.data.Model`. ** + * + * Sets a model of the "one" type. + * @param {Ext.data.Model/Object} value The value to set. This can be a model instance, a key value (if a keyed association) or `null` + * to clear the value. + * + * @param {Object/Function} [options] Options to handle callback. If specified as + * a function, it will act as the `callback` option. If specified as an object, the params are the same as + * {@link Ext.data.Model#save}. If options is specified, {@link Ext.data.Model#save} will be called on this record. + */ + /** + * @cfg {String} name + * The name of this association. + */ + /** + * @property {Object} owner + * Points at either `left` or `right` objects if one is the owning party in this + * association or is `null` if there is no owner. + * @readonly + */ + owner: null, + /** + * @property {Ext.Class} definedBy + * @readonly + */ + /** + * @property {Ext.data.field.Field} field + * @readonly + */ + field: null, + /** + * @property {Ext.data.schema.Schema} schema + * @readonly + */ + /** + * @property {Boolean} nullable + * @readonly + */ + /** + * @property {Ext.data.schema.Role} left + * @readonly + */ + /** + * @property {Ext.data.schema.Role} right + * @readonly + */ + constructor: function(config) { + var me = this, + left, right; + Ext.apply(me, config); + me.left = left = new me.Left(me, me.left); + me.right = right = new me.Right(me, me.right); + left.inverse = right; + right.inverse = left; + }, + hasField: function() { + return !!this.field; + }, + getFieldName: function() { + var field = this.field; + return field ? field.name : ''; + } +}); + +/** + * **This class is never created directly. It should be constructed through associations in `Ext.data.Model`.** + * + * This is a specialized version of `Ext.data.schema.ManyToOne` that declares a relationship between a single + * entity type and a single related entities. The relationship can be declared as a keyed or keyless relationship. + * + * // Keyed + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: ['id', 'name', { + * name: 'userInfoId', + * reference: { + * type: 'UserInfo', + * unique: true + * } + * }] + * }); + * + * Ext.define('UserInfo', { + * extend: 'Ext.data.Model', + * fields: ['id', 'secretKey'] + * }); + * + * // Keyless + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: ['id', 'name'], + * hasOne: 'UserInfo' + * }); + * + * Ext.define('Ticket', { + * extend: 'Ext.data.Model', + * fields: ['id', 'secretKey'] + * }); + * + * // Generated methods + * var user = new User(); + * user.getUserInfo(); + * user.setUserInfo(); + * + * var info = new UserInfo(); + * info.getUser(); + * info.setUser(); + * + * + * var ticket = new Ticket(); + * ticket.setCustomer(customer); + * console.log(ticket.getCustomer()); // The customer object + * + * By declaring a keyed relationship, extra functionality is gained that maintains + * the key field in the model as changes are made to the association. + * + * For available configuration options, see {@link Ext.data.schema.Reference}. + * Each record type will have a {@link Ext.data.schema.Association#recordGetter getter} and {@link Ext.data.schema.Association#recordSetter setter}. + */ +Ext.define('Ext.data.schema.OneToOne', { + extend: 'Ext.data.schema.Association', + isOneToOne: true, + isToOne: true, + kind: 'one-to-one', + Left: Ext.define(null, { + extend: 'Ext.data.schema.Role', + onDrop: function(rightRecord, session) { + var leftRecord = this.getAssociatedItem(rightRecord); + rightRecord[this.getInstanceName()] = null; + if (leftRecord) { + leftRecord[this.inverse.getInstanceName()] = null; + } + }, + onIdChanged: function(rightRecord, oldId, newId) { + var leftRecord = this.getAssociatedItem(rightRecord), + fieldName = this.association.getFieldName(); + if (!rightRecord.session && leftRecord && fieldName) { + leftRecord.set(fieldName, newId); + } + }, + createGetter: function() { + var me = this; + return function() { + // 'this' refers to the Model instance inside this function + return me.doGet(this); + }; + }, + createSetter: function() { + var me = this; + return function(value) { + // 'this' refers to the Model instance inside this function + return me.doSet(this, value); + }; + }, + doGet: function(rightRecord) { + // Consider the Department entity with a managerId to a User entity. The + // Department is on the left (the FK holder's side) so we are implementing the + // guts of the getManagerDepartment method we place on the User entity. Since + // we represent the "managerDepartment" role and as such our goal is to get a + // Department instance, we start that from the User (rightRecord). Sadly that + // record has no FK back to us. + var instanceName = this.getInstanceName(), + // ex "managerDepartment" + ret = rightRecord[instanceName], + session = rightRecord.session; + if (!ret && session) {} + // @TODO: session - we'll cache the result on the record as always + // but to get it we must ask the session + return ret || null; + }, + doSet: function(rightRecord, leftRecord) { + // We are the guts of the setManagerDepartment method we place on the User + // entity. Our goal here is to establish the relationship between the new + // Department (leftRecord) and the User (rightRecord). + var instanceName = this.getInstanceName(), + // ex "managerDepartment" + ret = rightRecord[instanceName], + inverseSetter = this.inverse.setterName; + // setManager for Department + if (ret !== leftRecord) { + rightRecord[instanceName] = leftRecord; + if (inverseSetter) { + // Because the FK is owned by the inverse record, we delegate the + // majority of work to its setter. We've already locked in the only + // thing we keep on this side so we won't recurse back-and-forth. + leftRecord[inverseSetter](rightRecord); + } + rightRecord.onAssociatedRecordSet(leftRecord, this); + } + return ret; + }, + read: function(rightRecord, node, fromReader, readOptions) { + var me = this, + leftRecords = me.callParent([ + rightRecord, + node, + fromReader, + readOptions + ]), + leftRecord; + if (leftRecords) { + leftRecord = leftRecords[0]; + if (leftRecord) { + leftRecord[me.inverse.getInstanceName()] = rightRecord; + rightRecord[me.getInstanceName()] = leftRecord; + // Inline associations should *not* arrive on the "data" object: + delete rightRecord.data[me.role]; + } + } + } + }), + Right: Ext.define(null, { + extend: 'Ext.data.schema.Role', + left: false, + side: 'right', + createGetter: function() { + // As the target of the FK (say "manager" for the Department entity) this + // getter is responsible for getting the entity referenced by the FK value. + var me = this; + return function(options, scope) { + // 'this' refers to the Model instance inside this function + return me.doGetFK(this, options, scope); + }; + }, + createSetter: function() { + var me = this; + return function(value, options, scope) { + // 'this' refers to the Model instance inside this function + return me.doSetFK(this, value, options, scope); + }; + }, + onDrop: function(leftRecord, session) { + var me = this, + field = me.association.field, + rightRecord = me.getAssociatedItem(leftRecord), + id; + if (me.inverse.owner) { + if (session && field) { + id = leftRecord.get(field.name); + if (id || id === 0) { + rightRecord = session.getEntry(me.cls, id).record; + if (rightRecord) { + rightRecord.drop(); + } + } + } else { + if (rightRecord) { + rightRecord.drop(); + } + } + } + if (field) { + leftRecord.set(field.name, null); + } + leftRecord[me.getInstanceName()] = null; + if (rightRecord) { + rightRecord[me.inverse.getInstanceName()] = null; + } + }, + onValueChange: function(leftRecord, session, newValue) { + // Important to get the record before changing the key. + var me = this, + rightRecord = leftRecord[me.getOldInstanceName()] || me.getAssociatedItem(leftRecord), + hasNewValue = newValue || newValue === 0, + instanceName = me.getInstanceName(), + cls = me.cls; + leftRecord.changingKey = true; + me.doSetFK(leftRecord, newValue); + if (!hasNewValue) { + leftRecord[instanceName] = null; + } else if (session && cls) { + // Setting to undefined is important so that we can load the record later. + leftRecord[instanceName] = session.peekRecord(cls, newValue) || undefined; + } + if (me.inverse.owner && rightRecord) { + me.association.schema.queueKeyCheck(rightRecord, me); + } + leftRecord.changingKey = false; + }, + checkKeyForDrop: function(rightRecord) { + var leftRecord = this.inverse.getAssociatedItem(rightRecord); + if (!leftRecord) { + // Not reassigned to another parent + rightRecord.drop(); + } + }, + read: function(leftRecord, node, fromReader, readOptions) { + var me = this, + rightRecords = me.callParent([ + leftRecord, + node, + fromReader, + readOptions + ]), + rightRecord, field, fieldName, session, refs, id, oldId, setKey, data; + if (rightRecords) { + rightRecord = rightRecords[0]; + field = me.association.field; + if (field) { + fieldName = field.name; + } + session = leftRecord.session; + data = leftRecord.data; + if (rightRecord) { + if (session) { + refs = session.getRefs(rightRecord, this.inverse, true); + // If we have an existing reference in the session, or we don't and the data is + // undefined, allow the nested load to go ahead + setKey = (refs && refs[leftRecord.id]) || (data[fieldName] === undefined); + } else { + setKey = true; + } + if (setKey) { + // We want to poke the inferred key onto record if it exists, but we don't + // want to mess with the dirty or modified state of the record. + if (field) { + oldId = data[fieldName]; + id = rightRecord.id; + if (oldId !== id) { + data[fieldName] = id; + if (session) { + session.updateReference(leftRecord, field, id, oldId); + } + } + } + rightRecord[me.inverse.getInstanceName()] = leftRecord; + leftRecord[me.getInstanceName()] = rightRecord; + } + // Inline associations should *not* arrive on the "data" object: + delete data[me.role]; + } + } + } + }) +}); + +/** + * **This class is never created directly. It should be constructed through associations in `Ext.data.Model`.** + * + * Declares a relationship between a single entity type and multiple related entities. The relationship can + * be declared as a keyed or keyless relationship. + * + * // Keyed + * Ext.define('Customer', { + * extend: 'Ext.data.Model', + * fields: ['id', 'name'] + * }); + * + * Ext.define('Ticket', { + * extend: 'Ext.data.Model', + * fields: ['id', 'title', { + * name: 'customerId', + * reference: 'Customer' + * }] + * }); + * + * // Keyless + * Ext.define('Customer', { + * extend: 'Ext.data.Model', + * fields: ['id', 'name'], + * hasMany: 'Ticket' + * }); + * + * Ext.define('Ticket', { + * extend: 'Ext.data.Model', + * fields: ['id', 'title'] + * }); + * + * // Generated methods + * var customer = new Customer(); + * customer.tickets(); + * + * var ticket = new Ticket(); + * ticket.getCustomer(); + * ticket.setCustomer(); + * + * By declaring a keyed relationship, extra functionality is gained that maintains + * the key field in the model as changes are made to the association. + * + * For available configuration options, see {@link Ext.data.schema.Reference}. + * The "one" record type will have a generated {@link Ext.data.schema.Association#storeGetter}. The "many" record type + * will have a {@link Ext.data.schema.Association#recordGetter getter} and {@link Ext.data.schema.Association#recordSetter setter}. + */ +Ext.define('Ext.data.schema.ManyToOne', { + extend: 'Ext.data.schema.Association', + isManyToOne: true, + isToOne: true, + kind: 'many-to-one', + Left: Ext.define(null, { + extend: 'Ext.data.schema.Role', + isMany: true, + onDrop: function(rightRecord, session) { + var me = this, + store = me.getAssociatedItem(rightRecord), + leftRecords, len, i, refs, id; + if (store) { + // Removing will cause the foreign key to be set to null. + leftRecords = store.removeAll(); + if (leftRecords && me.inverse.owner) { + // If we're a child, we need to destroy all the "tickets" + for (i = 0 , len = leftRecords.length; i < len; ++i) { + leftRecords[i].drop(); + } + } + store.destroy(); + rightRecord[me.getStoreName()] = null; + } else if (session) { + leftRecords = session.getRefs(rightRecord, me); + if (leftRecords) { + for (id in leftRecords) { + leftRecords[id].drop(); + } + } + } + }, + onIdChanged: function(rightRecord, oldId, newId) { + var fieldName = this.association.getFieldName(), + store = this.getAssociatedItem(rightRecord), + leftRecords, i, len, filter; + if (store) { + filter = store.getFilters().get(this.$roleFilterId); + if (filter) { + filter.setValue(newId); + } + // A session will automatically handle this updating. If we don't have a field + // then there's nothing to do here. + if (!rightRecord.session && fieldName) { + leftRecords = store.getDataSource().items; + for (i = 0 , len = leftRecords.length; i < len; ++i) { + leftRecords[i].set(fieldName, newId); + } + } + } + }, + processUpdate: function(session, associationData) { + var me = this, + entityType = me.inverse.cls, + items = associationData.R, + id, rightRecord, store, leftRecords; + if (items) { + for (id in items) { + rightRecord = session.peekRecord(entityType, id); + if (rightRecord) { + leftRecords = session.getEntityList(me.cls, items[id]); + store = me.getAssociatedItem(rightRecord); + if (store) { + store.loadData(leftRecords); + store.complete = true; + } else { + // We don't have a store. Create it and add the records. + rightRecord[me.getterName](null, null, leftRecords); + } + } else { + session.onInvalidAssociationEntity(entityType, id); + } + } + } + }, + findRecords: function(session, rightRecord, leftRecords, allowInfer) { + var ret = leftRecords, + refs = session.getRefs(rightRecord, this, true), + field = this.association.field, + fieldName, leftRecord, id, i, len, seen; + if (field && (refs || allowInfer)) { + fieldName = field.name; + ret = []; + if (leftRecords) { + seen = {}; + // Loop over the records returned by the server and + // check they all still belong. If the session doesn't have any prior knowledge + // and we're allowed to infer the parent id (via nested loading), only do so if + // we explicitly have an id specified + for (i = 0 , len = leftRecords.length; i < len; ++i) { + leftRecord = leftRecords[i]; + id = leftRecord.id; + if (refs && refs[id]) { + ret.push(leftRecord); + } else if (allowInfer && leftRecord.data[fieldName] === undefined) { + ret.push(leftRecord); + leftRecord.data[fieldName] = rightRecord.id; + session.updateReference(leftRecord, field, rightRecord.id, undefined); + } + seen[id] = true; + } + } + // Loop over the expected set and include any missing records. + if (refs) { + for (id in refs) { + if (!seen || !seen[id]) { + ret.push(refs[id]); + } + } + } + } + return ret; + }, + processLoad: function(store, rightRecord, leftRecords, session) { + var ret = leftRecords; + if (session) { + // Allow infer here, we only get called when loading an associated store + ret = this.findRecords(session, rightRecord, leftRecords, true); + } + this.onLoadMany(rightRecord, ret, session); + return ret; + }, + adoptAssociated: function(rightRecord, session) { + var store = this.getAssociatedItem(rightRecord), + leftRecords, i, len; + if (store) { + store.setSession(session); + leftRecords = store.getData().items; + for (i = 0 , len = leftRecords.length; i < len; ++i) { + session.adopt(leftRecords[i]); + } + } + }, + createGetter: function() { + var me = this; + return function(options, scope, leftRecords) { + // 'this' refers to the Model instance inside this function + return me.getAssociatedStore(this, options, scope, leftRecords, true); + }; + }, + createSetter: null, + // no setter for an isMany side + onAddToMany: function(store, leftRecords) { + var rightRecord = store.getAssociatedEntity(); + if (this.association.field) { + this.syncFK(leftRecords, rightRecord, false); + } else { + this.setInstances(rightRecord, leftRecords); + } + }, + onLoadMany: function(rightRecord, leftRecords, session) { + this.setInstances(rightRecord, leftRecords, session); + }, + onRemoveFromMany: function(store, leftRecords) { + if (this.association.field) { + this.syncFK(leftRecords, store.getAssociatedEntity(), true); + } else { + this.setInstances(null, leftRecords); + } + }, + read: function(rightRecord, node, fromReader, readOptions) { + var me = this, + // We use the inverse role here since we're setting ourselves + // on the other record + instanceName = me.inverse.getInstanceName(), + leftRecords = me.callParent([ + rightRecord, + node, + fromReader, + readOptions + ]), + store, len, i; + if (leftRecords) { + // Create the store and dump the data + store = rightRecord[me.getterName](null, null, leftRecords); + // Inline associations should *not* arrive on the "data" object: + delete rightRecord.data[me.role]; + leftRecords = store.getData().items; + for (i = 0 , len = leftRecords.length; i < len; ++i) { + leftRecords[i][instanceName] = rightRecord; + } + } + }, + setInstances: function(rightRecord, leftRecords, session) { + var instanceName = this.inverse.getInstanceName(), + id = rightRecord ? rightRecord.getId() : null, + field = this.association.field, + len = leftRecords.length, + i, leftRecord, oldId, data, name; + for (i = 0; i < len; ++i) { + leftRecord = leftRecords[i]; + leftRecord[instanceName] = rightRecord; + if (field) { + name = field.name; + data = leftRecord.data; + oldId = data[name]; + if (oldId !== id) { + data[name] = id; + if (session) { + session.updateReference(leftRecord, field, id, oldId); + } + } + } + } + }, + syncFK: function(leftRecords, rightRecord, clearing) { + // We are called to set things like the FK (ticketId) of an array of Comment + // entities. The best way to do that is call the setter on the Comment to set + // the Ticket. Since we are setting the Ticket, the name of that setter is on + // our inverse role. + var foreignKeyName = this.association.getFieldName(), + inverse = this.inverse, + setter = inverse.setterName, + // setTicket + instanceName = inverse.getInstanceName(), + i = leftRecords.length, + id = rightRecord.getId(), + different, leftRecord, val; + while (i-- > 0) { + leftRecord = leftRecords[i]; + different = !leftRecord.isEqual(id, leftRecord.get(foreignKeyName)); + val = clearing ? null : rightRecord; + if (different !== clearing) { + // clearing === true + // different === true :: leave alone (not associated anymore) + // ** different === false :: null the value (no longer associated) + // + // clearing === false + // ** different === true :: set the value (now associated) + // different === false :: leave alone (already associated) + // + leftRecord.changingKey = true; + leftRecord[setter](val); + leftRecord.changingKey = false; + } else { + // Ensure we set the instance, we may only have the key + leftRecord[instanceName] = val; + } + } + } + }), + Right: Ext.define(null, { + extend: 'Ext.data.schema.Role', + left: false, + side: 'right', + onDrop: function(leftRecord, session) { + // By virtue of being dropped, this record will be removed + // from any stores it belonged to. The only case we have + // to worry about is if we have a session but were not yet + // part of any stores, so we need to clear the foreign key. + var field = this.association.field; + if (field) { + leftRecord.set(field.name, null); + } + leftRecord[this.getInstanceName()] = null; + }, + createGetter: function() { + // As the target of the FK (say "ticket" for the Comment entity) this + // getter is responsible for getting the entity referenced by the FK value. + var me = this; + return function(options, scope) { + // 'this' refers to the Comment instance inside this function + return me.doGetFK(this, options, scope); + }; + }, + createSetter: function() { + var me = this; + return function(rightRecord, options, scope) { + // 'this' refers to the Comment instance inside this function + return me.doSetFK(this, rightRecord, options, scope); + }; + }, + checkMembership: function(session, leftRecord) { + var field = this.association.field, + store; + if (field) { + store = this.getSessionStore(session, leftRecord.get(field.name)); + // Check we're not in the middle of an add to the store. + if (store && !store.contains(leftRecord)) { + store.add(leftRecord); + } + } + }, + onValueChange: function(leftRecord, session, newValue, oldValue) { + // If we have a session, we may be able to find the new store this belongs to + // If not, the best we can do is to remove the record from the associated store/s. + var me = this, + instanceName = me.getInstanceName(), + cls = me.cls, + hasNewValue, joined, store, i, associated, rightRecord; + if (!leftRecord.changingKey) { + hasNewValue = newValue || newValue === 0; + if (!hasNewValue) { + leftRecord[instanceName] = null; + } + if (session) { + // Find the store that holds this record and remove it if possible. + store = me.getSessionStore(session, oldValue); + if (store) { + store.remove(leftRecord); + } + // If we have a new value, try and find it and push it into the new store. + if (hasNewValue) { + store = me.getSessionStore(session, newValue); + if (store && !store.isLoading()) { + store.add(leftRecord); + } + if (cls) { + rightRecord = session.peekRecord(cls, newValue); + } + // Setting to undefined is important so that we can load the record later. + leftRecord[instanceName] = rightRecord || undefined; + } + } else { + joined = leftRecord.joined; + if (joined) { + // Loop backwards because the store remove may cause unjoining, which means + // removal from the joined array. + for (i = joined.length - 1; i >= 0; i--) { + store = joined[i]; + if (store.isStore) { + associated = store.getAssociatedEntity(); + if (associated && associated.self === me.cls && associated.getId() === oldValue) { + store.remove(leftRecord); + } + } + } + } + } + } + if (me.owner && newValue === null) { + me.association.schema.queueKeyCheck(leftRecord, me); + } + }, + checkKeyForDrop: function(leftRecord) { + var field = this.association.field; + if (leftRecord.get(field.name) === null) { + leftRecord.drop(); + } + }, + getSessionStore: function(session, value) { + // May not have the cls loaded yet + var cls = this.cls, + rec; + if (cls) { + rec = session.peekRecord(cls, value); + if (rec) { + return this.inverse.getAssociatedItem(rec); + } + } + }, + read: function(leftRecord, node, fromReader, readOptions) { + var rightRecords = this.callParent([ + leftRecord, + node, + fromReader, + readOptions + ]), + rightRecord; + if (rightRecords) { + rightRecord = rightRecords[0]; + if (rightRecord) { + leftRecord[this.getInstanceName()] = rightRecord; + delete leftRecord.data[this.role]; + } + } + } + }) +}); + +/** + * This relationship describes the case where any one entity of one type may relate to any + * number of entities of another type, and also in the reverse. + * + * This form of association cannot store id's in the related entities since that would + * limit the number of related entities to one for the entity with the foreign key. Instead, + * these relationships are typically implemented using a so-called "matrix" table. This + * table typically has two columns to hold the id's of a pair of related entities. This + * pair of id's is unique in the matrix table. + * + * # Declaration Forms + * + * // Fully spelled out - all properties are their defaults: + * + * Ext.define('App.models.Group', { + * extend: 'Ext.data.Model', + * + * manyToMany: { + * UserGroups: { + * type: 'User', + * role: 'users', + * field: 'userId', + * right: { + * field: 'groupId', + * role: 'groups' + * } + * } + * } + * }); + * + * // Eliminate "right" object and use boolean to indicate Group is on the + * // right. By default, left/right is determined by alphabetic order. + * + * Ext.define('App.models.Group', { + * extend: 'Ext.data.Model', + * + * manyToMany: { + * UserGroups: { + * type: 'User', + * role: 'users', + * field: 'userId', + * right: true + * } + * } + * }); + * + * // Eliminate object completely and rely on string to name the other type. Still + * // keep Group on the "right". + * + * Ext.define('App.models.Group', { + * extend: 'Ext.data.Model', + * + * manyToMany: { + * UserGroups: 'User#' // '#' is on the side (left or right) of Group + * } + * }); + * + * // Remove explicit matrix name and keep Group on the "right". Generated matrixName + * // remains "UserGroups". + * + * Ext.define('App.models.Group', { + * extend: 'Ext.data.Model', + * + * manyToMany: [ + * 'User#' + * ] + * }); + * + * // Minimal definition but now Group is on the "left" since "Group" sorts before + * // "User". Generated matrixName is now "GroupUsers". + * + * Ext.define('App.models.Group', { + * extend: 'Ext.data.Model', + * + * manyToMany: [ + * 'User' + * ] + * }); + */ +Ext.define('Ext.data.schema.ManyToMany', { + extend: 'Ext.data.schema.Association', + isManyToMany: true, + isToMany: true, + kind: 'many-to-many', + Left: Ext.define(null, { + extend: 'Ext.data.schema.Role', + isMany: true, + digitRe: /^\d+$/, + findRecords: function(session, rightRecord, leftRecords) { + var slice = session.getMatrixSlice(this.inverse, rightRecord.id), + members = slice.members, + ret = [], + cls = this.cls, + seen, i, len, id, member, leftRecord; + if (leftRecords) { + seen = {}; + // Loop over the records returned by the server and + // check they all still belong + for (i = 0 , len = leftRecords.length; i < len; ++i) { + leftRecord = leftRecords[i]; + id = leftRecord.id; + member = members[id]; + if (!(member && member[2] === -1)) { + ret.push(leftRecord); + } + seen[id] = true; + } + } + // Loop over the expected set and include any missing records. + for (id in members) { + member = members[id]; + if (!seen || !seen[id] && (member && member[2] !== -1)) { + leftRecord = session.peekRecord(cls, id); + if (leftRecord) { + ret.push(leftRecord); + } + } + } + return ret; + }, + onIdChanged: function(rightRecord, oldId, newId) { + var store = this.getAssociatedItem(rightRecord); + if (store) { + store.getFilters().get(this.$roleFilterId).setValue(newId); + } + }, + processLoad: function(store, rightRecord, leftRecords, session) { + var ret = leftRecords; + if (session) { + ret = this.findRecords(session, rightRecord, leftRecords); + this.onAddToMany(store, ret, true); + } + return ret; + }, + processUpdate: function(session, associationData) { + var me = this, + entityType = me.inverse.cls, + items = associationData.R, + id, rightRecord, store, leftRecords; + if (items) { + for (id in items) { + rightRecord = session.peekRecord(entityType, id); + if (rightRecord) { + leftRecords = session.getEntityList(me.cls, items[id]); + store = me.getAssociatedItem(rightRecord); + if (store) { + store.loadData(leftRecords); + store.complete = true; + } else { + // We don't have a store. Create it and add the records. + rightRecord[me.getterName](null, null, leftRecords); + } + } else { + session.onInvalidAssociationEntity(entityType, id); + } + } + } + me.processMatrixBlock(session, associationData.C, 1); + me.processMatrixBlock(session, associationData.D, -1); + }, + checkMembership: function(session, rightRecord) { + var matrix = session.getMatrix(this.association, true), + side, entityType, inverse, slice, slices, id, members, member, leftRecord, store; + if (!matrix) { + return; + } + side = this.left ? matrix.right : matrix.left; + entityType = side.inverse.role.cls; + inverse = this.inverse; + slices = side.slices; + if (slices) { + slice = slices[rightRecord.id]; + if (slice) { + members = slice.members; + for (id in members) { + member = members[id]; + if (member[2] !== -1) { + // Do we have the record in the session? If so, do we also have the store? + leftRecord = session.peekRecord(entityType, id); + if (leftRecord) { + store = inverse.getAssociatedItem(leftRecord); + if (store) { + store.matrixUpdate = 1; + store.add(rightRecord); + store.matrixUpdate = 0; + } + } + } + } + } + } + }, + onStoreCreate: function(store, session, id) { + var me = this, + matrix; + if (session) { + // If we are creating a store of say Groups in a UserGroups matrix, we want + // to traverse the inverse side of the matrix (Users) because the id we have + // is that of the User to which these Groups are associated. + matrix = session.getMatrixSlice(me.inverse, id); + matrix.attach(store); + matrix.notify = me.onMatrixUpdate; + matrix.scope = me; + } + }, + processMatrixBlock: function(session, leftKeys, state) { + var inverse = this.inverse, + digitRe = this.digitRe, + slice, id; + if (leftKeys) { + for (id in leftKeys) { + // We may not have the record available to pull out the id, so the best we can + // do here is try to detect a number id. + if (digitRe.test(id)) { + id = parseInt(id, 10); + } + slice = session.getMatrixSlice(inverse, id); + slice.update(leftKeys[id], state); + } + } + }, + createGetter: function() { + var me = this; + return function(options, scope, leftRecords) { + // 'this' refers to the Model instance inside this function + return me.getAssociatedStore(this, options, scope, leftRecords, false); + }; + }, + /* + * This method is called when records are added to the association store. If this + * is happening as a side-effect of the underlying matrix update, we skip telling + * the matrix what it already knows. Otherwise we need to tell the matrix of the + * changes on this side so that they can be reflected on the other side. + */ + onAddToMany: function(store, leftRecords, load) { + if (!store.matrixUpdate) { + store.matrixUpdate = 1; + // By default the "load" param is really the index, but we call this manually in a few + // spots to indicate it's a default load + store.matrix.update(leftRecords, load === true ? 0 : 1); + store.matrixUpdate = 0; + } + }, + /* + * This method is called when records are removed from the association store. The + * same logic applies here as in onAddToMany with respect to the update that may + * or may not be taking place on the underlying matrix. + */ + onRemoveFromMany: function(store, records) { + if (!store.matrixUpdate) { + store.matrixUpdate = 1; + store.matrix.update(records, -1); + store.matrixUpdate = 0; + } + }, + read: function(rightRecord, node, fromReader, readOptions) { + var me = this, + leftRecords = me.callParent([ + rightRecord, + node, + fromReader, + readOptions + ]); + if (leftRecords) { + // Create the store and dump the data + rightRecord[me.getterName](null, null, leftRecords); + // Inline associations should *not* arrive on the "data" object: + delete rightRecord.data[me.role]; + } + }, + onMatrixUpdate: function(matrixSlice, id, state) { + var store = matrixSlice.store, + index, leftRecord, entry; + if (store && !store.loading && !store.matrixUpdate) { + store.matrixUpdate = 1; + index = store.indexOfId(id); + if (state < 0) { + if (index >= 0) { + store.remove([ + index + ]); + } + } else if (index < 0) { + entry = store.getSession().getEntry(this.type, id); + leftRecord = entry && entry.record; + if (leftRecord) { + store.add(leftRecord); + } + } + store.matrixUpdate = 0; + } + }, + adoptAssociated: function(record, session) { + var store = this.getAssociatedItem(record), + records, i, len; + if (store) { + store.setSession(session); + this.onStoreCreate(store, session, record.getId()); + records = store.getData().items; + for (i = 0 , len = records.length; i < len; ++i) { + session.adopt(records[i]); + } + } + } + }, function() { + var Left = this; + // Left is created but ManyToMany may not yet be created + Ext.ClassManager.onCreated(function() { + Ext.data.schema.ManyToMany.prototype.Right = Ext.define(null, { + extend: Left, + left: false, + side: 'right' + }); + }, null, 'Ext.data.schema.ManyToMany'); + }) +}); + +/** + * General purpose inflector class that {@link #pluralize pluralizes}, {@link #singularize singularizes} and + * {@link #ordinalize ordinalizes} words. Sample usage: + * + * //turning singular words into plurals + * Ext.util.Inflector.pluralize('word'); //'words' + * Ext.util.Inflector.pluralize('person'); //'people' + * Ext.util.Inflector.pluralize('sheep'); //'sheep' + * + * //turning plurals into singulars + * Ext.util.Inflector.singularize('words'); //'word' + * Ext.util.Inflector.singularize('people'); //'person' + * Ext.util.Inflector.singularize('sheep'); //'sheep' + * + * //ordinalizing numbers + * Ext.util.Inflector.ordinalize(11); //"11th" + * Ext.util.Inflector.ordinalize(21); //"21st" + * Ext.util.Inflector.ordinalize(1043); //"1043rd" + * + * # Customization + * + * The Inflector comes with a default set of US English pluralization rules. These can be augmented with additional + * rules if the default rules do not meet your application's requirements, or swapped out entirely for other languages. + * Here is how we might add a rule that pluralizes "ox" to "oxen": + * + * Ext.util.Inflector.plural(/^(ox)$/i, "$1en"); + * + * Each rule consists of two items - a regular expression that matches one or more rules, and a replacement string. In + * this case, the regular expression will only match the string "ox", and will replace that match with "oxen". Here's + * how we could add the inverse rule: + * + * Ext.util.Inflector.singular(/^(ox)en$/i, "$1"); + * + * Note that the ox/oxen rules are present by default. + */ +Ext.define('Ext.util.Inflector', { + /* Begin Definitions */ + singleton: true, + /* End Definitions */ + /** + * @private + * The registered plural tuples. Each item in the array should contain two items - the first must be a regular + * expression that matchers the singular form of a word, the second must be a String that replaces the matched + * part of the regular expression. This is managed by the {@link #plural} method. + * @property {Array} plurals + */ + plurals: [ + [ + (/(quiz)$/i), + "$1zes" + ], + [ + (/^(ox)$/i), + "$1en" + ], + [ + (/([m|l])ouse$/i), + "$1ice" + ], + [ + (/(matr|vert|ind)ix|ex$/i), + "$1ices" + ], + [ + (/(x|ch|ss|sh)$/i), + "$1es" + ], + [ + (/([^aeiouy]|qu)y$/i), + "$1ies" + ], + [ + (/(hive)$/i), + "$1s" + ], + [ + (/(?:([^f])fe|([lr])f)$/i), + "$1$2ves" + ], + [ + (/sis$/i), + "ses" + ], + [ + (/([ti])um$/i), + "$1a" + ], + [ + (/(buffal|tomat|potat)o$/i), + "$1oes" + ], + [ + (/(bu)s$/i), + "$1ses" + ], + [ + (/(alias|status|sex)$/i), + "$1es" + ], + [ + (/(octop|vir)us$/i), + "$1i" + ], + [ + (/(ax|test)is$/i), + "$1es" + ], + [ + (/^(p)erson$/i), + "$1eople" + ], + [ + (/^(m)an$/i), + "$1en" + ], + [ + (/(.*)(child)(ren)?$/i), + "$1$2ren" + ], + [ + (/s$/i), + "s" + ], + [ + (/$/), + "s" + ] + ], + /** + * @private + * The set of registered singular matchers. Each item in the array should contain two items - the first must be a + * regular expression that matches the plural form of a word, the second must be a String that replaces the + * matched part of the regular expression. This is managed by the {@link #singular} method. + * @property {Array} singulars + */ + singulars: [ + [ + (/(address)$/i), + "$1" + ], + [ + (/(quiz)zes$/i), + "$1" + ], + [ + (/(matr)ices$/i), + "$1ix" + ], + [ + (/(vert|ind)ices$/i), + "$1ex" + ], + [ + (/^(ox)en/i), + "$1" + ], + [ + (/(alias|status)es$/i), + "$1" + ], + [ + (/(octop|vir)i$/i), + "$1us" + ], + [ + (/(cris|ax|test)es$/i), + "$1is" + ], + [ + (/(shoe)s$/i), + "$1" + ], + [ + (/(o)es$/i), + "$1" + ], + [ + (/(bus)es$/i), + "$1" + ], + [ + (/([m|l])ice$/i), + "$1ouse" + ], + [ + (/(x|ch|ss|sh)es$/i), + "$1" + ], + [ + (/(m)ovies$/i), + "$1ovie" + ], + [ + (/(s)eries$/i), + "$1eries" + ], + [ + (/([^aeiouy]|qu)ies$/i), + "$1y" + ], + [ + (/([lr])ves$/i), + "$1f" + ], + [ + (/(tive)s$/i), + "$1" + ], + [ + (/(hive)s$/i), + "$1" + ], + [ + (/([^f])ves$/i), + "$1fe" + ], + [ + (/(^analy)ses$/i), + "$1sis" + ], + [ + (/((a)naly|(b)a|(d)iagno|(p)arenthe|(p)rogno|(s)ynop|(t)he)ses$/i), + "$1$2sis" + ], + [ + (/([ti])a$/i), + "$1um" + ], + [ + (/(n)ews$/i), + "$1ews" + ], + [ + (/(p)eople$/i), + "$1erson" + ], + [ + (/s$/i), + "" + ] + ], + /** + * @private + * The registered uncountable words + * @property {String[]} uncountable + */ + uncountable: [ + "sheep", + "fish", + "series", + "species", + "money", + "rice", + "information", + "equipment", + "grass", + "mud", + "offspring", + "deer", + "means" + ], + /** + * Adds a new singularization rule to the Inflector. See the intro docs for more information + * @param {RegExp} matcher The matcher regex + * @param {String} replacer The replacement string, which can reference matches from the matcher argument + */ + singular: function(matcher, replacer) { + this.singulars.unshift([ + matcher, + replacer + ]); + }, + /** + * Adds a new pluralization rule to the Inflector. See the intro docs for more information + * @param {RegExp} matcher The matcher regex + * @param {String} replacer The replacement string, which can reference matches from the matcher argument + */ + plural: function(matcher, replacer) { + this.plurals.unshift([ + matcher, + replacer + ]); + }, + /** + * Removes all registered singularization rules + */ + clearSingulars: function() { + this.singulars = []; + }, + /** + * Removes all registered pluralization rules + */ + clearPlurals: function() { + this.plurals = []; + }, + /** + * Returns true if the given word is transnumeral (the word is its own singular and plural form - e.g. sheep, fish) + * @param {String} word The word to test + * @return {Boolean} True if the word is transnumeral + */ + isTransnumeral: function(word) { + return Ext.Array.indexOf(this.uncountable, word) != -1; + }, + /** + * Returns the pluralized form of a word (e.g. Ext.util.Inflector.pluralize('word') returns 'words') + * @param {String} word The word to pluralize + * @return {String} The pluralized form of the word + */ + pluralize: function(word) { + if (this.isTransnumeral(word)) { + return word; + } + var plurals = this.plurals, + length = plurals.length, + tuple, regex, i; + for (i = 0; i < length; i++) { + tuple = plurals[i]; + regex = tuple[0]; + if (regex == word || (regex.test && regex.test(word))) { + return word.replace(regex, tuple[1]); + } + } + return word; + }, + /** + * Returns the singularized form of a word (e.g. Ext.util.Inflector.singularize('words') returns 'word') + * @param {String} word The word to singularize + * @return {String} The singularized form of the word + */ + singularize: function(word) { + if (this.isTransnumeral(word)) { + return word; + } + var singulars = this.singulars, + length = singulars.length, + tuple, regex, i; + for (i = 0; i < length; i++) { + tuple = singulars[i]; + regex = tuple[0]; + if (regex == word || (regex.test && regex.test(word))) { + return word.replace(regex, tuple[1]); + } + } + return word; + }, + /** + * Returns the correct {@link Ext.data.Model Model} name for a given string. Mostly used internally by the data + * package + * @param {String} word The word to classify + * @return {String} The classified version of the word + */ + classify: function(word) { + return Ext.String.capitalize(this.singularize(word)); + }, + /** + * Ordinalizes a given number by adding a prefix such as 'st', 'nd', 'rd' or 'th' based on the last digit of the + * number. 21 -> 21st, 22 -> 22nd, 23 -> 23rd, 24 -> 24th etc + * @param {Number} number The number to ordinalize + * @return {String} The ordinalized number + */ + ordinalize: function(number) { + var parsed = parseInt(number, 10), + mod10 = parsed % 10, + mod100 = parsed % 100; + //11 through 13 are a special case + if (11 <= mod100 && mod100 <= 13) { + return number + "th"; + } else { + switch (mod10) { + case 1: + return number + "st"; + case 2: + return number + "nd"; + case 3: + return number + "rd"; + default: + return number + "th"; + } + } + } +}, function() { + //aside from the rules above, there are a number of words that have irregular pluralization so we add them here + var irregulars = { + alumnus: 'alumni', + cactus: 'cacti', + focus: 'foci', + nucleus: 'nuclei', + radius: 'radii', + stimulus: 'stimuli', + ellipsis: 'ellipses', + paralysis: 'paralyses', + oasis: 'oases', + appendix: 'appendices', + index: 'indexes', + beau: 'beaux', + bureau: 'bureaux', + tableau: 'tableaux', + woman: 'women', + child: 'children', + man: 'men', + corpus: 'corpora', + criterion: 'criteria', + curriculum: 'curricula', + genus: 'genera', + memorandum: 'memoranda', + phenomenon: 'phenomena', + foot: 'feet', + goose: 'geese', + tooth: 'teeth', + antenna: 'antennae', + formula: 'formulae', + nebula: 'nebulae', + vertebra: 'vertebrae', + vita: 'vitae' + }, + singular; + for (singular in irregulars) { + if (irregulars.hasOwnProperty(singular)) { + this.plural(singular, irregulars[singular]); + this.singular(irregulars[singular], singular); + } + } +}); + +/** + * This class provides name derivation methods for use by a `Schema`. + * + * # Caching + * + * Because most name derivations are only textual manipulations of input strings, the + * results can be cached. This is handled by the `apply` method by giving it the name of + * the method to call. For example: + * + * var str = namer.capitalize('foo'); // = "Foo" + * + * var str = namer.apply('capitalize', 'foo'); + * + * The return value of the second call (using `apply`) is the same as the first, however, + * the results of `capitalize` are cached. This allows repeated calls to `apply` given the + * same operation and string to avoid the extra string manipulation. + * + * # Usage + * + * This class is not intended to be created by application code. It is created by `Schema` + * instances as directed by the `namer` config. Application code can derive from this + * class and set the `namer` config to customize naming conventions used by the `Schema`. + * + * @protected + */ +Ext.define('Ext.data.schema.Namer', { + mixins: [ + 'Ext.mixin.Factoryable' + ], + requires: [ + 'Ext.util.Inflector' + ], + alias: 'namer.default', + // also configures Factoryable + isNamer: true, + //------------------------------------------------------------------------- + // Cacheable methods + capitalize: function(name) { + return Ext.String.capitalize(name); + }, + /** + * Given the name of a foreign key field, return the role of the related entity. For + * example, fields like "fooId" or "foo_id" this implementation returns "foo". + * @template + */ + fieldRole: function(name) { + var match = name.match(this.endsWithIdRe, ''); + if (match) { + name = name.substr(0, name.length - (match[1] || match[2]).length); + } + return this.apply('uncapitalize', name); + }, + idField: function(name) { + // ex: User ==> userId + return this.apply('uncapitalize,singularize', name) + 'Id'; + }, + instanceName: function(roleName) { + return this.apply('underscore', roleName); + }, + multiRole: function(name) { + return this.apply('undotted,uncapitalize,pluralize', name); + }, + pluralize: function(name) { + return Ext.util.Inflector.pluralize(name); + }, + readerRoot: function(roleName) { + return this.apply('uncapitalize', roleName); + }, + singularize: function(name) { + return Ext.util.Inflector.singularize(name); + }, + storeName: function(roleName) { + return this.apply('underscore', roleName); + }, + uncapitalize: function(name) { + return Ext.String.uncapitalize(name); + }, + underscore: function(name) { + return '_' + name; + }, + uniRole: function(name) { + return this.apply('undotted,uncapitalize,singularize', name); + }, + undotted: function(name) { + if (name.indexOf('.') < 0) { + return name; + } + var parts = name.split('.'), + index = parts.length; + while (index-- > 1) { + parts[index] = this.apply('capitalize', parts[index]); + } + return parts.join(''); + }, + //------------------------------------------------------------------------- + // Non-Cacheable methods + getterName: function(role) { + var name = role.role; + if (role && role.isMany) { + //return this.apply('uncapitalize,pluralize', name); + return name; + } + //return this.apply('capitalize,singularize', name); + return 'get' + this.apply('capitalize', name); + }, + inverseFieldRole: function(leftType, unique, rightRole, rightType) { + // In a FK association, the left side may be unique in which case we have a + // one-to-one otherwise we have a one-to-many. If the FK field is just the + // name of the right side class (e.g., if it is "order"), then we don't want + // to include the field name in the left role. + var me = this, + leftRole = me.apply(unique ? 'uniRole' : 'multiRole', leftType), + s1 = me.apply('pluralize', rightRole), + s2 = me.apply('undotted,pluralize', rightType); + if (s1.toLowerCase() !== s2.toLowerCase()) { + // Otherwise, we have something like "creatorId" on Ticket that holds a + // reference to User. This makes the right role "creator" so rather than + // make the left role "tickets" we make it "creatorTickets". + leftRole = rightRole + me.apply('capitalize', leftRole); + } + return leftRole; + }, + manyToMany: function(relation, leftType, rightType) { + var me = this, + // ex: UserGroups + ret = me.apply('undotted,capitalize,singularize', leftType) + me.apply('undotted,capitalize,pluralize', rightType); + if (relation) { + ret = me.apply('capitalize', relation + ret); + } + return ret; + }, + /** + * Returns the name for a one-to-many association given the left and right type and + * the associating `role`. + * + * In many cases the `role` matches the target type. For example, an OrderItem might + * have an "orderId" field which would have a `role` of "order". If this is a reference + * to an Order entity then the association name will be "OrderOrderItems". + * + * When the `role` does not match, it is included in the association name. For example, + * consider a Ticket entity with a "creatorId" field that references a User entity. + * The `role` of that field will (by default) be "creator". The returned association + * name will be "UserCreatorTickets". + */ + manyToOne: function(leftType, leftRole, rightType, rightRole) { + // ex: OrderItem -> Order ==> OrderOrderItems + // Ticket (creator) -> User ==> UserCreatorTickets + return this.apply('capitalize,singularize', rightType) + this.apply('capitalize', leftRole); + }, + matrixRole: function(relation, entityType) { + var ret = this.apply(relation ? 'multiRole,capitalize' : 'multiRole', entityType); + return relation ? relation + ret : ret; + }, + oneToOne: function(leftType, leftRole, rightType, rightRole) { + return this.apply('undotted,capitalize,singularize', rightType) + this.apply('capitalize', leftRole); + }, + setterName: function(role) { + return 'set' + this.apply('capitalize', role.role); + }, + //------------------------------------------------------------------------- + // Private + endsWithIdRe: /(?:(_id)|[^A-Z](Id))$/, + cache: {}, + apply: function(operation, name) { + var me = this, + cache = me.cache, + entry = cache[name] || (cache[name] = {}), + ret = entry[operation], + i, length, operations; + if (!ret) { + if (operation.indexOf(',') < 0) { + ret = me[operation](name); + } else { + length = (operations = operation.split(',')).length; + ret = name; + for (i = 0; i < length; ++i) { + ret = me.apply(operations[i], ret); + } + } + entry[operation] = ret; + } + return ret; + } +}); + +/** + * A Schema is a collection of related {@link Ext.data.Model entities} and their respective + * {@link Ext.data.schema.Association associations}. + * + * # Schema Instances + * + * By default a single instance of this class is created which serves as the schema for all + * entities that do not have an explicit `{@link Ext.data.Model#cfg-schema schema}` config + * either specified or inherited. This is sufficient in most cases. + * + * When an entity does specify a `{@link Ext.data.Model#cfg-schema schema}`, however, that + * looks up (or creates) an instance for that entity class which is then inherited. + * + * **Important:** All related entities *must* belong to a single schema instance in order + * to properly link up their associations. + * + * ## Configuring Schemas + * + * The best way to control the configuration of your `schema` is to define a base class for + * all of your entities and use the `{@link Ext.data.Model#cfg-schema schema}` config like + * this: + * + * Ext.define('MyApp.model.Base', { + * extend: 'Ext.data.Model', + * + * // This configures the default schema because we don't assign an "id": + * schema: { + * // configs go here + * } + * }); + * + * **Note:** Only one explicit configuration can be applied to the default schema. In most + * applications this will not be an issue. + * + * By using a base class for your entities you can ensure that the default schema is fully + * configured before declaration of your classes proceeds. This is especially helpful if + * you need to set the `namespace` for your schema (see below). + * + * ## Relative Naming + * + * When describing associations between entities, it is desirable to use shorthand names + * that do not contain the common namespace portion. This is called the `entityName` as + * opposed to its class name. By default, the `entityName` is the full class name. However, + * if a namespace is used, the common portion can be discarded and we can derive a shorter name. + * In the following code, `"MyApp.model.Foo"` has an `entityName` of `"Foo"` and the schema has + * a `namespace` of "MyApp.model". + * + * If you use deeper nesting for entities, you may need to set the `namespace` config to + * account for this. For example: + * + * Ext.define('MyApp.model.Base', { + * extend: 'Ext.data.Model', + * + * schema: { + * namespace: 'MyApp.model' + * } + * }); + * + * Your derived classes now will generate proper default `entityName` values even if they + * have further namespaces. For example, "MyApp.model.foo.Thing" will produce "foo.Thing" + * as the `entityName` given the above as a base class. + * + * # Association Naming + * + * There are various terms involved when describing associations. Perhaps the simplest + * example that will clarify these terms is that of the common many-to-many association + * of User and Group. + * + * * `entityName` - The names "User" and "Group" are the `entityName` values associated + * with these two classes. These are derived from their full classnames (perhaps + * something like "App.model.User" and "App.model.Group"). + * + * * `associationName` - When talking about associations, especially the many-to-many + * variety, it is important to give them names. Associations are not owned by either of + * the entities involved, so this name is similar to an `entityName`. In the case of + * "User" and "Group", the default `associationName` would be "GroupUsers". + * + * * `left` and `right` - Associations describe a relationship between two entities. To + * talk about specific associations we would use the `entityName` of the parties (such + * as "User" or "Group"). When discussing associations in the abstract, however, it is + * very helpful to be able to talk about the entities in an association in a general way. + * In the case of the "GroupUsers" association, "User" is said to be the `left` while + * "Group" is said to be the `right`. In a many-to-many association the selection of + * `left` and `right` is arbitrary. When a foreign-key is involved, the `left` entity + * is the one containing the foreign-key. + * + * ## Custom Naming Conventions + * + * One of the jobs the the `Schema` is to manage name generation (such as `entityName`). + * This job is delegated to a class called the `namer`. If you need to generate names in + * other ways, you can provide a custom `namer` for your classes: + * + * Ext.define('MyApp.model.Base', { + * extend: 'Ext.data.Model', + * + * schema: { + * namespace: 'MyApp.model', + * namer: 'custom' + * } + * }); + * + * This will create a class using the alias "namer.custom". For example: + * + * Ext.define('MyApp.model.CustomNamer', { + * extend: 'Ext.data.schema.Namer', + * + * alias: 'namer.custom', + * ... + * }); + * + * For details see the documentation for {@link Ext.data.schema.Namer Namer}. + */ +Ext.define('Ext.data.schema.Schema', { + mixins: [ + 'Ext.mixin.Factoryable' + ], + requires: [ + 'Ext.util.ObjectTemplate', + 'Ext.data.schema.OneToOne', + 'Ext.data.schema.ManyToOne', + 'Ext.data.schema.ManyToMany', + 'Ext.data.schema.Namer' + ], + alias: 'schema.default', + // also configures Factoryable + aliasPrefix: 'schema.', + isSchema: true, + /** + * @property {String} type + * The name of the schema's type. This should be the suffix of the `alias` for this + * class following the "schema." prefix. For example, if the `alias` for a schema is + * "schema.foo" then `type` should "foo". If an `alias` is specified on the derived + * class, this property is set automatically. + * @readonly + */ + type: 'default', + statics: { + /** + * @property {Object} instances + * A collection of `Schema` instances keyed by its `type`. + * + * var mySchema = Ext.data.schema.Schema.instances.mySchema; + * + * If the `Schema` may not have been created yet, use the {@link #get} method to + * create the instance on first request: + * + * var mySchema = Ext.data.schema.Schema.get('mySchema'); + * + * @readonly + * @private + */ + instances: {}, + // Method used for testing to clear cache for custom instances. + clearInstance: function(id) { + var schema = this.instances[id]; + delete this.instances[id]; + if (schema) { + schema.clear(true); + schema.destroy(); + } + }, + /** + * Returns the `Schema` instance given its `id` or config object. If only the `id` + * is specified, that `Schema` instance is looked up and returned. If there is no + * instance already created, the `id` is assumed to be the `type`. For example: + * + * schema: 'foo' + * + * Would be created from the alias `"schema.foo"` and assigned the `id` of "foo" + * as well. + * + * @param {String/Object} config The id, type or config object of the schema. + * @param {String} [config.type] The type alias of the schema. A "schema." prefix + * is added to this string, if provided, to complete the alias. This should match + * match the "alias" of some class derived from `Ext.data.schema.Schema`. + * @return {Ext.data.schema.Schema} The previously existing or newly created + * instance. + */ + get: function(config) { + var Schema = this, + cache = Schema.instances, + id = 'default', + isString = config && Ext.isString(config), + instance, newConfig; + if (config) { + if (config.isSchema) { + return config; + } + id = isString ? config : (config.id || id); + } + if (!(instance = cache[id])) { + cache[id] = instance = Schema.create(config); + instance.id = id; + } else if (config && !isString) { + if (id !== 'default') { + Ext.raise('Only the default Schema instance can be reconfigured'); + } + // When a Model contains a "schema" config object it is allowed to set the + // configuration of the default schema. This is the default behavior of + // this config on a model unless there is an "id" specified on it. So + // the trick is that we already have an instance so we want to merge the + // incoming config with the initial config of the default schema and then + // make that the effective initial config. + newConfig = Ext.merge({}, instance.config); + Ext.merge(newConfig, config); + instance.setConfig(newConfig); + instance.config = newConfig; + instance.setConfig = function() { + Ext.raise('The schema can only be reconfigured once'); + }; + } + return instance; + }, + lookupEntity: function(entity) { + var ret = null, + instances = this.instances, + match, name, schema; + if (entity) { + if (entity.isEntity) { + ret = entity.self; + } + // a record + else if (Ext.isFunction(entity)) { + // A function (assume that a constructor is the Class). + ret = entity; + } else if (Ext.isString(entity)) { + ret = Ext.ClassManager.get(entity); + // If we've found a singleton or non-Entity class by that name, ignore it. + if (ret && (!ret.prototype || !ret.prototype.isEntity)) { + ret = null; + } + if (!ret) { + for (name in instances) { + schema = instances[name]; + match = schema.getEntity(entity); + if (match) { + if (ret) { + Ext.raise('Ambiguous entity name "' + entity + '". Defined by schema "' + ret.schema.type + '" and "' + name + '"'); + } + ret = match; + } + } + } + if (!ret) { + Ext.raise('No such Entity "' + entity + '".'); + } + } + } + return ret; + } + }, + /** + * @property {Number} assocCount The number of {@link Ext.data.schema.Association associations} + * in this `schema`. + * @readonly + */ + assocCount: 0, + /** + * @property {Number} entityCount The number of {@link Ext.data.Model entities} in this + * `schema`. + * @readonly + */ + entityCount: 0, + config: { + /** + * @cfg {Object} defaultIdentifier + * This config is used to initialize the `{@link Ext.data.Model#identifier}` config + * for classes that do not define one. + */ + defaultIdentifier: null, + /** + * @cfg {Number} keyCheckDelay + * The time to wait (in ms) before checking for null foreign keys on records that + * will cause them to be dropped. This is useful for allowing records to be moved to a different + * source. + * @private + * @since 5.0.1 + */ + keyCheckDelay: 10, + /** + * @cfg {String/Object/Ext.data.schema.Namer} namer + * Specifies or configures the name generator for the schema. + */ + namer: 'default', + /** + * @cfg {String} namespace + * The namespace for entity classes in this schema. + */ + namespace: null, + /** + * @cfg {Object/Ext.util.ObjectTemplate} proxy + * This is a template used to produce `Ext.data.proxy.Proxy` configurations for + * Models that do not define an explicit `{@link Ext.data.Model#cfg-proxy proxy}`. + * + * This template is processed with the Model class as the data object which means + * any static properties of the Model are available. The most useful of these are + * + * * `prefix` - The `urlPrefix` property of this instance. + * * `entityName` - The {@link Ext.data.Model#entityName name} of the Model + * (for example, "User"). + * * `schema` - This instance. + */ + proxy: { + type: 'ajax', + url: '{prefix}/{entityName}' + }, + /** + * @cfg {String} [urlPrefix=""] + * This is the URL prefix used for all requests to the server. It could be something + * like "/~api". This value is included in the `proxy` template data as "prefix". + */ + urlPrefix: '' + }, + onClassExtended: function(cls, data) { + var alias = data.alias; + if (alias && !data.type) { + if (!Ext.isString(alias)) { + alias = alias[0]; + } + cls.prototype.type = alias.substring(this.prototype.aliasPrefix.length); + } + }, + constructor: function(config) { + this.initConfig(config); + this.clear(); + }, + //------------------------------------------------------------------------- + // Config + // + applyDefaultIdentifier: function(identifier) { + return identifier && Ext.Factory.dataIdentifier(identifier); + }, + applyNamer: function(namer) { + var ret = Ext.data.schema.Namer.create(namer); + ret.schema = this; + return ret; + }, + applyNamespace: function(namespace) { + if (namespace) { + var end = namespace.length - 1; + if (namespace.charAt(end) !== '.') { + namespace += '.'; + } + } + return namespace; + }, + applyProxy: function(proxy) { + return Ext.util.ObjectTemplate.create(proxy); + }, + // + //------------------------------------------------------------------------- + // Public + eachAssociation: function(fn, scope) { + var associations = this.associations, + name; + for (name in associations) { + if (associations.hasOwnProperty(name)) { + if (fn.call(scope, name, associations[name]) === false) { + break; + } + } + } + }, + eachEntity: function(fn, scope) { + var entities = this.entities, + name; + for (name in entities) { + if (entities.hasOwnProperty(name)) { + if (fn.call(scope, name, entities[name].cls) === false) { + break; + } + } + } + }, + /** + * Returns an `Association` by name. + * @param {String} name The name of the association. + * @return {Ext.data.schema.Association} The association instance. + */ + getAssociation: function(name) { + var entry = this.associations[name]; + return entry || null; + }, + /** + * Returns an entity by name. + * @param {String} name The name of the entity + * @return {Ext.data.Model} The entity class. + */ + getEntity: function(name) { + var entry = this.entityClasses[name] || this.entities[name]; + return (entry && entry.cls) || null; + }, + /** + * Get the entity name taking into account the {@link #namespace}. + * @param {String/Ext.data.Model} cls The model class or name of the class. + * @return {String} The entity name + */ + getEntityName: function(cls) { + var ns = this.getNamespace(), + index, name; + if (typeof cls === 'string') { + name = cls; + } else { + name = cls.$className || null; + } + if (name) { + // if (not anonymous class) + if (ns) { + index = ns.length; + if (name.substring(0, index) !== ns) { + return name; + } + } + if (index) { + name = name.substring(index); + } + } + return name; + }, + /** + * Checks if the passed entity has attached associations that need to be read when + * using nested loading. + * + * @param {String/Ext.Class/Ext.data.Model} name The name, instance, or Model class. + * @return {Boolean} `true` if there are associations attached to the entity. + */ + hasAssociations: function(name) { + name = name.entityName || name; + return !!this.associationEntityMap[name]; + }, + /** + * Checks if an entity is defined + * @param {String/Ext.data.Model} entity The name or model + * @return {Boolean} True if this entity is defined + */ + hasEntity: function(entity) { + var name = this.getEntityName(entity); + return !!(this.entities[name] || this.entityClasses[name]); + }, + //------------------------------------------------------------------------- + // Protected + /** + * Adds an entry from a {@link Ext.data.schema.ManyToMany matrix config} declared by an + * entity. + * + * This is the ideal method to override in a derived class if the standard, default + * naming conventions need to be adjusted. In the override, apply whatever logic is + * appropriate to determine the missing values and pass along the proper results to + * this method in the `callParent`. + * + * @param {Ext.Class} entityType A class derived from `Ext.data.Model`. + * + * @param {String} matrixName The name of the matrix association. + * + * @param {String} [relation] A base name for the matrix. For information about the + * meaning of this see {@link Ext.data.Schema#ManyToMany}. + * + * @param {Object} left The descriptor for the "left" of the matrix. + * @param {String} left.type The type of the entity on the "left" of the matrix. + * + * @param {String} [left.field] The name of the field in the matrix table for the "left" + * side entity. If not provided, this defaults to the `left.type` name + * {@link Ext.util.Inflector#singularize singularized} and uncapitalized followed by + * "Id". For example, "userId" for a `left.type` of "Users". + * + * @param {String} [left.role] The name of the relationship from the `left.type` to the + * `right.type`. If not provided, this defaults to the `left.type` name + * {@link Ext.util.Inflector#pluralize pluralized} and uncapitalized. For example, + * "users" for a `left.type` of "User". + * + * @param {Object} right The descriptor for the "right" of the matrix. + * @param {String} right.type The type of the entity on the "right" of the matrix. + * + * @param {String} [right.field] The name of the field in the matrix table for the + * "right" side entity. If not provided, this defaults in the same way as `left.field` + * except this is based on `right.type`. + * + * @param {String} [right.role] The name of the relationship from the `right.type` to + * the `left.type`. If not provided, this defaults in the same way as `left.role` + * except this is based on `right.type`. + * + * @protected + */ + addMatrix: function(entityType, matrixName, relation, left, right) { + var me = this, + namer = me.getNamer(), + associations = me.associations, + entities = me.entities, + leftType = left.type, + rightType = right.type, + leftField = left.field || namer.apply('idField', leftType), + rightField = right.field || namer.apply('idField', rightType), + leftRole = left.role || namer.matrixRole(relation, leftType), + rightRole = right.role || namer.matrixRole(relation, rightType), + matrix, leftEntry, rightEntry; + leftEntry = entities[leftType] || (entities[leftType] = { + cls: null, + name: leftType, + associations: {} + }); + rightEntry = entities[rightType] || (entities[rightType] = { + cls: null, + name: rightType, + associations: {} + }); + ++me.assocCount; + associations[matrixName] = matrix = new Ext.data.schema.ManyToMany({ + name: matrixName, + schema: me, + definedBy: entityType, + left: { + cls: leftEntry.cls, + type: leftType, + role: leftRole, + field: leftField, + associationKey: left.associationKey + }, + right: { + cls: rightEntry.cls, + type: rightType, + role: rightRole, + field: rightField, + associationKey: right.associationKey + } + }); + leftEntry.associations[matrix.right.role] = matrix.right; + rightEntry.associations[matrix.left.role] = matrix.left; + if (leftEntry.cls) { + me.associationEntityMap[leftEntry.cls.entityName] = true; + } + if (rightEntry.cls) { + me.associationEntityMap[rightEntry.cls.entityName] = true; + } + me.decorateModel(matrix); + }, + /** + * Adds a {@link Ext.data.Field#reference reference} field association for an entity + * to this `schema`. + * + * This is the ideal method to override in a derived class if the standard, default + * naming conventions need to be adjusted. In the override, apply whatever logic is + * appropriate to determine the missing values and pass along the proper results to + * this method in the `callParent`. + * + * @param {Ext.Class} entityType A class derived from `Ext.data.Model`. + * + * @param {Ext.data.field.Field} referenceField The `field` with the `reference` config. + * + * @param {Object} [descr] The `reference` descriptor from the `referenceField` if one + * was given in the field definition. + * + * @param {String} [descr.association] The name of the association. If empty or null, this + * will be derived from `entityType`, `role`, `inverse` and + * `referenceField.unique`. + * + * @param {String} [descr.role] The name of the relationship from `entityType` to the target + * `type`. If not specified, the default is the `referenceField.name` (minus any "Id" + * suffix if present). + * + * @param {String} [descr.inverse] The name of the relationship from the target `type` + * to the `entityType`. If not specified, this is derived from the + * {@link Ext.data.Model#entityName entityName} of the `entityType` + * ({@link Ext.util.Inflector#singularize singularized} or + * {@link Ext.util.Inflector#pluralize pluralized} based on `referenceField.unique`). + * + * @param {String} descr.type The {@link Ext.data.Model#entityName entityName} of the + * target of the reference. + * + * @param {Boolean} [unique=false] Indicates if the reference is one-to-one. + * @param {Boolean} [dupeCheck] (private) + * + * @protected + */ + addReference: function(entityType, referenceField, descr, unique, dupeCheck) { + var me = this, + namer = me.getNamer(), + entities = me.entities, + associations = me.associations, + entityName = entityType.entityName, + association = descr.association, + child = descr.child, + parent = descr.parent, + rightRole = descr.role, + // Allow { child: 'OrderItem' } or the reverse (for one-to-one mostly): + rightType = descr.type || parent || child, + leftVal = descr.inverse, + left = Ext.isString(leftVal) ? { + role: leftVal + } : leftVal, + leftRole = left && left.role, + entry, T; + if (!rightRole) { + // In a FK association, the left side has the key in a field named something + // like "orderId". The default implementation of "fieldRole" namer is to drop + // the id suffix which gives is the role of the right side. + if (!referenceField || descr.legacy) { + rightRole = namer.apply('uncapitalize', rightType); + } else { + rightRole = namer.apply('fieldRole', referenceField.name); + } + } + if (!leftRole) { + leftRole = namer.inverseFieldRole(entityName, unique, rightRole, rightType); + } + if (!association) { + if (unique) { + association = namer.oneToOne(entityType, leftRole, rightType, rightRole); + } else { + association = namer.manyToOne(entityType, leftRole, rightType, rightRole); + } + } + if (dupeCheck && association in associations) { + if (dupeCheck(associations[association], association, leftRole, rightRole) !== false) { + return; + } + } + if (association in associations) { + Ext.raise('Duplicate association: "' + association + '" declared by ' + entityName + (referenceField ? ('.' + referenceField.name) : '') + ' (collides with ' + associations[association].definedBy.entityName + ')'); + } + if (referenceField && referenceField.definedBy === entities[rightType]) { + Ext.raise('ForeignKey reference should not be owned by the target model'); + } + // Lookup the entry for the target of the reference. Since it may not as yet be + // defined, we may need to create the entry. + entry = entities[rightType] || (entities[rightType] = { + cls: null, + name: rightType, + associations: {} + }); + // as a field w/reference we are always "left": + T = unique ? Ext.data.schema.OneToOne : Ext.data.schema.ManyToOne; + association = new T({ + name: association, + // Note: "parent" or "child" can be strings so don't assume otherwise + owner: child ? 'left' : (parent ? 'right' : null), + definedBy: entityType, + schema: me, + field: referenceField, + nullable: referenceField ? !!referenceField.allowBlank : true, + left: { + cls: entityType, + type: entityName, + role: leftRole, + extra: left + }, + right: { + cls: entry.cls, + type: rightType, + role: rightRole, + extra: descr + }, + meta: descr + }); + // Add the left and right association "sides" to the appropriate collections, but + // remember that the right-side entity class may not yet be declared (that's ok as + // we store the associations in the entry): + entityType.associations[rightRole] = association.right; + entry.associations[leftRole] = association.left; + if (referenceField) { + // Store the role on the FK field. This "upgrades" legacy associations to the + // new "field.reference" form. + referenceField.reference = association.right; + entityType.references.push(referenceField); + } + ++me.assocCount; + me.associationEntityMap[entityName] = true; + if (entry.cls) { + me.associationEntityMap[entry.cls.entityName] = true; + } + associations[association.name] = association; + if (association.right.cls) { + me.decorateModel(association); + } + }, + //------------------------------------------------------------------------- + privates: { + /** + * Adds an {@link Ext.data.Model entity} to this `schema`. + * @param {Ext.Class} entityType A class derived from {@link Ext.data.Model}. + * @private + */ + addEntity: function(entityType) { + var me = this, + entities = me.entities, + entityName = entityType.entityName, + entry = entities[entityName], + fields = entityType.fields, + associations, field, i, length, name; + if (!entry) { + entities[entityName] = entry = { + name: entityName, + associations: {} + }; + } else if (entry.cls) { + Ext.raise('Duplicate entity name "' + entityName + '": ' + entry.cls.$className + ' and ' + entityType.$className); + } else { + associations = entry.associations; + for (name in associations) { + // the associations collection describes the types to which this entity is + // related, but the inverse descriptors need this entityType: + associations[name].inverse.cls = entityType; + me.associationEntityMap[entityName] = true; + // We already have an entry, which means other associations have likely been added + // for us, so go ahead and do the inverse decoration + me.decorateModel(associations[name].association); + } + } + entry.cls = entityType; + entityType.prototype.associations = entityType.associations = entry.associations; + me.entityClasses[entityType.$className] = entry; + ++me.entityCount; + for (i = 0 , length = fields.length; i < length; ++i) { + field = fields[i]; + if (field.reference) { + me.addReferenceDescr(entityType, field); + } + } + }, + /** + * Adds the matrix associations of an {@link Ext.data.Model entity} to this `schema`. + * @param {Ext.Class} entityType A class derived from {@link Ext.data.Model Entity}. + * @param {Object/String[]} matrices The manyToMany matrices for the class. + * @private + */ + addMatrices: function(entityType, matrices) { + var me = this, + i, length, matrixName; + if (Ext.isString(matrices)) { + me.addMatrixDescr(entityType, null, matrices); + } else if (matrices[0]) { + // if (isArray) + for (i = 0 , length = matrices.length; i < length; ++i) { + me.addMatrixDescr(entityType, null, matrices[i]); + } + } else { + for (matrixName in matrices) { + me.addMatrixDescr(entityType, matrixName, matrices[matrixName]); + } + } + }, + /** + * Adds an entry from a {@link Ext.data.schema.ManyToMany matrix config} declared by an + * {@link Ext.data.Model entity}. + * + * @param {Ext.Class} entityType A class derived from {@link Ext.data.Model Entity}. + * @param {String} [matrixName] The name of the matrix association. + * @param {String/Object} matrixDef A {@link Ext.data.schema.ManyToMany matrix config} + * declared by an {@link Ext.data.Model entity}. + * @private + */ + addMatrixDescr: function(entityType, matrixName, matrixDef) { + var me = this, + entityName = entityType.entityName, + associations = me.associations, + namer = me.getNamer(), + left = matrixDef.left, + right = matrixDef.right, + last, relation; + if (Ext.isString(matrixDef)) { + if (matrixDef.charAt(0) === '#') { + // "#User" (entity is on the left) + /* + * Ext.define('User', { + * extend: 'Ext.data.Model', + * manyToMany: '#Group' + * }); + */ + left = { + type: entityName + }; + // User + right = { + type: matrixDef.substring(1) + }; + } + // Group + else if (matrixDef.charAt(last = matrixDef.length - 1) === '#') { + // "User#" + /* + * Ext.define('Group', { + * extend: 'Ext.data.Model', + * manyToMany: 'User#' + * }); + */ + left = { + type: matrixDef.substring(0, last) + }; + // User + right = { + type: entityName + }; + } + // Group + else if (namer.apply('multiRole', entityName) < namer.apply('multiRole', matrixDef)) { + /* + * Ext.define('Group', { + * extend: 'Ext.data.Model', + * manyToMany: 'User' + * }); + */ + left = { + type: entityName + }; + // Group + right = { + type: matrixDef + }; + } else // User + { + /* + * Ext.define('User', { + * extend: 'Ext.data.Model', + * manyToMany: 'Group' + * }); + */ + left = { + type: matrixDef + }; + // Group + right = { + type: entityName + }; + } + } else // User + { + Ext.Assert.isString(matrixDef.type, 'No "type" for manyToMany in ' + entityName); + relation = matrixDef.relation; + if (left || (!right && namer.apply('multiRole', entityName) < namer.apply('multiRole', matrixDef.type))) { + if (!left || left === true) { + /* + * Ext.define('User', { + * extend: 'Ext.data.Model', + * manyToMany: { + * type: 'Group', + * left: true + * } + * }); + */ + left = { + type: entityName + }; + } else // User + { + /* + * Ext.define('User', { + * extend: 'Ext.data.Model', + * manyToMany: { + * type: 'Group', + * left: { + * role: 'useroids' + * } + * } + * }); + */ + left = Ext.apply({ + type: entityName + }, left); + } + // User + right = matrixDef; + } else // Group + { + if (!right || right === true) { + /* + * Ext.define('Group', { + * extend: 'Ext.data.Model', + * manyToMany: { + * type: 'User', + * right: true + * } + * }); + */ + right = { + type: entityName + }; + } else // Group + { + /* + * Ext.define('Group', { + * extend: 'Ext.data.Model', + * manyToMany: { + * type: 'User', + * right: { + * role: 'groupoids' + * } + * } + * }); + */ + right = Ext.apply({ + type: entityName + }, right); + } + // Group + left = matrixDef; + } + } + // User + if (!matrixName) { + matrixName = namer.manyToMany(relation, left.type, right.type); + } + if (!(matrixName in associations)) { + me.addMatrix(entityType, matrixName, relation, left, right); + } else // + // In the case of a matrix association, both sides may need to declare it to allow + // them to be used w/o the other present. In development mode, we want to check + // that they declare the same thing! + // + { + var entry = associations[matrixName], + before = [ + entry.kind, + entry.left.type, + entry.left.role, + entry.left.field, + entry.right.type, + entry.right.role, + entry.right.field + ].join('|'); + // Call back in to bypass this check and realize the new association: + delete associations[matrixName]; + me.addMatrix(entityType, matrixName, relation, left, right); + var after = associations[matrixName]; + // Restore the originals so we match production behavior (for testing) + associations[matrixName] = entry; + entry.left.cls.associations[entry.right.role] = entry.right; + entry.right.cls.associations[entry.left.role] = entry.left; + --me.assocCount; + // Now we can compare the old and the new to see if they are the same. + after = [ + after.kind, + after.left.type, + after.left.role, + after.left.field, + after.right.type, + after.right.role, + after.right.field + ].join('|'); + if (before != after) { + Ext.log.warn(matrixName + '(' + entry.definedBy.entityName + '): ' + before); + Ext.log.warn(matrixName + '(' + entityName + '): ' + after); + Ext.raise('Conflicting association: "' + matrixName + '" declared by ' + entityName + ' was previously declared by ' + entry.definedBy.entityName); + } + } + }, + /** + * Adds a {@link Ext.data.Field#reference reference} {@link Ext.data.Field field} + * association for an entity to this `schema`. This method decodes the `reference` + * config of the `referenceField` and calls {@link #addReference}. + * + * @param {Ext.Class} entityType A class derived from {@link Ext.data.Model Model}. + * @param {Ext.data.Field} referenceField The `field` with the `reference` config. + * @private + */ + addReferenceDescr: function(entityType, referenceField) { + var me = this, + descr = referenceField.$reference; + if (Ext.isString(descr)) { + descr = { + type: descr + }; + } else { + descr = Ext.apply({}, descr); + } + me.addReference(entityType, referenceField, descr, referenceField.unique); + }, + addBelongsTo: function(entityType, assoc) { + this.addKeylessSingle(entityType, assoc, false); + }, + addHasOne: function(entityType, assoc) { + this.addKeylessSingle(entityType, assoc, true); + }, + addKeylessSingle: function(entityType, assoc, unique) { + var foreignKey, referenceField; + assoc = Ext.apply({}, this.checkLegacyAssociation(entityType, assoc)); + assoc.type = this.getEntityName(assoc.child || assoc.parent || assoc.type); + foreignKey = assoc.foreignKey || (assoc.type.toLowerCase() + '_id'); + referenceField = entityType.getField(foreignKey); + assoc.fromSingle = true; + if (referenceField) { + referenceField.$reference = assoc; + referenceField.unique = true; + assoc.legacy = true; + Ext.log.warn('Using foreignKey is deprecated, use a keyed association. See Ext.data.field.Field.reference'); + } + this.addReference(entityType, referenceField, assoc, unique); + }, + addHasMany: function(entityType, assoc) { + var me = this, + entities = me.entities, + pending = me.pending, + cls, name, referenceField, target, foreignKey, inverseOptions, child, declaredInverse; + assoc = Ext.apply({}, this.checkLegacyAssociation(entityType, assoc)); + assoc.type = this.getEntityName(assoc.child || assoc.parent || assoc.type); + name = assoc.type; + target = entities[name]; + cls = target && target.cls; + if (cls) { + name = entityType.entityName; + foreignKey = assoc.foreignKey || (name.toLowerCase() + '_id'); + delete assoc.foreignKey; + // The assoc is really the inverse, so we only set the minimum. + // We copy the inverse from assoc and apply it over assoc! + declaredInverse = Ext.apply({}, assoc.inverse); + delete assoc.inverse; + inverseOptions = Ext.apply({}, assoc); + delete inverseOptions.type; + assoc = Ext.apply({ + type: name, + inverse: inverseOptions + }, declaredInverse); + child = inverseOptions.child; + if (child) { + delete inverseOptions.child; + assoc.parent = name; + } + referenceField = cls.getField(foreignKey); + if (referenceField) { + referenceField.$reference = assoc; + assoc.legacy = true; + Ext.log.warn('Using foreignKey is deprecated, use a keyed association. See Ext.data.field.Field.reference'); + } + // We already have the entity, we can process it + me.addReference(cls, referenceField, assoc, false, function(association, name, leftRole, rightRole) { + // Check to see if the user has used belongsTo/hasMany in conjunction. + var result = !!association.meta.fromSingle && cls === association.left.cls, + l, r; + if (result) { + l = cls.entityName; + r = entityType.entityName; + Ext.raise('hasMany ("' + r + '") and belongsTo ("' + l + '") should not be used in conjunction to declare a relationship. Use only one.'); + } + return result; + }); + } else { + // Pending, push it in the queue for when we load it + if (!pending[name]) { + pending[name] = []; + } + pending[name].push([ + entityType, + assoc + ]); + } + }, + checkLegacyAssociation: function(entityType, assoc) { + if (Ext.isString(assoc)) { + assoc = { + type: assoc + }; + } else { + assoc = Ext.apply({}, assoc); + } + if (assoc.model) { + assoc.type = assoc.model; + // TODO: warn + delete assoc.model; + } + var name = assoc.associatedName || assoc.name; + if (name) { + // TODO: warn + delete assoc.associatedName; + delete assoc.name; + assoc.role = name; + } + return assoc; + }, + afterKeylessAssociations: function(cls) { + var pending = this.pending, + name = cls.entityName, + mine = pending[name], + i, len; + if (mine) { + for (i = 0 , len = mine.length; i < len; ++i) { + this.addHasMany.apply(this, mine[i]); + } + delete pending[name]; + } + }, + clear: function(clearNamespace) { + // for testing + var me = this, + timer = me.timer; + delete me.setConfig; + if (timer) { + window.clearTimeout(timer); + me.timer = null; + } + me.associations = {}; + me.associationEntityMap = {}; + me.entities = {}; + me.entityClasses = {}; + me.pending = {}; + me.assocCount = me.entityCount = 0; + if (clearNamespace) { + me.setNamespace(null); + } + }, + constructProxy: function(Model) { + var me = this, + data = Ext.Object.chain(Model), + proxy = me.getProxy(); + data.schema = me; + data.prefix = me.getUrlPrefix(); + return proxy.apply(data); + }, + applyDecoration: function(role) { + var me = this, + // To decorate a role like "users" (of a User / Group matrix) we need to add + // getter/setter methods to access the "users" collection ... to Group! All + // other data about the "users" role and the User class belong to the given + // "role" but the receiver class is the inverse. + cls = role.inverse.cls, + namer = me.getNamer(), + getterName, setterName, proto; + // The cls may not be loaded yet, so we need to check if it is before + // we can decorate it. + if (cls && !role.decorated) { + role.decorated = true; + proto = cls.prototype; + if (!(getterName = role.getterName)) { + role.getterName = getterName = namer.getterName(role); + } + proto[getterName] = role.createGetter(); + // Not all associations will create setters + if (role.createSetter) { + if (!(setterName = role.setterName)) { + role.setterName = setterName = namer.setterName(role); + } + proto[setterName] = role.createSetter(); + } + } + }, + decorateModel: function(association) { + this.applyDecoration(association.left); + this.applyDecoration(association.right); + }, + processKeyChecks: function(processAll) { + var me = this, + keyCheckQueue = me.keyCheckQueue, + timer = me.timer, + len, i, item; + if (timer) { + window.clearTimeout(timer); + me.timer = null; + } + if (!keyCheckQueue) { + return; + } + // It's possible that processing a drop may cause another drop + // to occur. If we're trying to forcibly resolve the state, then + // we need to trigger all the drops at once. With processAll: false, + // the loop will jump out after the first iteration. + do { + keyCheckQueue = me.keyCheckQueue; + me.keyCheckQueue = []; + for (i = 0 , len = keyCheckQueue.length; i < len; ++i) { + item = keyCheckQueue[i]; + item.role.checkKeyForDrop(item.record); + } + } while (processAll && me.keyCheckQueue.length); + }, + queueKeyCheck: function(record, role) { + var me = this, + keyCheckQueue = me.keyCheckQueue, + timer = me.timer; + if (!keyCheckQueue) { + me.keyCheckQueue = keyCheckQueue = []; + } + keyCheckQueue.push({ + record: record, + role: role + }); + if (!timer) { + me.timer = timer = Ext.defer(me.processKeyChecks, me.getKeyCheckDelay(), me); + } + }, + rankEntities: function() { + var me = this, + entities = me.entities, + entityNames = Ext.Object.getKeys(entities), + length = entityNames.length, + entityType, i; + me.nextRank = 1; + // We do an alpha sort to make the results more stable. + entityNames.sort(); + for (i = 0; i < length; ++i) { + entityType = entities[entityNames[i]].cls; + if (!entityType.rank) { + me.rankEntity(entityType); + } + } + me.topoStack = null; + }, + // cleanup diagnostic stack + rankEntity: function(entityType) { + var associations = entityType.associations, + associatedType, role, roleName; + var topoStack = this.topoStack || (this.topoStack = []), + entityName = entityType.entityName; + topoStack.push(entityName); + if (entityType.rank === 0) { + Ext.raise(entityName + " has circular foreign-key references: " + topoStack.join(" --> ")); + } + entityType.rank = 0; + // mark as "adding" so we can detect cycles + for (roleName in associations) { + role = associations[roleName]; + // The role describes the thing to which entityType is associated, so we + // want to know about *this* type and whether it has a foreign-key to the + // associated type. The left side is the FK owner so if the associated + // type is !left then entityType is left. + // + if (!role.left && role.association.field) { + // This entityType has a foreign-key to the associated type, so add + // that type first. + associatedType = role.cls; + if (!associatedType.rank) { + this.rankEntity(associatedType); + } + } + } + entityType.rank = this.nextRank++; + topoStack.pop(); + } + } +}); +// private + +/** + * AbstractStore is a superclass of {@link Ext.data.ProxyStore} and {@link Ext.data.ChainedStore}. It's never used directly, + * but offers a set of methods used by both of those subclasses. + * + * Unless you need to make a whole new type of Store, see {@link Ext.data.Store} instead. + */ +Ext.define('Ext.data.AbstractStore', { + mixins: [ + 'Ext.mixin.Observable', + 'Ext.mixin.Factoryable' + ], + requires: [ + 'Ext.util.Collection', + 'Ext.data.Range', + 'Ext.data.schema.Schema', + 'Ext.util.Filter' + ], + factoryConfig: { + defaultType: 'store', + type: 'store' + }, + $configPrefixed: false, + $configStrict: false, + config: { + /** + * @cfg {Object[]/Function[]} filters + * Array of {@link Ext.util.Filter Filters} for this store. Can also be passed array of + * functions which will be used as the {@link Ext.util.Filter#filterFn filterFn} config + * for filters: + * + * filters: [ + * function(item) { + * return item.weight > 0; + * } + * ] + * + * Individual filters can be specified as an `Ext.util.Filter` instance, a config + * object for `Ext.util.Filter` or simply a function that will be wrapped in a + * instance with its {@Ext.util.Filter#filterFn filterFn} set. + * + * For fine grain control of the filters collection, call `getFilters` to return + * the `Ext.util.Collection` instance that holds this store's filters. + * + * var filters = store.getFilters(); // an Ext.util.FilterCollection + * + * function legalAge (item) { + * return item.age >= 21; + * } + * + * filters.add(legalAge); + * + * //... + * + * filters.remove(legalAge); + * + * Any changes to the `filters` collection will cause this store to adjust + * its items accordingly. + */ + filters: null, + /** + * @cfg {Boolean} [autoDestroy] + * When a Store is used by only one {@link Ext.view.View DataView}, and should only exist for the lifetime of that view, then + * configure the autoDestroy flag as `true`. This causes the destruction of the view to trigger the destruction of its Store. + */ + autoDestroy: undefined, + /** + * @cfg {String} storeId + * Unique identifier for this store. If present, this Store will be registered with the {@link Ext.data.StoreManager}, + * making it easy to reuse elsewhere. + * + * Note that when a store is instantiated by a Controller, the storeId will default + * to the name of the store if not specified in the class. + */ + storeId: null, + /** + * @cfg {Boolean} statefulFilters + * Configure as `true` to have the filters saved when a client {@link Ext.grid.Panel grid} saves its state. + */ + statefulFilters: false, + /** + * @cfg {Ext.util.Sorter[]/Object[]} sorters + * The initial set of {@link Ext.util.Sorter Sorters} + * + * Individual sorters can be specified as an `Ext.util.Sorter` instance, a config + * object for `Ext.util.Sorter` or simply the name of a property by which to sort. + * + * An alternative way to extend the sorters is to call the `sort` method and pass + * a property or sorter config to add to the sorters. + * + * For fine grain control of the sorters collection, call `getSorters` to return + * the `Ext.util.Collection` instance that holds this collection's sorters. + * + * var sorters = store.getSorters(); // an Ext.util.SorterCollection + * + * sorters.add('name'); + * + * //... + * + * sorters.remove('name'); + * + * Any changes to the `sorters` collection will cause this store to adjust + * its items accordingly. + */ + sorters: null, + /** + * @cfg {Boolean} [remoteSort=false] + * `true` if the sorting should be performed on the server side, false if it is local only. + */ + remoteSort: { + lazy: true, + $value: false + }, + /** + * @cfg {Boolean} [remoteFilter=false] + * `true` to defer any filtering operation to the server. If `false`, filtering is done locally on the client. + */ + remoteFilter: { + lazy: true, + $value: false + }, + /** + * @cfg {String} groupField + * The field by which to group data in the store. Internally, grouping is very similar to sorting - the + * groupField and {@link #groupDir} are injected as the first sorter (see {@link #method-sort}). Stores support a single + * level of grouping, and groups can be fetched via the {@link #getGroups} method. + */ + groupField: undefined, + /** + * @cfg {String} groupDir + * The direction in which sorting should be applied when grouping. Supported values are "ASC" and "DESC". + */ + groupDir: 'ASC', + /** + * @cfg {Object/Ext.util.Grouper} grouper + * The grouper by which to group the data store. May also be specified by the {@link #groupField} config, however + * they should not be used together. + */ + grouper: null, + /** + * @cfg {Number} pageSize + * The number of records considered to form a 'page'. This is used to power the built-in + * paging using the nextPage and previousPage functions when the grid is paged using a + * {@link Ext.toolbar.Paging PagingToolbar} Defaults to 25. + * + * To disable paging, set the pageSize to `0`. + */ + pageSize: 25, + /** + * @cfg {Boolean} [autoSort=true] `true` to maintain sorted order when records + * are added regardless of requested insertion point, or when an item mutation + * results in a new sort position. + * + * This does not affect a ChainedStore's reaction to mutations of the source + * Store. If sorters are present when the source Store is mutated, this ChainedStore's + * sort order will always be maintained. + * @private + */ + autoSort: null, + /** + * @cfg {Boolean} reloadOnClearSorters + * Set this to `true` to trigger a reload when the last sorter is removed (only + * applicable when {@link #cfg!remoteSort} is `true`). + * + * By default, the store reloads itself when a sorter is added or removed. + * + * When the last sorter is removed, however, the assumption is that the data + * does not need to become "unsorted", and so no reload is triggered. + * + * If the server has a default order to which it reverts in the absence of any + * sorters, then it is useful to set this config to `true`. + * @since 6.5.1 + */ + reloadOnClearSorters: false + }, + /** + * @property {Number} currentPage + * The page that the Store has most recently loaded (see {@link Ext.data.Store#loadPage loadPage}) + */ + currentPage: 1, + /** + * @property {Boolean} loading + * `true` if the Store is currently loading via its Proxy. + * @private + */ + loading: false, + /** + * @property {Boolean} isStore + * `true` in this class to identify an object as an instantiated Store, or subclass thereof. + */ + isStore: true, + /** + * @property {Number} updating + * A counter that is increased by `beginUpdate` and decreased by `endUpdate`. When + * this transitions from 0 to 1 the `{@link #event-beginupdate beginupdate}` event is + * fired. When it transitions back from 1 to 0 the `{@link #event-endupdate endupdate}` + * event is fired. + * @readonly + * @since 5.0.0 + */ + updating: 0, + //documented above + constructor: function(config) { + var me = this, + storeId; + me.callParent([ + config + ]); + /** + * @event add + * Fired when a Model instance has been added to this Store. + * + * @param {Ext.data.Store} store The store. + * @param {Ext.data.Model[]} records The records that were added. + * @param {Number} index The index at which the records were inserted. + * @since 1.1.0 + */ + /** + * @event remove + * Fired when one or more records have been removed from this Store. + * + * **The signature for this event has changed in 5.0: ** + * + * @param {Ext.data.Store} store The Store object + * @param {Ext.data.Model[]} records The records that were removed. In previous + * releases this was a single record, not an array. + * @param {Number} index The index at which the records were removed. + * @param {Boolean} isMove `true` if the child node is being removed so it can be + * moved to another position in this Store. + * @since 5.0.0 + */ + /** + * @event update + * Fires when a Model instance has been updated. + * @param {Ext.data.Store} this + * @param {Ext.data.Model} record The Model instance that was updated + * @param {String} operation The update operation being performed. Value may be one of: + * + * Ext.data.Model.EDIT + * Ext.data.Model.REJECT + * Ext.data.Model.COMMIT + * @param {String[]} modifiedFieldNames Array of field names changed during edit. + * @param {Object} details An object describing the change. See the + * {@link Ext.util.Collection#event-itemchange itemchange event} of the store's backing collection + * @since 1.1.0 + */ + /** + * @event clear + * Fired after the {@link Ext.data.Store#removeAll removeAll} method is called. + * @param {Ext.data.Store} this + * @since 1.1.0 + */ + /** + * @event datachanged + * Fires for any data change in the store. This is a catch-all event that is typically fired + * in conjunction with other events (such as `add`, `remove`, `update`, `refresh`). + * @param {Ext.data.Store} this The data store + * @since 1.1.0 + */ + /** + * @event refresh + * Fires when the data cache has changed in a bulk manner (e.g., it has been sorted, filtered, etc.) and a + * widget that is using this Store as a Record cache should refresh its view. + * @param {Ext.data.Store} this The data store + */ + /** + * @event beginupdate + * Fires when the {@link #beginUpdate} method is called. Automatic synchronization as configured + * by the {@link Ext.data.ProxyStore#autoSync autoSync} flag is deferred until the {@link #endUpdate} method is called, so multiple + * mutations can be coalesced into one synchronization operation. + */ + /** + * @event endupdate + * Fires when the {@link #endUpdate} method is called. Automatic synchronization as configured + * by the {@link Ext.data.ProxyStore#autoSync autoSync} flag is deferred until the {@link #endUpdate} method is called, so multiple + * mutations can be coalesced into one synchronization operation. + */ + /** + * @event beforesort + * Fires before a store is sorted. + * + * For {@link #remoteSort remotely sorted} stores, this will be just before the load operation triggered by changing the + * store's sorters. + * + * For locally sorted stores, this will be just before the data items in the store's backing collection are sorted. + * @param {Ext.data.Store} store The store being sorted + * @param {Ext.util.Sorter[]} sorters Array of sorters applied to the store + */ + /** + * @event sort + * Fires after a store is sorted. + * + * For {@link #remoteSort remotely sorted} stores, this will be upon the success of a load operation triggered by + * changing the store's sorters. + * + * For locally sorted stores, this will be just after the data items in the store's backing collection are sorted. + * @param {Ext.data.Store} store The store being sorted + */ + me.isInitializing = true; + me.mixins.observable.constructor.call(me, config); + me.isInitializing = false; + storeId = me.getStoreId(); + if (!storeId && (config && config.id)) { + me.setStoreId(storeId = config.id); + } + if (storeId) { + Ext.data.StoreManager.register(me); + } + }, + /** + * Create a `Range` instance to access records by their index. + * + * @param {Object/Ext.data.Range} [config] + * @return {Ext.data.Range} + * @since 6.5.0 + */ + createActiveRange: function(config) { + var range = Ext.apply({ + store: this + }, config); + return new Ext.data.Range(range); + }, + /** + * @private + * Called from onCollectionItemsAdd. Collection add changes the items reference of the + * collection, and that array object if directly referenced by Ranges. The ranges + * have to refresh themselves upon add. + */ + syncActiveRanges: function() { + var activeRanges = this.activeRanges, + len = activeRanges && activeRanges.length, + i; + for (i = 0; i < len; i++) { + activeRanges[i].refresh(); + } + }, + /** + * Gets the number of records in store. + * + * If using paging, this may not be the total size of the dataset. If the data object + * used by the Reader contains the dataset size, then the {@link Ext.data.ProxyStore#getTotalCount} function returns + * the dataset size. **Note**: see the Important note in {@link Ext.data.ProxyStore#method-load}. + * + * When store is filtered, it's the number of records matching the filter. + * + * @return {Number} The number of Records in the Store. + */ + getCount: function() { + var data = this.getData(); + // We may be destroyed, in which case "data" will be null... best to just + // report 0 items vs throw an exception + return data ? data.getCount() : 0; + }, + /** + * Determines if the passed range is available in the page cache. + * @private + * @param {Number} start The start index + * @param {Number} end The end index in the range + */ + rangeCached: function(start, end) { + return this.getData().getCount() >= Math.max(start, end); + }, + /** + * Checks if a record is in the current active data set. + * @param {Ext.data.Model} record The record + * @return {Boolean} `true` if the record is in the current active data set. + * @method contains + */ + /** + * Finds the index of the first matching Record in this store by a specific field value. + * + * When store is filtered, finds records only within filter. + * + * **IMPORTANT + * + * If this store is {@link Ext.data.BufferedStore Buffered}, this can ONLY find records which happen to be cached in the page cache. + * This will be parts of the dataset around the currently visible zone, or recently visited zones if the pages + * have not yet been purged from the cache.** + * + * @param {String} property The name of the Record field to test. + * @param {String/RegExp} value Either a string that the field value + * should begin with, or a RegExp to test against the field. + * @param {Number} [startIndex=0] The index to start searching at + * @param {Boolean} [anyMatch=false] True to match any part of the string, not just the + * beginning. + * @param {Boolean} [caseSensitive=false] True for case sensitive comparison + * @param {Boolean} [exactMatch=false] True to force exact match (^ and $ characters + * added to the regex). Ignored if `anyMatch` is `true`. + * @return {Number} The matched index or -1 + */ + find: function(property, value, startIndex, anyMatch, caseSensitive, exactMatch) { + // exactMatch + // anyMatch F T + // F ^abc ^abc$ + // T abc abc + // + var startsWith = !anyMatch, + endsWith = !!(startsWith && exactMatch); + return this.getData().findIndex(property, value, startIndex, startsWith, endsWith, !caseSensitive); + }, + /** + * Finds the first matching Record in this store by a specific field value. + * + * When store is filtered, finds records only within filter. + * + * **IMPORTANT + * + * If this store is {@link Ext.data.BufferedStore Buffered}, this can ONLY find records which happen to be cached in the page cache. + * This will be parts of the dataset around the currently visible zone, or recently visited zones if the pages + * have not yet been purged from the cache.** + * + * @param {String} fieldName The name of the Record field to test. + * @param {String/RegExp} value Either a string that the field value + * should begin with, or a RegExp to test against the field. + * @param {Number} [startIndex=0] The index to start searching at + * @param {Boolean} [anyMatch=false] True to match any part of the string, not just the + * beginning. + * @param {Boolean} [caseSensitive=false] True for case sensitive comparison + * @param {Boolean} [exactMatch=false] True to force exact match (^ and $ characters + * added to the regex). Ignored if `anyMatch` is `true`. + * @return {Ext.data.Model} The matched record or null + */ + findRecord: function() { + var me = this, + index = me.find.apply(me, arguments); + return index !== -1 ? me.getAt(index) : null; + }, + /** + * Finds the index of the first matching Record in this store by a specific field value. + * + * When store is filtered, finds records only within filter. + * + * **IMPORTANT + * + * If this store is {@link Ext.data.BufferedStore Buffered}, this can ONLY find records which happen to be cached in the page cache. + * This will be parts of the dataset around the currently visible zone, or recently visited zones if the pages + * have not yet been purged from the cache.** + * + * @param {String} fieldName The name of the Record field to test. + * @param {Object} value The value to match the field against. + * @param {Number} [startIndex=0] The index to start searching at + * @return {Number} The matched index or -1 + */ + findExact: function(fieldName, value, startIndex) { + return this.getData().findIndexBy(function(rec) { + return rec.isEqual(rec.get(fieldName), value); + }, this, startIndex); + }, + /** + * Find the index of the first matching Record in this Store by a function. + * If the function returns `true` it is considered a match. + * + * When store is filtered, finds records only within filter. + * + * **IMPORTANT + * + * If this store is {@link Ext.data.BufferedStore Buffered}, this can ONLY find records which happen to be cached in the page cache. + * This will be parts of the dataset around the currently visible zone, or recently visited zones if the pages + * have not yet been purged from the cache.** + * + * @param {Function} fn The function to be called. It will be passed the following parameters: + * @param {Ext.data.Model} fn.record The record to test for filtering. Access field values + * using {@link Ext.data.Model#get}. + * @param {Object} fn.id The ID of the Record passed. + * @param {Object} [scope] The scope (this reference) in which the function is executed. + * Defaults to this Store. + * @param {Number} [start=0] The index at which to start searching. + * @return {Number} The matched index or -1 + */ + findBy: function(fn, scope, start) { + return this.getData().findIndexBy(fn, scope, start); + }, + /** + * Get the Record at the specified index. + * + * The index is effected by filtering. + * + * @param {Number} index The index of the Record to find. + * @return {Ext.data.Model} The Record at the passed index. Returns null if not found. + */ + getAt: function(index) { + return this.getData().getAt(index) || null; + }, + /** + * Gathers a range of Records between specified indices. + * + * This method is affected by filtering. + * + * @param {Number} start The starting index. Defaults to zero. + * @param {Number} end The ending index. Defaults to the last record. The end index + * **is included**. + * @param [options] (private) Used by BufferedRenderer when using a BufferedStore. + * @return {Ext.data.Model[]} An array of records. + */ + getRange: function(start, end, options) { + // Collection's getRange is exclusive. Do NOT mutate the value: it is passed to the callback. + var result = this.getData().getRange(start, Ext.isNumber(end) ? end + 1 : end); + // BufferedRenderer requests a range with a callback to process that range. + // Because it may be dealing with a buffered store and the range may not be available synchronously. + if (options && options.callback) { + options.callback.call(options.scope || this, result, start, end, options); + } + return result; + }, + /** + * Gets the filters for this store. + * @param {Boolean} [autoCreate] (private) + * @return {Ext.util.FilterCollection} The filters + */ + getFilters: function(autoCreate) { + var result = this.callParent(); + if (!result && autoCreate !== false) { + this.setFilters([]); + result = this.callParent(); + } + return result; + }, + applyFilters: function(filters, filtersCollection) { + var created; + if (!filtersCollection) { + filtersCollection = this.createFiltersCollection(); + created = true; + } + filtersCollection.add(filters); + if (created) { + this.onRemoteFilterSet(filtersCollection, this.getRemoteFilter()); + } + return filtersCollection; + }, + /** + * Gets the sorters for this store. + * @param {Boolean} [autoCreate] (private) + * @return {Ext.util.SorterCollection} The sorters + */ + getSorters: function(autoCreate) { + var result = this.callParent(); + if (!result && autoCreate !== false) { + // If not preventing creation, force it here + this.setSorters([]); + result = this.callParent(); + } + return result; + }, + applySorters: function(sorters, sortersCollection) { + var created; + if (!sortersCollection) { + sortersCollection = this.createSortersCollection(); + created = true; + } + sortersCollection.add(sorters); + if (created) { + this.onRemoteSortSet(sortersCollection, this.getRemoteSort()); + } + return sortersCollection; + }, + /** + * Filters the data in the Store by one or more fields. Example usage: + * + * //filter with a single field + * myStore.filter('firstName', 'Don'); + * + * //filtering with multiple filters + * myStore.filter([ + * { + * property : 'firstName', + * value : 'Don' + * }, + * { + * property : 'lastName', + * value : 'Griffin' + * } + * ]); + * + * Internally, Store converts the passed arguments into an array of + * {@link Ext.util.Filter} instances, and delegates the actual filtering to its internal + * {@link Ext.util.Collection} or the remote server. + * + * @param {String/Ext.util.Filter[]} [filters] Either a string name of one of the + * fields in this Store's configured {@link Ext.data.Model Model}, or an array of + * filter configurations. + * @param {String} [value] The property value by which to filter. Only applicable if + * `filters` is a string. + * @param {Boolean} [suppressEvent] (private) + */ + filter: function(filters, value, suppressEvent) { + if (Ext.isString(filters)) { + filters = { + property: filters, + value: value + }; + } + this.suppressNextFilter = !!suppressEvent; + this.getFilters().add(filters); + this.suppressNextFilter = false; + }, + /** + * Removes an individual Filter from the current {@link #cfg-filters filter set} + * using the passed Filter/Filter id and by default, applies the updated filter set + * to the Store's unfiltered dataset. + * + * @param {String/Ext.util.Filter} toRemove The id of a Filter to remove from the + * filter set, or a Filter instance to remove. + * @param {Boolean} [suppressEvent] If `true` the filter is cleared silently. + */ + removeFilter: function(toRemove, suppressEvent) { + var me = this, + filters = me.getFilters(); + me.suppressNextFilter = !!suppressEvent; + if (toRemove instanceof Ext.util.Filter) { + filters.remove(toRemove); + } else { + filters.removeByKey(toRemove); + } + me.suppressNextFilter = false; + }, + updateAutoSort: function(autoSort) { + // Keep collection synced with our autoSort setting + this.getData().setAutoSort(autoSort); + }, + updateRemoteSort: function(remoteSort) { + // Don't call the getter here, we don't want to force sorters to be created here. + // Also, applySorters calls getRemoteSort, which may trigger the initGetter. + this.onRemoteSortSet(this.getSorters(false), remoteSort); + }, + updateRemoteFilter: function(remoteFilter) { + this.onRemoteFilterSet(this.getFilters(false), remoteFilter); + }, + /** + * Adds a new Filter to this Store's {@link #cfg-filters filter set} and + * by default, applies the updated filter set to the Store's unfiltered dataset. + * @param {Object[]/Ext.util.Filter[]} filters The set of filters to add to the current {@link #cfg-filters filter set}. + * @param {Boolean} [suppressEvent] If `true` the filter is cleared silently. + */ + addFilter: function(filters, suppressEvent) { + this.suppressNextFilter = !!suppressEvent; + this.getFilters().add(filters); + this.suppressNextFilter = false; + }, + /** + * Filters by a function. The specified function will be called for each + * Record in this Store. If the function returns `true` the Record is included, + * otherwise it is filtered out. + * + * When store is filtered, most of the methods for accessing store data will be working only + * within the set of filtered records. The notable exception is {@link #getById}. + * + * @param {Function} fn The function to be called. It will be passed the following parameters: + * @param {Ext.data.Model} fn.record The record to test for filtering. Access field values + * using {@link Ext.data.Model#get}. + * @param {Object} [scope] The scope (this reference) in which the function is executed. + * Defaults to this Store. + */ + filterBy: function(fn, scope) { + this.getFilters().add({ + filterFn: fn, + scope: scope || this + }); + }, + /** + * Reverts to a view of the Record cache with no filtering applied. + * @param {Boolean} [suppressEvent] If `true` the filter is cleared silently. + * + * For a locally filtered Store, this means that the filter collection is cleared without firing the + * {@link #datachanged} event. + * + * For a remotely filtered Store, this means that the filter collection is cleared, but the store + * is not reloaded from the server. + */ + clearFilter: function(suppressEvent) { + var me = this, + filters = me.getFilters(false); + if (!filters || filters.getCount() === 0) { + return; + } + me.suppressNextFilter = !!suppressEvent; + filters.removeAll(); + me.suppressNextFilter = false; + }, + /** + * Tests whether the store currently has any active filters. + * @return {Boolean} `true` if the store is filtered. + */ + isFiltered: function() { + return this.getFilters().getCount() > 0; + }, + /** + * Tests whether the store currently has any active sorters. + * @return {Boolean} `true` if the store is sorted. + */ + isSorted: function() { + var sorters = this.getSorters(false); + return !!(sorters && sorters.length > 0) || this.isGrouped(); + }, + addFieldTransform: function(sorter) { + // Transform already specified, leave it + if (sorter.getTransform()) { + return; + } + var fieldName = sorter.getProperty(), + Model = this.getModel(), + field, sortType; + if (Model) { + field = Model.getField(fieldName); + sortType = field ? field.getSortType() : null; + } + if (sortType && sortType !== Ext.identityFn) { + sorter.setTransform(sortType); + } + }, + /** + * This method may be called to indicate the start of multiple changes to the store. + * + * Automatic synchronization as configured by the {@link Ext.data.ProxyStore#autoSync autoSync} flag is deferred + * until the {@link #endUpdate} method is called, so multiple mutations can be coalesced + * into one synchronization operation. + * + * Internally this method increments a counter that is decremented by `endUpdate`. It + * is important, therefore, that if you call `beginUpdate` directly you match that + * call with a call to `endUpdate` or you will prevent the collection from updating + * properly. + * + * For example: + * + * var store = Ext.StoreManager.lookup({ + * //... + * autoSync: true + * }); + * + * store.beginUpdate(); + * + * record.set('fieldName', 'newValue'); + * + * store.add(item); + * // ... + * + * store.insert(index, otherItem); + * //... + * + * // Interested parties will listen for the endupdate event + * store.endUpdate(); + * + * @since 5.0.0 + */ + beginUpdate: function() { + if (!this.updating++ && this.hasListeners.beginupdate) { + // jshint ignore:line + this.fireEvent('beginupdate'); + } + }, + /** + * This method is called after modifications are complete on a store. For details + * see `{@link #beginUpdate}`. + * @since 5.0.0 + */ + endUpdate: function() { + if (this.updating && !--this.updating) { + if (this.hasListeners.endupdate) { + this.fireEvent('endupdate'); + } + this.onEndUpdate(); + } + }, + /** + * @private + * Returns the grouping, sorting and filtered state of this Store. + */ + getState: function() { + var me = this, + sorters = [], + filters = me.getFilters(), + grouper = me.getGrouper(), + filterState, hasState, result; + // Create sorters config array. + me.getSorters().each(function(s) { + sorters[sorters.length] = s.getState(); + hasState = true; + }); + // Because we do not provide a filter changing mechanism, only statify the filters if they opt in. + // Otherwise filters would get "stuck". + if (me.statefulFilters && me.saveStatefulFilters) { + // If saveStatefulFilters is turned on then we know that the filter collection has changed since + // page load. Initiate the filterState as an empty stack, which is meaningful in itself. If there + // are any filter in the collection, persist them. + hasState = true; + filterState = []; + filters.each(function(f) { + filterState[filterState.length] = f.getState(); + }); + } + if (grouper) { + hasState = true; + } + // If there is any state to save, return it as an object + if (hasState) { + result = {}; + if (sorters.length) { + result.sorters = sorters; + } + if (filterState) { + result.filters = filterState; + } + if (grouper) { + result.grouper = grouper.getState(); + } + } + return result; + }, + /** + * @private + * Restores state to the passed state + */ + applyState: function(state) { + var me = this, + stateSorters = state.sorters, + stateFilters = state.filters, + stateGrouper = state.grouper; + if (stateSorters) { + me.getSorters().replaceAll(stateSorters); + } + if (stateFilters) { + // We found persisted filters so let's save stateful filters from this point forward. + me.saveStatefulFilters = true; + me.getFilters().replaceAll(stateFilters); + } + if (stateGrouper) { + me.setGrouper(stateGrouper); + } + }, + /** + * Get the Record with the specified id. + * + * This method is not affected by filtering, lookup will be performed from all records + * inside the store, filtered or not. + * + * @param {Mixed} id The id of the Record to find. + * @return {Ext.data.Model} The Record with the passed id. Returns null if not found. + * @method getById + */ + /** + * Returns true if the store has a pending load task. + * @return {Boolean} `true` if the store has a pending load task. + * @private + * @method + */ + hasPendingLoad: Ext.emptyFn, + /** + * Returns `true` if the Store has been loaded. + * @return {Boolean} `true` if the Store has been loaded. + * @method + */ + isLoaded: Ext.emptyFn, + /** + * Returns `true` if the Store is currently performing a load operation. + * @return {Boolean} `true` if the Store is currently loading. + * @method + */ + isLoading: Ext.emptyFn, + destroy: function() { + var me = this; + if (me.hasListeners.beforedestroy) { + me.fireEvent('beforedestroy', me); + } + me.destroying = true; + if (me.getStoreId()) { + Ext.data.StoreManager.unregister(me); + } + me.doDestroy(); + if (me.hasListeners.destroy) { + me.fireEvent('destroy', me); + } + me.destroying = false; + // This will finish the sequence and null object references + me.callParent(); + }, + /** + * Perform the Store destroying sequence. Override this method to add destruction + * behaviors to your custom Stores. + * + */ + doDestroy: Ext.emptyFn, + /** + * Sorts the data in the Store by one or more of its properties. Example usage: + * + * //sort by a single field + * myStore.sort('myField', 'DESC'); + * + * //sorting by multiple fields + * myStore.sort([ + * { + * property : 'age', + * direction: 'ASC' + * }, + * { + * property : 'name', + * direction: 'DESC' + * } + * ]); + * + * Internally, Store converts the passed arguments into an array of {@link Ext.util.Sorter} instances, and + * either delegates the actual sorting to its internal {@link Ext.util.Collection} or the remote server. + * + * When passing a single string argument to sort, Store maintains a ASC/DESC toggler per field, so this code: + * + * store.sort('myField'); + * store.sort('myField'); + * + * Is equivalent to this code, because Store handles the toggling automatically: + * + * store.sort('myField', 'ASC'); + * store.sort('myField', 'DESC'); + * + * @param {String/Ext.util.Sorter[]} [field] Either a string name of one of the + * fields in this Store's configured {@link Ext.data.Model Model}, or an array of + * sorter configurations. + * @param {"ASC"/"DESC"} [direction="ASC"] The overall direction to sort the data by. + * @param {"append"/"prepend"/"replace"/"multi"} [mode="replace"] + */ + sort: function(field, direction, mode) { + var me = this; + if (arguments.length === 0) { + if (me.getRemoteSort()) { + me.load(); + } else { + me.forceLocalSort(); + } + } else { + me.getSorters().addSort(field, direction, mode); + } + }, + // This is attached to the data Collection's beforesort event only if not remoteSort + // If remoteSort, the event is fired before the reload call in Ext.data.ProxyStore#load. + onBeforeCollectionSort: function(store, sorters) { + if (sorters) { + this.fireEvent('beforesort', this, sorters.getRange()); + } + }, + onSorterEndUpdate: function() { + var me = this, + fireSort = true, + sorters = me.getSorters(false), + sorterCount; + // If we're in the middle of grouping, it will take care of loading. + // If the collection is not instantiated yet, it's because we are constructing. + if (me.settingGroups || !sorters) { + return; + } + sorters = sorters.getRange(); + sorterCount = sorters.length; + if (me.getRemoteSort()) { + // Only reload if there are sorters left to influence the sort order. + // Unless reloadOnClearSorters is set to indicate that there's a default + // order used by the server which must be returned to when there is no + // explicit sort order. + if (sorters.length || me.getReloadOnClearSorters()) { + // The sort event will fire in the load callback; + fireSort = false; + me.load({ + callback: function() { + me.fireEvent('sort', me, sorters); + } + }); + } + } else if (sorterCount) { + me.fireEvent('datachanged', me); + me.fireEvent('refresh', me); + } + if (fireSort) { + // Sort event must fire when sorters collection is updated to empty. + me.fireEvent('sort', me, sorters); + } + }, + onFilterEndUpdate: function() { + var me = this, + suppressNext = me.suppressNextFilter, + filters = me.getFilters(false); + // If the collection is not instantiated yet, it's because we are constructing. + if (!filters) { + return; + } + if (me.getRemoteFilter()) { + me.getFilters().each(function(filter) { + if (filter.getInitialConfig().filterFn) { + Ext.raise('Unable to use a filtering function in conjunction with remote filtering.'); + } + }); + me.currentPage = 1; + if (!suppressNext) { + me.load(); + } + } else if (!suppressNext) { + me.fireEvent('datachanged', me); + me.fireEvent('refresh', me); + } + if (me.trackStateChanges) { + // We just mutated the filter collection so let's save stateful filters from this point forward. + me.saveStatefulFilters = true; + } + // This is not affected by suppressEvent. + me.fireEvent('filterchange', me, me.getFilters().getRange()); + }, + updateGroupField: function(field) { + if (field) { + this.setGrouper({ + property: field, + direction: this.getGroupDir() + }); + } else { + this.setGrouper(null); + } + }, + /** + * @method setFilters + */ + /** + * @method setSorters + */ + getGrouper: function() { + return this.getData().getGrouper(); + }, + /** + * Groups data inside the store. + * @param {String/Object} grouper Either a string name of one of the fields in this Store's + * configured {@link Ext.data.Model Model}, or an object, or a {@link Ext.util.Grouper grouper} configuration object. + * @param {String} [direction] The overall direction to group the data by. Defaults to the value of {@link #groupDir}. + */ + group: function(grouper, direction) { + var me = this, + sorters = me.getSorters(false), + change = grouper || (sorters && sorters.length), + data = me.getData(); + if (grouper && typeof grouper === 'string') { + grouper = { + property: grouper, + direction: direction || me.getGroupDir() + }; + } + me.settingGroups = true; + // The config system would reject this case as no change + // Assume the caller has changed a configuration of the Grouper + // and requires the sorting to be redone. + if (grouper === data.getGrouper()) { + data.updateGrouper(grouper); + } else { + data.setGrouper(grouper); + } + delete me.settingGroups; + if (change) { + if (me.getRemoteSort()) { + if (!me.isInitializing) { + me.load({ + scope: me, + callback: me.fireGroupChange + }); + } + } else { + me.fireEvent('datachanged', me); + me.fireEvent('refresh', me); + me.fireGroupChange(); + } + } else // groupchange event must fire when group is cleared. + // The Grouping feature forces a view refresh when changed to a null grouper + { + me.fireGroupChange(); + } + }, + fireGroupChange: function() { + if (!this.destroyed) { + this.fireEvent('groupchange', this, this.getGrouper()); + } + }, + /** + * Clear the store grouping + */ + clearGrouping: function() { + this.group(null); + }, + getGroupField: function() { + var grouper = this.getGrouper(), + group = ''; + if (grouper) { + group = grouper.getProperty(); + } + return group; + }, + /** + * Tests whether the store currently has an active grouper. + * @return {Boolean} `true` if the store is grouped. + */ + isGrouped: function() { + return !!this.getGrouper(); + }, + applyGrouper: function(grouper) { + this.group(grouper); + return this.getData().getGrouper(); + }, + /** + * Returns a collection of readonly sub-collections of your store's records + * with grouping applied. These sub-collections are maintained internally by + * the collection. + * + * See {@link #groupField}, {@link #groupDir}. Example for a store + * containing records with a color field: + * + * var myStore = Ext.create('Ext.data.Store', { + * groupField: 'color', + * groupDir : 'DESC' + * }); + * + * myStore.getGroups(); + * + * The above should result in the following format: + * + * [ + * { + * name: 'yellow', + * children: [ + * // all records where the color field is 'yellow' + * ] + * }, + * { + * name: 'red', + * children: [ + * // all records where the color field is 'red' + * ] + * } + * ] + * + * Group contents are affected by filtering. + * + * @return {Ext.util.Collection} The grouped data + */ + getGroups: function() { + return this.getData().getGroups(); + }, + onEndUpdate: Ext.emptyFn, + privates: { + _metaProperties: { + count: 'getCount', + first: 'first', + last: 'last', + loading: 'hasPendingLoad', + totalCount: 'getTotalCount' + }, + interpret: function(name) { + var me = this, + accessor = me._metaProperties[name]; + return accessor && me[accessor](); + }, + // e.g., me.getCount() + loadsSynchronously: Ext.privateFn, + onRemoteFilterSet: function(filters, remoteFilter) { + if (filters) { + filters[remoteFilter ? 'on' : 'un']('endupdate', 'onFilterEndUpdate', this); + } + }, + // If remoteSort is set, we react to the endUpdate of the sorters Collection by reloading + // if there are still some sorters, or we're configured to reload on sorter remove. + // If remoteSort is set, we do not need to listen for the data Collection's beforesort event. + // + // If local sorting, we do not need to react to the endUpdate of the sorters Collection. + // If local sorting, we listen for the data Collection's beforesort event to fire our beforesort event. + onRemoteSortSet: function(sorters, remoteSort) { + var me = this, + data; + if (sorters) { + sorters[remoteSort ? 'on' : 'un']('endupdate', 'onSorterEndUpdate', me); + data = me.getData(); + if (data) { + data[remoteSort ? 'un' : 'on']('beforesort', 'onBeforeCollectionSort', me); + } + } + } + }, + deprecated: { + 5: { + methods: { + destroyStore: function() { + this.destroy(); + } + } + } + } +}); + +/** + * This class hols the results of a validator for an `Ext.data.Model`. These objects are + * placed in an `Ext.data.ErrorCollection` and returned by `{@link Ext.data.Model#validate}`. + * + * Usually this class does not need to be instantiated directly - instances are instead created + * automatically when {@link Ext.data.Model#validate validate} on a model instance. + * + * @deprecated 5.0 Use `Ext.data.Validation` instead. + */ +Ext.define('Ext.data.Error', { + isError: true, + $configPrefixed: false, + // compat + config: { + /** + * @cfg {String} field + * The name of the field this error belongs to. + */ + field: null, + /** + * @cfg {String} message + * The message containing the description of the error. + */ + message: '' + }, + constructor: function(config) { + this.initConfig(config); + this.msg = this.message; + } +}); +// compat + +/** + * Wraps a collection of validation error responses and provides convenient functions for + * accessing and errors for specific fields. + * + * Usually this class does not need to be instantiated directly - instances are instead + * created automatically when {@link Ext.data.Model#validate validate} on a model instance: + * + * // Validate some existing model instance - in this case it returned 2 failures + * // messages + * + * var errors = myModel.validate(); + * errors.isValid(); //false + * + * errors.length; //2 + * errors.getByField('name'); // [{field: 'name', message: 'must be present'}] + * errors.getByField('title'); // [{field: 'title', message: 'is too short'}] + */ +Ext.define('Ext.data.ErrorCollection', { + extend: 'Ext.util.MixedCollection', + // not Ext.util.Collection due to API differences + alternateClassName: 'Ext.data.Errors', + requires: [ + 'Ext.data.Error' + ], + init: function(record) { + var me = this, + fields = record.fields, + data = record.data, + before, field, item, i, len, msg, val, name; + for (i = 0 , len = fields.length; i < len; ++i) { + field = fields[i]; + name = field.name; + val = data[name]; + if (field.validate && !field.validate.$nullFn) { + before = me.length; + msg = field.validate(val, null, me, record); + if (before === me.length && msg !== true) { + me.add(name, msg); + } + } + } + return me; + }, + add: function(key, value) { + var me = this, + defaultMessage = Ext.data.field.Field.defaultInvalidMessage, + obj = key, + // for single argument form + current; + if (Ext.isString(key)) { + obj = new Ext.data.Error({ + field: key, + message: value || defaultMessage + }); + } else { + if (!(obj.isError)) { + obj = new Ext.data.Error({ + field: obj.field || obj.name, + message: obj.error || obj.message || obj.msg || defaultMessage + }); + } + key = obj.field; + } + current = me.get(key); + if (current) { + if (Ext.isArray(current)) { + current.push(obj); + return current; + } + me.removeAtKey(key); + obj = [ + current, + obj + ]; + obj.field = key; + // Because the value we want in the collection is an array, we need to wrap it + // another layer of array or the base add method will add each element. + obj = [ + obj + ]; + } + return me.callParent([ + obj + ]); + }, + getKey: function(item) { + return item.field; + }, + /** + * Returns true if there are no errors in the collection + * @return {Boolean} + */ + isValid: function() { + return this.length === 0; + }, + /** + * Returns all of the errors for the given field + * @param {String} fieldName The field to get errors for + * @return {Object[]} All errors for the given field + */ + getByField: function(fieldName) { + var values = this.get(fieldName); + if (values && !Ext.isArray(values)) { + values = [ + values + ]; + } + return values || []; + } +}); + +/** + * Represents a read or write operation performed by a {@link Ext.data.proxy.Proxy Proxy}. + * Operation objects are used to enable communication between Stores and Proxies. + * Application developers should rarely need to interact with Operation objects directly. + * + * Several Operations can be batched together in a {@link Ext.data.Batch batch}. + */ +Ext.define('Ext.data.operation.Operation', { + alternateClassName: 'Ext.data.Operation', + isOperation: true, + config: { + /** + * @cfg {Boolean} synchronous + * True if this Operation is to be executed synchronously. This property is inspected by a + * {@link Ext.data.Batch Batch} to see if a series of Operations can be executed in parallel or not. + */ + synchronous: false, + /** + * @cfg {String} url + * The url for this operation. Typically this will be provided by a proxy and not configured here. + */ + url: '', + /** + * @cfg {Object} params + * Parameters to pass along with the request when performing the operation. + */ + params: undefined, + /** + * @cfg {Function} callback + * Function to execute when operation completed. + * @cfg {Ext.data.Model[]} callback.records Array of records. + * @cfg {Ext.data.operation.Operation} callback.operation The Operation itself. + * @cfg {Boolean} callback.success True when operation completed successfully. + */ + callback: undefined, + /** + * @cfg {Object} scope + * Scope for the {@link #callback} function. + */ + scope: undefined, + /** + * @cfg {Ext.data.ResultSet} resultSet + * The ResultSet for this operation. + * @accessor + */ + resultSet: null, + /** + * @private + * @cfg {Object} response + * The response for this operation. + */ + response: null, + /** + * @cfg {Ext.data.Request} request + * The request for this operation. + */ + request: null, + /** + * @cfg {Ext.data.Model[]} records + * The records associated with this operation. If this is a `read` operation, this will be + * `null` until data is returned from the {@link Ext.data.proxy.Proxy}. + */ + records: null, + /** + * @cfg {Object} id + * The id of the operation. + */ + id: undefined, + /** + * @cfg {Ext.data.proxy.Proxy} proxy + * The proxy for this operation + */ + proxy: null, + /** + * @cfg {Ext.data.Batch} + * The batch for this operation, if applicable + */ + batch: null, + /** + * @cfg {Function} recordCreator + * Passed to the reader, see {@link Ext.data.reader.Reader#read} + * @private + */ + recordCreator: null, + //We use this because in a lot of cases the developer can indirectly pass + // a callback/scope and that will get pushed on to the operation. As such, + // create our own hook for the callback that will fire first + /** + * @cfg {Function} internalCallback + * A callback to run before the {@link #callback}. + * @private + */ + internalCallback: null, + /** + * @cfg {Object} internalScope + * Scope to run the {@link #internalCallback} + * @private + */ + internalScope: null + }, + /** + * @property {Number} order + * This number is used by `{@link Ext.data.Batch#sort}` to order operations. Order of + * operations of the same type is determined by foreign-key dependencies. The array of + * operations is sorted by ascending (increasing) values of `order`. + * @private + * @readonly + * @since 5.0.0 + */ + order: 0, + /** + * @property {Number} foreignKeyDirection + * This number is used by `{@link Ext.data.Batch#sort}` to order operations of the + * same type. This value is multipled by the "entity rank" (which is determined by + * foreign-key dependencies) to invert the direction of the sort based on the type of + * operation. Only `Ext.data.operation.Destroy` overrides this value. + * @private + * @readonly + * @since 5.0.0 + */ + foreignKeyDirection: 1, + /** + * @property {Boolean} started + * The start status of this Operation. Use {@link #isStarted}. + * @readonly + * @private + */ + started: false, + /** + * @property {Boolean} running + * The run status of this Operation. Use {@link #isRunning}. + * @readonly + * @private + */ + running: false, + /** + * @property {Boolean} complete + * The completion status of this Operation. Use {@link #isComplete}. + * @readonly + * @private + */ + complete: false, + /** + * @property {Boolean} success + * Whether the Operation was successful or not. This starts as undefined and is set to true + * or false by the Proxy that is executing the Operation. It is also set to false by {@link #setException}. Use + * {@link #wasSuccessful} to query success status. + * @readonly + * @private + */ + success: undefined, + /** + * @property {Boolean} exception + * The exception status of this Operation. Use {@link #hasException} and see {@link #getError}. + * @readonly + * @private + */ + exception: false, + /** + * @property {String/Object} error + * The error object passed when {@link #setException} was called. This could be any object or primitive. + * @private + */ + error: undefined, + idPrefix: 'ext-operation-', + /** + * Creates new Operation object. + * @param {Object} config (optional) Config object. + */ + constructor: function(config) { + // This ugliness is here to prevent an issue when specifying scope + // as an object literal. The object will be pulled in as part of + // the merge() during initConfig which will change the object + // reference. As such, we attempt to fudge it here until we come + // up with a better solution for describing how specific config + // objects should behave during init() time. + var scope = config && config.scope; + this.initConfig(config); + if (config) { + config.scope = scope; + } + if (scope) { + this.setScope(scope); + this.initialConfig.scope = scope; + } + // We need an internal id to track operations in Proxy + this._internalId = Ext.id(this, this.idPrefix); + }, + getAction: function() { + return this.action; + }, + /** + * @private + * Executes the operation on the configured {@link #proxy}. + * @return {Ext.data.Request} The request object + */ + execute: function() { + var me = this, + request; + delete me.error; + delete me.success; + me.complete = me.exception = false; + me.setStarted(); + me.request = request = me.doExecute(); + if (request) { + request.setOperation(me); + } + return request; + }, + doExecute: Ext.emptyFn, + /** + * Aborts the processing of this operation on the {@link #proxy}. + * This is only valid for proxies that make asynchronous requests. + */ + abort: function() { + var me = this, + request = me.request; + if (me.running && request) { + me.getProxy().abort(request); + me.request = null; + } + }, + process: function(resultSet, request, response, autoComplete) { + var me = this; + autoComplete = autoComplete !== false; + me.setResponse(response); + me.setResultSet(resultSet); + if (resultSet.getSuccess()) { + me.doProcess(resultSet, request, response); + me.setSuccessful(autoComplete); + } else if (autoComplete) { + me.setException(resultSet.getMessage()); + } + }, + /** + * @private + * This private object is used to save on memory allocation. This instance is used to + * apply server record updates as part of a record commit performed by calling the + * set() method on the record. See doProcess. + */ + _commitSetOptions: { + convert: true, + commit: true + }, + /** + * Process records in the operation after the response is successful and the result + * set is parsed correctly. The base class implementation of this method is used by + * "create" and "update" operations to allow the server response to update the client + * side records. + * + * @param {Ext.data.ResultSet} resultSet The result set + * @param {Ext.data.Request} request The request + * @param {Object} response The response + * @protected + */ + doProcess: function(resultSet, request, response) { + var me = this, + commitSetOptions = me._commitSetOptions, + clientRecords = me.getRecords(), + clientLen = clientRecords.length, + clientIdProperty = clientRecords[0].clientIdProperty, + serverRecords = resultSet.getRecords(), + // a data array, not records yet + serverLen = serverRecords ? serverRecords.length : 0, + clientMap, serverRecord, clientRecord, i; + if (serverLen && clientIdProperty) { + // Linear pass over clientRecords to map them by their idProperty + clientMap = Ext.Array.toValueMap(clientRecords, 'id'); + // Linear pass over serverRecords to match them by clientIdProperty to the + // corresponding clientRecord (if one exists). + for (i = 0; i < serverLen; ++i) { + serverRecord = serverRecords[i]; + clientRecord = clientMap[serverRecord[clientIdProperty]]; + if (clientRecord) { + // Remove this one so we don't commit() on it next + delete clientMap[clientRecord.id]; + // Remove the clientIdProperty value since we don't want to store it + delete serverRecord[clientIdProperty]; + clientRecord.set(serverRecord, commitSetOptions); + } else // set & commit + { + Ext.log.warn('Ignoring server record: ' + Ext.encode(serverRecord)); + } + } + // Linear pass over any remaining client records. + for (i in clientMap) { + clientMap[i].commit(); + } + } else { + // Either no serverRecords or no clientIdProperty, so index correspondence is + // all we have to go on. If there is no serverRecord at a given index we just + // commit() the record. + for (i = 0; i < clientLen; ++i) { + clientRecord = clientRecords[i]; + if (serverLen === 0 || !(serverRecord = serverRecords[i])) { + // once i > serverLen then serverRecords[i] will be undefined... + clientRecord.commit(); + } else { + clientRecord.set(serverRecord, commitSetOptions); + } + } + } + }, + /** + * Marks the Operation as started. + */ + setStarted: function() { + this.started = this.running = true; + }, + /** + * Marks the Operation as completed. + */ + setCompleted: function() { + var me = this, + proxy = me.getProxy(); + me.complete = true; + me.running = false; + me.triggerCallbacks(); + // Store and proxy could be destroyed in callbacks + if (proxy && !proxy.destroyed) { + proxy.completeOperation(me); + } + }, + /** + * Marks the Operation as successful. + * @param {Boolean} [complete] `true` to also mark this operation + * as being complete See {@link #setCompleted}. + */ + setSuccessful: function(complete) { + this.success = true; + if (complete) { + this.setCompleted(); + } + }, + /** + * Marks the Operation as having experienced an exception. Can be supplied with an option error message/object. + * @param {String/Object} error (optional) error string/object + */ + setException: function(error) { + var me = this; + me.exception = true; + me.success = me.running = false; + me.error = error; + me.setCompleted(); + }, + triggerCallbacks: function() { + var me = this, + callback = me.getInternalCallback(); + // Call internal callback first (usually the Store's onProxyLoad method) + if (callback) { + callback.call(me.getInternalScope() || me, me); + me.setInternalCallback(null); + me.setInternalScope(null); + } + // Call the user's callback as passed to Store's read/write + if (callback = me.getCallback()) { + // Maintain the public API for callback + callback.call(me.getScope() || me, me.getRecords(), me, me.wasSuccessful()); + me.setCallback(null); + me.setScope(null); + } + }, + /** + * Returns true if this Operation encountered an exception (see also {@link #getError}) + * @return {Boolean} True if there was an exception + */ + hasException: function() { + return this.exception; + }, + /** + * Returns the error string or object that was set using {@link #setException} + * @return {String/Object} The error object + */ + getError: function() { + return this.error; + }, + /** + * Returns the {@link Ext.data.Model record}s associated with this operation. For read + * operations the records as set by the {@link Ext.data.proxy.Proxy Proxy} will be + * returned (returns `null` if the proxy has not yet set the records). + * + * For create, update, and destroy operations the operation's initially configured + * records will be returned, although the proxy may modify these records' data at some + * point after the operation is initialized. + * + * @return {Ext.data.Model[]} + */ + getRecords: function() { + var resultSet; + return this._records || ((resultSet = this.getResultSet()) ? resultSet.getRecords() : null); + }, + /** + * Returns true if the Operation has been started. Note that the Operation may have started AND completed, see + * {@link #isRunning} to test if the Operation is currently running. + * @return {Boolean} True if the Operation has started + */ + isStarted: function() { + return this.started; + }, + /** + * Returns true if the Operation has been started but has not yet completed. + * @return {Boolean} True if the Operation is currently running + */ + isRunning: function() { + return this.running; + }, + /** + * Returns true if the Operation has been completed + * @return {Boolean} True if the Operation is complete + */ + isComplete: function() { + return this.complete; + }, + /** + * Returns true if the Operation has completed and was successful + * @return {Boolean} True if successful + */ + wasSuccessful: function() { + return this.isComplete() && this.success === true; + }, + // success can be undefined + /** + * Checks whether this operation should cause writing to occur. + * @return {Boolean} Whether the operation should cause a write to occur. + */ + allowWrite: function() { + return true; + } +}); + +/** + * Encapsulates a create operation as performed by a {@link Ext.data.proxy.Proxy proxy}. + * + * This class is instantiated by {@link Ext.data.Store stores} and {@link Ext.data.Model records} and should + * not need to be instantiated in user code. + */ +Ext.define('Ext.data.operation.Create', { + extend: 'Ext.data.operation.Operation', + alias: 'data.operation.create', + action: 'create', + isCreateOperation: true, + order: 10, + config: { + recordCreator: Ext.identityFn + }, + doExecute: function() { + return this.getProxy().create(this); + } +}); + +/** + * Encapsulates a destroy operation as performed by a {@link Ext.data.proxy.Proxy proxy}. + * + * This class is instantiated by {@link Ext.data.Store stores} and {@link Ext.data.Model records} and should + * not need to be instantiated in user code. + */ +Ext.define('Ext.data.operation.Destroy', { + extend: 'Ext.data.operation.Operation', + alias: 'data.operation.destroy', + action: 'destroy', + isDestroyOperation: true, + order: 30, + foreignKeyDirection: -1, + doProcess: function() /* resultSet, request, response */ + { + var clientRecords = this.getRecords(), + clientLen = clientRecords.length, + i; + for (i = 0; i < clientLen; ++i) { + clientRecords[i].setErased(); + } + }, + doExecute: function() { + return this.getProxy().erase(this); + }, + getRecordData: function(record, operation) { + var data = {}, + idField = record.idField, + nameProperty = this.getNameProperty() || 'name'; + data[idField[nameProperty]] = record.id; + return data; + } +}); + +/** + * Encapsulates a read operation as performed by a {@link Ext.data.proxy.Proxy proxy}. + * + * This class is instantiated by {@link Ext.data.Store stores} and {@link Ext.data.Model records} and should + * not need to be instantiated in user code. + */ +Ext.define('Ext.data.operation.Read', { + extend: 'Ext.data.operation.Operation', + alias: 'data.operation.read', + action: 'read', + isReadOperation: true, + config: { + /** + * @cfg {Ext.util.Filter[]} filters + * Optional array of filter objects. Only applies to 'read' actions. + */ + filters: undefined, + /** + * @cfg {Ext.util.Sorter[]} sorters + * Optional array of sorter objects. Only applies to 'read' actions. + */ + sorters: undefined, + /** + * @cfg {Ext.util.Grouper} grouper + * Optional grouping configuration. Only applies to 'read' actions where grouping is desired. + */ + grouper: undefined, + /** + * @cfg {Number} start + * The start index (offset), used in paging when running a 'read' action. + */ + start: undefined, + /** + * @cfg {Number} limit + * The number of records to load. Used on 'read' actions when paging is being used. + */ + limit: undefined, + /** + * @cfg {Number} page + * The page for this operation. + */ + page: undefined, + /** + * @cfg {Boolean} addRecords + * Passed internally to loadRecords when the load completes + * @private + */ + addRecords: false + }, + doExecute: function() { + return this.getProxy().read(this); + }, + doProcess: Ext.emptyFn, + allowWrite: function() { + return false; + } +}); + +/** + * Encapsulates a update operation as performed by a {@link Ext.data.proxy.Proxy proxy}. + * + * This class is instantiated by {@link Ext.data.Store stores} and {@link Ext.data.Model records} and should + * not need to be instantiated in user code. + */ +Ext.define('Ext.data.operation.Update', { + extend: 'Ext.data.operation.Operation', + alias: 'data.operation.update', + action: 'update', + isUpdateOperation: true, + order: 20, + config: { + recordCreator: Ext.identityFn + }, + doExecute: function() { + return this.getProxy().update(this); + } +}); + +/** + * This class defines a series of static methods that are used on a + * {@link Ext.data.Field} for performing sorting. The methods cast the + * underlying values into a data type that is appropriate for sorting on + * that particular field. If a {@link Ext.data.Field#type} is specified, + * the sortType will be set to a sane default if the sortType is not + * explicitly defined on the field. The sortType will make any necessary + * modifications to the value and return it. + * + * - **`asText`** - Removes any tags and converts the value to a string + * - **`asUCText`** - Removes any tags and converts the value to an uppercase string + * - **`asUCString`** - Converts the value to an uppercase string + * - **`asDate`** - Converts the value into Unix epoch time + * - **`asFloat`** - Converts the value to a floating point number + * - **`asInt`** - Converts the value to an integer number + * + * It is also possible to create a custom sortType that can be used throughout + * an application. + * + * Ext.apply(Ext.data.SortTypes, { + * asPerson: function(person){ + * // expects an object with a first and last name property + * return person.lastName.toUpperCase() + person.firstName.toLowerCase(); + * } + * }); + * + * Ext.define('Employee', { + * extend: 'Ext.data.Model', + * fields: [{ + * name: 'person', + * sortType: 'asPerson' + * }, { + * name: 'salary', + * type: 'float' // sortType set to asFloat + * }] + * }); + * + * @singleton + */ +Ext.define('Ext.data.SortTypes', function() { + var me; + return { + singleton: true, + constructor: function() { + me = this; + }, + /** + * Default sort that does nothing + * @param {Object} s The value being converted + * @return {Object} The comparison value + */ + none: Ext.identityFn, + /** + * The regular expression used to strip commas + * @type {RegExp} + * @property + */ + stripCommasRe: /,/g, + /** + * The regular expression used to strip tags + * @type {RegExp} + * @property + */ + stripTagsRE: /<\/?[^>]+>/gi, + /** + * Strips all HTML tags to sort on text only + * @param {Object} s The value being converted + * @return {String} The comparison value + */ + asText: function(s) { + // If allowNull, return the Unicode null character. + return (s != null) ? String(s).replace(me.stripTagsRE, '') : '\x00'; + }, + /** + * Strips all HTML tags to sort on text only - Case insensitive + * @param {Object} s The value being converted + * @return {String} The comparison value + */ + asUCText: function(s) { + // If allowNull, return the Unicode null character. + return (s != null) ? String(s).toUpperCase().replace(me.stripTagsRE, '') : '\x00'; + }, + /** + * Case insensitive string + * @param {Object} s The value being converted + * @return {String} The comparison value + */ + asUCString: function(s) { + // If allowNull, return the Unicode null character. + return (s != null) ? String(s).toUpperCase() : '\x00'; + }, + /** + * Date sorting + * @param {Object} s The value being converted + * @return {Number} The comparison value + */ + asDate: function(s) { + if (!s) { + return 0; + } + if (Ext.isDate(s)) { + return s.getTime(); + } + return Date.parse(String(s)); + }, + /** + * Float sorting + * @param {Object} s The value being converted + * @return {Number} The comparison value + */ + asFloat: function(s) { + var val = parseFloat(String(s).replace(me.stripCommasRe, '')); + return isNaN(val) ? 0 : val; + }, + /** + * Integer sorting + * @param {Object} s The value being converted + * @return {Number} The comparison value + */ + asInt: function(s) { + var val = parseInt(String(s).replace(me.stripCommasRe, ''), 10); + return isNaN(val) ? 0 : val; + } + }; +}); + +/** + * The base class for validators to be used to validate {@link Ext.data.Field fields} in + * a {@link Ext.data.Model model}. + * + * The model will call the {@link #validate} method, which may be overridden by subclasses. + */ +Ext.define('Ext.data.validator.Validator', { + mixins: [ + 'Ext.mixin.Factoryable' + ], + alias: 'data.validator.base', + // also configures Factoryable + isValidator: true, + factoryConfig: { + cacheable: true + }, + /** + * @property {String} type + * A string representation of this format. + */ + type: 'base', + /** + * Creates new Validator. + * @param {Object/Function} config A config object. A function may also be passed, + * which will be used as the {@link #validate} method for this validator. + */ + constructor: function(config) { + if (typeof config === 'function') { + this.fnOnly = true; + this.validate = config; + } else { + this.initConfig(config); + } + }, + /** + * Validates the passed value. + * @param {Object} value The value + * @param {Ext.data.Model} record The record + * @return {Boolean/String} `true` if the value is valid. A string may be returned if the value + * is not valid, to indicate an error message. Any other non `true` value indicates the value + * is not valid. + */ + validate: function() { + return true; + }, + /** + * Creates a copy of this validator + * @private + * @return {Ext.data.validator.Validator} The clone + */ + clone: function() { + var me = this; + if (me.fnOnly) { + return new Ext.data.validator.Validator(me.validate); + } + return new me.self(me.getCurrentConfig()); + } +}, function(Validator) { + Ext.Factory.validator = Ext.Factory.dataValidator; +}); + +/** + * Fields are used to define the members of a Model. They aren't instantiated directly; + * instead, when we create a class that extends {@link Ext.data.Model}, it automatically + * creates Field instances for each field configured in a {@link Ext.data.Model Model}. + * For example, we might set up a model like this: + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [ + * 'name', 'email', + * { name: 'age', type: 'int' }, + * { name: 'gender', type: 'string', defaultValue: 'Unknown' } + * ] + * }); + * + * Four fields will have been created for the User Model - name, email, age and gender. + * Note that we specified a couple of different formats here; if we only pass in the string + * name of the field (as with name and email), the field is set up with the 'auto' type. + * It's as if we'd done this instead: + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [ + * { name: 'name', type: 'auto' }, + * { name: 'email', type: 'auto' }, + * { name: 'age', type: 'int' }, + * { name: 'gender', type: 'string', defaultValue: 'Unknown' } + * ] + * }); + * + * # Field Types + * + * Fields come in various types. When declaring a field, the `type` property is used to + * specify the type of `Field` derived class used to manage values. + * + * The predefined set of types are: + * + * - {@link Ext.data.field.Field auto} (Default, implies no conversion) + * - {@link Ext.data.field.String string} + * - {@link Ext.data.field.Integer int} + * - {@link Ext.data.field.Number number} + * - {@link Ext.data.field.Boolean boolean} + * - {@link Ext.data.field.Date date} + * + * # Conversion + * + * When reading fields it is often necessary to convert the values received before using + * them or storing them in records. To handle these cases there is the + * `{@link #method-convert convert}` method. This method is passed the received value (as + * well as the current record instance, but see below) and it returns the value to carry + * forward. + * + * For `auto` fields there is no `{@link #method-convert convert}` method. This is for + * efficiency. For other field types, there are often `convert` methods. You can provide + * a `{@link #cfg-convert convert}` config when the field is defined like this: + * + * { + * name: 'timestamp', + * + * convert: function (value) { + * return new Date(value); + * } + * } + * + * While this can be convenient, see below for details on defining Custom Types as that is + * often a better practice and avoids repeating these functions. + * + * Note that when a `defaultValue` is specified, it will also be passed through to + * `convert` (either to the `{@link #method-convert convert}` method or to the + * `{@link #cfg-convert convert} config)`. + * + * ## Calculated Values + * + * In some cases fields are the result of a calculation from other fields. Historically + * this was a second role for `{@link #method-convert convert}` but that has some short + * comings. The simpler solution is the `{@link #cfg-calculate calculate}` config. + * + * Values produced by `{@link #cfg-calculate calculate}` and `{@link #method-convert convert}` + * are stored in the record as with any other field. In fact, if we define a calculated + * "firstName" field and log out all of the data, we'll see this: + * + * var ed = Ext.create('User', { name: 'Ed Spencer' }); + * + * console.log(ed.data); + * + * //outputs this: + * { + * age: 0, + * email: "", + * firstName: "Ed", // calculated field + * gender: "Unknown", + * name: "Ed Spencer" + * } + * + * ### Using `calculate` + * + * { + * name: 'firstName', + * + * calculate: function (data) { + * return data.name.split(' ')[0]; + * } + * } + * + * Using `{@link #cfg-calculate calculate}` is the simplest and safest way to define a + * calculated field. The most important part of this is that, internally, the code of the + * supplied function is parsed to extract its dependencies. In this case, the "name" field + * is the only dependency. This means that "firstName" will only need to be recalculated + * when "name" is modified. + * + * **Note:** Fields used by the calculate method must be explicitly defined in the + * {@link Ext.data.Model#cfg-fields #fields} of the model. + * + * ### Using `convert` + * + * Following is the equivalent technique using `{@link #cfg-convert convert}` + * + * { + * name: 'firstName', + * + * convert: function (value, record) { + * return record.get('name').split(' ')[0]; + * }, + * + * depends: [ 'name' ] + * } + * + * When a `{@link #method-convert convert}` function accepts a 2nd argument (a reference to + * the record), it is considered a calculated field. If a `{@link #cfg-depends depends}` + * config is not provided then this field's dependencies are unknown. In this case, the + * `{@link #cfg-depends depends}` are provided as would be automatically determined with + * the `{@link #cfg-calculate calculate}` config. + * + * ### Updating + * + * Fields modified with the {@link Ext.data.Model#set set} method will have their stored + * value set using the convert / calculate method when present. + * + * For example: + * + * Ext.define('MyApp.model.Employee', { + * extend: 'Ext.data.Model', + * fields: [{ + * name: 'salary', + * convert: function (val) { + * var startingBonus = val * .1; + * return val + startingBonus; + * } + * }], + * convertOnSet: false + * }); + * + * var tina = Ext.create('MyApp.model.Employee', { + * salary: 50000 + * }); + * + * console.log(tina.get('salary')); // logs 55000 + * + * tina.set('salary', 60000); + * console.log(tina.get('salary')); // logs 60000 + * + * This default behavior can be disabled by setting the Model's + * `{@link Ext.data.Model#cfg-convertOnSet}` config to `false`. + * + * **Note:** convertOnSet `false` only prevents the convert / calculate call when the + * set `fieldName` param matches the field's `{@link #name}`. See + * {@link Ext.data.Model#convertOnSet convertOnSet} for additional details. + * + * ### Dependencies + * + * When a field's `{@link #method-convert convert}` method processes values from the record + * (vs. just the field's value), it is best to also provide a `depends` config as shown + * above. Fields that provide a `{@link #cfg-calculate calculate}` method must follow the + * proper form for using fields so that dependencies can be extracted. + * + * Calculated fields are processed after other fields based on their dependencies. Fields + * with `{@link #method-convert convert}` methods that use the provided record that do *not* + * specify a `{@link #cfg-depends depends}` config are processed as a group after all other + * fields since such converters can rely on anything in the record. The order of processing + * these fields with respect to each other is unspecified and should not be relied upon. + * + * # Serialization + * + * To handle the inverse scenario of `convert` there is the `serialize` method. This + * method is called to produce the value to send to a server based on the internal value + * as would be returned from `convert`. In most cases, these methods should "round trip" + * a value: + * + * assertEqual(value, field.serialize(field.convert(value))); + * + * By default, only `{@link Ext.data.field.Date date}` fields have a `serialize` method. + * Other types simply send their value unmodified. + * + * # Custom Types + * + * Developers may create their own application-specific data types by deriving from this + * class. This is typically much better than applying multiple configuration values on + * field instances as these often become repetitive. + * + * To illustrate, we define a "time" field type that stores a time-of-day represented as a + * number of minutes since Midnight. + * + * Ext.define('App.field.Time', { + * extend: 'Ext.data.field.Field', + * + * alias: 'data.field.time', + * + * timeFormat: 'g:i', + * + * convert: function (value) { + * if (value && Ext.isString(value)) { + * var date = Ext.Date.parse(value, this.timeFormat); + * if (!date) { + * return null; + * } + * return (date.getHours() - 1) * 60 + date.getMinutes(); + * } + * return value; + * } + * }); + * + * ## Validation + * + * Custom field types can override the `{@link #method-validate validate}` method or + * provide a set of `{@link #cfg-validators validators}`. + * + * Ext.define('App.field.PhoneNumber', { + * extend: 'Ext.data.field.Field', + * + * alias: 'data.field.phonenumber', + * + * // Match U.S. phone numbers for example purposes + * validators: { + * type: 'format', + * matcher: /\d{3}\-\d{3}\-\d{4}/ + * } + * }); + * + * Once the class is defined, fields can be declared using the new type (based on its + * `alias`) like so: + * + * Ext.define('App.model.PhoneCall', { + * fields: [ + * { name: 'startTime', type: 'time' }, + * { name: 'phoneNumber', type: 'phonenumber' } + * ] + * }); + */ +Ext.define('Ext.data.field.Field', { + mixins: [ + 'Ext.mixin.Factoryable' + ], + requires: [ + 'Ext.data.SortTypes', + 'Ext.data.validator.Validator' + ], + alternateClassName: 'Ext.data.Field', + alias: 'data.field.auto', + // also configures Factoryable + aliasPrefix: 'data.field.', + type: 'auto', + /** + * @property factoryConfig + * @inheritdoc + */ + factoryConfig: { + defaultProperty: 'name' + }, + isDataField: true, + isField: true, + // NOTE: We do not use "config: {}" here because these configs are simple, never really + // set after creation and expensive enough when processed per-instance that avoiding + // the overhead is worth while. Remember that a large app may have many dozens of + // entities in their data model and these may have many fields each. Easily hundreds + // of Field instances. Using config with inherited things (like convert methods) just + // pushes the set to the constructor where it needs to just be a normal method. + /** + * @cfg {Boolean} allowBlank + * @private + * + * Used for validating a {@link Ext.data.Model model}. Defaults to true. An empty value here will cause + * {@link Ext.data.Model}.{@link Ext.data.Model#isValid isValid} to evaluate to false. + */ + allowBlank: true, + /** + * @cfg {Boolean} allowNull + * + * Use when converting received data into a {@link Ext.data.field.Integer `int`}, + * {@link Ext.data.field.Number `float`}, {@link Ext.data.field.Boolean `bool`} + * or {@link Ext.data.field.String `string`} type. If the value cannot be + * parsed, `null` will be used if allowNull is true, otherwise a default value for + * that type will be used: + * + * - for `int` and `float` - `0`. + * - for `string` - `""`. + * - for `bool` - `false`. + * + * Note that when parsing of {@link Ext.data.field.Date `date`} type fails, the value + * will be `null` regardless of this setting. + */ + allowNull: false, + /** + * @cfg {Function} calculate + * This config defines a simple field calculation function. A calculate method only + * has access to the record data and should return the value of the calculated field. + * When provided in this way, the `depends` config is automatically determined by + * parsing the `calculate` function. For example: + * + * fields: [{ + * name: 'firstName', + * type: 'string' + * },{ + * name: 'lastName', + * type: 'string' + * },{ + * name: 'fullName', + * calculate: function (data) { + * return data.firstName + ' ' + data.lastName; + * } + * }] + * + * The above 'fullName' field is equivalent to: + * + * { + * name: 'fullName', + * convert: function (v, rec) { + * return rec.get('firstName') + ' ' + rec.get('lastName'); + * }, + * depends: ['firstName', 'lastName'] + * } + * + * The restrictions on form for a `calculate` method are that the accesses to field + * values must match the following regular expression (case insensitive): + * + * data.([a-z_][a-z0-9_]*) + * // where 'data' is the param passed to the calculate method + * + * The only advantage of a `calculate` method over a `convert` method is automatic + * determination of `depends`. + * + * **Note:** The use of calculate and {@link #method-convert} are exclusive. The + * calculate method will override the convert method if both are configured. + * + * **Note:** Fields used by the calculate method must be explicitly defined in the + * {@link Ext.data.Model#cfg-fields #fields} of the model. + * + * @param {Object} data An object with all values for each field in the parent + * model. See {@link Ext.data.Model#getData getData}. + * @return {Mixed} value The value of the calculated field + */ + /** + * @cfg {Function} convert + * If specified this config overrides the `{@link #method-convert convert}` method. + * See also `{@link #cfg-calculate calculate}` for simple field calculations. + * + * **Note:** The use of {@link #calculate} and convert are exclusive. The calculate + * method will override the convert method if both are configured. + */ + /** + * @cfg {Boolean} critical + * A critical field is a field that must always be sent to the server even if it has + * not changed. The most common example of such a field is the "id" of a record (see + * `{@link Ext.data.Model#idProperty}` but the + * `{@link Ext.data.Model#versionProperty}` is similarly a `critical` field. + */ + critical: false, + /** + * @property {String} defaultInvalidMessage + * The default message to present for an invalid field. + * @since 5.0.0 + */ + defaultInvalidMessage: 'This field is invalid', + /** + * @cfg {Object} defaultValue + * + * The default value used when the creating an instance from a raw data object, + * and the property referenced by the `{@link Ext.data.field.Field#mapping mapping}` + * does not exist in that data object. + * + * The value `undefined` prevents defaulting in a value. + */ + defaultValue: undefined, + /** + * @property {Ext.Class} definedBy + * The class (derived from {@link Ext.data.Model}) that defined this field. + * + * Ext.define('MyApp.models.Foo', { + * extend: 'Ext.data.Model', + * + * fields: [ + * { name: 'bar' } + * ], + * ... + * }); + * + * var barField = MyApp.models.Foo.getField('bar'); + * + * alert(barField.definedBy === MyApp.models.Foo); // alerts 'true' + * + * When a field is inherited, this value will reference the class that originally + * defined the field. + * + * Ext.define('MyApp.models.Base', { + * extend: 'Ext.data.Model', + * + * fields: [ + * { name: 'foo' } + * ], + * ... + * }); + * + * Ext.define('MyApp.models.Derived', { + * extend: 'MyApp.models.Base', + * + * fields: [ + * { name: 'bar' } + * ], + * ... + * }); + * + * var fooField = MyApp.models.Derived.getField('foo'); + * + * alert(fooField.definedBy === MyApp.models.Base); // alerts 'true' + */ + definedBy: null, + /** + * @cfg {String/String[]} depends + * The field name or names within the {@link Ext.data.Model Model} on which the value + * of this field depends, and from which a new value may be calculated. These values + * are the values used by the `convert` method. If you do not have a `convert` method + * then this config should not be specified. + * + * Before using this config you should consider if using a `calculate` method instead + * of a `convert` method would be simpler. + * + * Whenever any of the named fields are set using the {@link Ext.data.Model#set set} + * method, this fields will have its `convert` method called passing the + * {@link Ext.data.Model record} so that the dependent value can be calculated from + * all fields which it needs. + * + * For example, to display a person's full name, using two separate `firstName` and + * `lastName` fields, configure the name field like this: + * + * { + * name: 'name', + * + * // Will be called whenever forename or surname fields are set + * convert: function (v, rec) { + * return rec.get('firstName') + ' ' + rec.get('lastName'); + * }, + * + * depends: [ 'firstName', 'lastName' ], + * + * // It should not be returned to the server - it's not a database field + * persist: false + * } + * + * Note that if you do not want the calculated field to be part of the field set sent + * back to the server when the store is synchronized, you should configure the field + * with `persist` set to `false`. + */ + depends: null, + /** + * @property {Ext.data.field.Field[]} dependents + * This array tracks the fields that have indicated this field in their `depends` + * list. If no fields depend on this field, this will be `null`. + * @readonly + * @private + */ + dependents: null, + /** + * @cfg {String/Number/Function} mapping + * + * (Optional) A path expression for use by the {@link Ext.data.reader.Reader} + * implementation that is creating the {@link Ext.data.Model Model} to extract the + * Field value from the data object. If the path expression is the same as the field + * name, the mapping may be omitted. A function may be passed to do complex data + * extraction. The examples below are simple just to demonstrate the capability, + * typically, a function would not be used to extract such simple data. + * + * The form of the mapping expression depends on the Reader being used. + * + * - {@link Ext.data.reader.Json} + * + * The mapping is a string containing the javascript expression to reference the + * data from an element of the data item's + * {@link Ext.data.reader.Json#cfg-rootProperty rootProperty} Array. Defaults to + * the field name. If a function is passed, a single argument is received which + * contains the raw json object: + * + * // Server returns [{"name": "Foo", "age": 1}, {"name": "Bar", "age": 2}] + * mapping: function(data) { + * return data.name; + * } + * + * - {@link Ext.data.reader.Xml} + * + * The mapping is an {@link Ext.DomQuery} path to the data item relative to the DOM + * element that represents the {@link Ext.data.reader.Xml#record record}. Defaults + * to the field name. If a function is passed, a single argument is received which + * contains the record node: + * + * // Server returns Foo1Bar2 + * mapping: function(data) { + * return data.firstChild.textContent; + * } + * + * - {@link Ext.data.reader.Array} + * + * The mapping is a number indicating the Array index of the field's value. + * Defaults to the field specification's Array position. If a function is passed, a + * single argument is received which contains the child array. + * + * // Server returns [["Foo", 1], ["Bar", 2]] + * mapping: function(data) { + * return data[0]; + * } + * + * If a more complex value extraction strategy is required, then configure the Field + * with a {@link #cfg-convert} function. This is passed the whole row object, and may + * interrogate it in whatever way is necessary in order to return the desired data. + */ + mapping: null, + /** + * @cfg {String} name + * + * The name by which the field is referenced within the Model. This is referenced by, + * for example, the `dataIndex` property in column definition objects passed to + * {@link Ext.grid.property.HeaderContainer}. + * + * Note: In the simplest case, if no properties other than `name` are required, a + * field definition may consist of just a String for the field name. + */ + name: null, + /** + * @property {Number} ordinal + * + * The position of this field in the {@link Ext.data.Model} in which it was defined. + */ + ordinal: undefined, + /** + * @cfg {Boolean} persist + * + * False to exclude this field from the {@link Ext.data.Model#modified} fields in a + * record. This will also exclude the field from being written using a + * {@link Ext.data.writer.Writer}. This option is useful when fields are used to keep + * state on the client but do not need to be persisted to the server. + * + * Defaults to `false` for `calculated` fields and `true` otherwise. + */ + persist: null, + /** + * @cfg {String/Object} reference + * The {@link Ext.data.Model#entityName name} of the entity referenced by this field. + * In most databases, this relationship is represented by a "foreign key". That is, a + * value for such a field matches the value of the + * {@link Ext.data.Model#idProperty id} for an entity of this type. + * + * For further documentation, see {@link Ext.data.schema.Reference}. + */ + reference: null, + /** + * @cfg serialize + * @inheritdoc Ext.data.field.Field#method-serialize + */ + /** + * @cfg {String/Object/Function} summary + * The summary type for this field. This is used to calculate a + * summary value by the {@link Ext.data.Model Model}. + * + * - If a string, it should be an alias for one of the Ext.data.summary types. + * - If an object, a config for one of the Ext.data.summary types. + * - If a function, it should match the signature for + * {@link Ext.data.summary.Base#method-calculate calculate}. + * + * @since 6.5.0 + */ + summary: null, + /** + * @cfg {String} summaryField + * A field to use as the basis for calculating a summary. This is used in + * conjunction with the virtual summary fields. See + * {@link Ext.data.Model#cfg-summary}. + * + * @since 6.5.0 + * @private + */ + summaryField: '', + /** + * @cfg {Function/String} sortType + * + * A function which converts a Field's value to a comparable value in order to ensure + * correct sort ordering. + * + * Predefined functions are provided in {@link Ext.data.SortTypes}. A custom sort + * example: + * + * // current sort after sort we want + * // +-+------+ +-+------+ + * // |1|First | |1|First | + * // |2|Last | |3|Second| + * // |3|Second| |2|Last | + * // +-+------+ +-+------+ + * + * sortType: function(value) { + * switch (value.toLowerCase()) // native toLowerCase(): + * { + * case 'first': return 1; + * case 'second': return 2; + * default: return 3; + * } + * } + * + * May also be set to a String value, corresponding to one of the named sort types in + * {@link Ext.data.SortTypes}. + */ + /** + * @cfg {Boolean} [unique=false] + * `true` if the value of this field is unique amongst all instances. When used with a + * `reference` this describes a "one-to-one" relationship. It is almost always the + * case that a `unique` field cannot also be {@link #allowBlank nullable}. + */ + unique: false, + /** + * @cfg {Object[]} validators + * An array of {@link Ext.data.validator.Validator validators} for this field. These + * `validators` will only be passed a field value to validate. + */ + /** + * @property {Number} rank + * This is a 1-based value that describes the dependency order of this field. This is + * initialized to `null` (falsey) so we can cheaply topo-sort the fields of a class. + * @private + * @readonly + */ + rank: null, + /** + * @property {RegExp} stripRe + * A regular expression for stripping non-numeric characters from a numeric value. + * This should be overridden for localization. + * @readonly + * @protected + */ + stripRe: /[\$,%]/g, + /** + * @property {Boolean} calculated + * This property is `true` if this field has a `{@link #cfg-calculate calculate}` + * method or a `{@link #method-convert convert}` method that operates on the entire + * record as opposed to just the data value. This property is determined from the + * `length` of the `{@link #method-convert convert}` function which means this is + * *not* calculated: + * + * convert: function (value) { + * return ... + * } + * + * While this *is* calculated: + * + * convert: function (value, record) { + * return ... + * } + * + * **NOTE:** It is recommended for such fields to use + * `{@link #cfg-calculate calculate}` or explicitly specify the fields used by + * `{@link #method-convert convert}` using `{@link #cfg-depends depends}`. + * + * @readonly + */ + calculated: false, + /** + * @property {Boolean} evil + * This flag is set to true for fields that have `convert` methods which take the 2nd + * argument (the record) and do not specify a `depends` set. Good fields indicate the + * fields on which they depend (if any). + * @private + * @readonly + */ + evil: false, + /** + * @property {Boolean} identifier + * This property is set to `true` if this is an {@link Ext.data.Model#idProperty id} + * field. + * @readonly + */ + identifier: false, + onClassExtended: function(cls, data) { + var sortType = data.sortType, + proto = cls.prototype, + superValidators = proto.validators, + validators = data.validators; + if (sortType && Ext.isString(sortType)) { + proto.sortType = Ext.data.SortTypes[sortType]; + } + if (validators) { + // Force validators to be an array + if (!Ext.isArray(validators)) { + validators = [ + validators + ]; + } + delete data.validators; + // Need to join them + if (superValidators) { + validators = superValidators.concat(validators); + } + proto.validators = validators; + } + }, + argumentNamesRe: /^function\s*\(\s*([^,\)\s]+)/, + calculateRe: /[^\.a-z0-9_]([a-z_][a-z_0-9]*)\.([a-z_][a-z_0-9]*)/gi, + constructor: function(config) { + var me = this, + calculateRe = me.calculateRe, + calculate, calculated, defaultValue, sortType, depends, map, match, dataProp, str, fld, validators; + // NOTE: In bigger apps we create *lots* of these fellows so we really need to be + // very lean here. + if (config) { + if (Ext.isString(config)) { + me.name = config; + } else { + validators = config.validators; + if (validators) { + delete config.validators; + me.instanceValidators = validators; + } + Ext.apply(me, config); + } + } + if (!me.allowNull) { + me.allowNull = !!me.reference; + } + calculate = me.calculate; + depends = me.depends; + if (calculate) { + me.convert = me.doCalculate; + if (!depends) { + if (!(depends = calculate.$depends)) { + map = {}; + str = Ext.Function.toCode(calculate); + // strips comments in debug + calculate.$depends = depends = []; + match = me.argumentNamesRe.exec(str); + dataProp = match ? match[1] : 'data'; + while ((match = calculateRe.exec(str))) { + if (dataProp === match[1] && !map[fld = match[2]]) { + map[fld] = 1; + depends.push(fld); + } + } + } + me.depends = depends; + } + } + defaultValue = me.defaultValue; + if (me.convert) { + me.calculated = calculated = me.convert.length > 1; + me.evil = calculated && !depends; + } + if (me.persist === null) { + me.persist = !calculate; + } + sortType = me.sortType; + if (!me.sortType) { + me.sortType = Ext.data.SortTypes.none; + } else if (Ext.isString(sortType)) { + me.sortType = Ext.data.SortTypes[sortType]; + } + if (depends && typeof depends === 'string') { + me.depends = [ + depends + ]; + } + me.cloneDefaultValue = defaultValue !== undefined && (Ext.isDate(defaultValue) || Ext.isArray(defaultValue) || Ext.isObject(defaultValue)); + }, + setModelValidators: function(modelValidators) { + this._validators = null; + this.modelValidators = modelValidators; + }, + constructValidators: function(validators) { + if (validators) { + if (!(validators instanceof Array)) { + validators = [ + validators + ]; + } + var length = validators.length, + all = this._validators, + // we are inside getValidators so this is OK + i, item, validator, presence; + for (i = 0; i < length; ++i) { + item = validators[i]; + if (item.fn) { + item = item.fn; + } + validator = Ext.Factory.dataValidator(item); + if (!validator.isPresence) { + all.push(validator); + } else { + presence = validator; + } + } + if (presence) { + this.presence = [ + presence + ]; + } + } + }, + /** + * Compares two values to retrieve their relative position in sort order, taking into account + * any {@link #sortType}. Also see {@link #compare}. + * @param {Object} value1 The first value. + * @param {Object} value2 The second value. + * @return {Number} `-1` if `value1` is less than `value2`. `1` if `value1` is greater than `value2`. + * `0` otherwise. + */ + collate: function(value1, value2) { + var me = this, + lhs = value1, + rhs = value2; + if (me.sortType) { + lhs = me.sortType(lhs); + rhs = me.sortType(rhs); + } + return (lhs === rhs) ? 0 : ((lhs < rhs) ? -1 : 1); + }, + /** + * Compares two values to retrieve their relative position in sort order. Also see + * {@link #collate}. + * @param {Object} value1 The first value. + * @param {Object} value2 The second value. + * @return {Number} `-1` if `value1` is less than `value2`. `1` if `value1` is greater than `value2`. + * `0` otherwise. + */ + compare: function(value1, value2) { + return (value1 === value2) ? 0 : ((value1 < value2) ? -1 : 1); + }, + /** + * Tests whether two values are equal based on this field type. + * This uses the {@link #compare} method to determine equality, so + * this method should generally not be overridden. + * @param {Object} value1 The first value. + * @param {Object} value2 The second value. + * @return {Boolean} `true` if the values are equal. + */ + isEqual: function(value1, value2) { + return this.compare(value1, value2) === 0; + }, + /** + * A function which converts the value provided by the Reader into the value that will + * be stored in the record. This method can be overridden by a derived class or set as + * a `{@link #cfg-convert convert}` config. + * + * If configured as `null`, then no conversion will be applied to the raw data property + * when this Field is read. This will increase performance. but you must ensure that + * the data is of the correct type and does not *need* converting. + * + * Example of convert functions: + * + * function fullName(v, record){ + * return record.data.last + ', ' + record.data.first; + * } + * + * function location(v, record){ + * return !record.data.city ? '' : (record.data.city + ', ' + record.data.state); + * } + * + * Ext.define('Dude', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'fullname', convert: fullName}, + * {name: 'firstname', mapping: 'name.first'}, + * {name: 'lastname', mapping: 'name.last'}, + * {name: 'city', defaultValue: 'unknown'}, + * 'state', + * {name: 'location', convert: location} + * ] + * }); + * + * // create the data store + * var store = Ext.create('Ext.data.Store', { + * model: 'Dude', + * proxy: { + * type: 'memory', + * reader: { + * type: 'json', + * rootProperty: 'daRoot', + * totalProperty: 'total' + * } + * } + * }); + * + * var myData = [ + * { key: 1, + * name: { first: 'Fat', last: 'Albert' } + * // notice no city, state provided in data object + * }, + * { key: 2, + * name: { first: 'Barney', last: 'Rubble' }, + * city: 'Bedrock', state: 'Stoneridge' + * }, + * { key: 3, + * name: { first: 'Cliff', last: 'Claven' }, + * city: 'Boston', state: 'MA' + * } + * ]; + * + * @method + * @param {Mixed} value The data value as read by the Reader, if undefined will use + * the configured `defaultValue`. + * @param {Ext.data.Model} record The data object containing the Model as read so far + * by the Reader. Note that the Model may not be fully populated at this point as the + * fields are read in the order that they are defined. + * {@link Ext.data.Model#cfg-fields fields} array. + * @return {Mixed} The converted value for storage in the record. + */ + convert: null, + /** + * A function which converts the Model's value for this Field into a form which can be used by whatever {@link Ext.data.writer.Writer Writer} + * is being used to sync data with the server. + * + * @method + * @param {Mixed} value The Field's value - the value to be serialized. + * @param {Ext.data.Model} record The record being serialized. + * @return {String} The string that represents the Field's value. + */ + serialize: null, + /** + * Validates the passed value for this field. + * + * @param {Object} value The value to validate. + * @param {String} [separator] This string is passed if the caller wants all validation + * messages concatenated with this string between each. This can be handled as a + * "falsy" value because concatenating with no separator is seldom desirable. + * @param {Ext.data.ErrorCollection/Ext.util.Collection/Array} [errors] This parameter is + * passed if the caller wants all validation results individually added to the collection. + * @param {Ext.data.Model} record The record being validated + * @return {Boolean/String} `true` if the value is valid. A string may be returned if + * the value is not valid, to indicate an error message. Any other non `true` value + * indicates the value is not valid. This method is not implemented by default, + * subclasses may override it to provide an implementation. + * + * @protected + * @template + * @since 5.0.0 + */ + validate: function(value, separator, errors, record) { + var me = this, + validators = me.getValidators(), + result, presence; + presence = this.presence; + if (presence && (value == null || value === '')) { + result = me.validateGroup(presence, value, separator, errors, record); + if (result !== true) { + return result; + } + } + return me.validateGroup(validators, value, separator, errors, record); + }, + validateGroup: function(validators, value, separator, errors, record) { + var ret = '', + validator, length, i, result; + for (i = 0 , length = validators.length; i < length; ++i) { + validator = validators[i]; + result = validator.validate(value, record); + if (result !== true) { + result = result || this.defaultInvalidMessage; + if (errors) { + if (errors.isMixedCollection) { + errors.add(this.name, result); + } else if (errors.isCollection) { + errors.add(result); + } else { + errors.push(result); + } + ret = ret || result; + } else if (separator) { + if (ret) { + ret += separator; + } + ret += result; + } else { + ret = result; + break; + } + } + } + return ret || true; + }, + doCalculate: function(v, rec) { + return rec ? this.calculate(rec.data) : v; + }, + /** + * Gets the name for this field. See {@link #name}. + * @return {String} name + */ + getName: function() { + return this.name; + }, + /** + * Gets allowBlank for this field. See {@link #allowBlank}. + * @return {Boolean} allowBlank + */ + getAllowBlank: function() { + return this.allowBlank; + }, + /** + * Gets allowNull for this field. See {@link #allowNull}. + * @return {Boolean} allowNull + */ + getAllowNull: function() { + return this.allowNull; + }, + /** + * Gets converter for this field. See {@link #method-convert}. + * @return {Function} convert + */ + getConvert: function() { + return this.convert; + }, + /** + * Gets the defaultValue for this field. See {@link #defaultValue}. + * @return {Object} defaultValue + */ + getDefaultValue: function() { + return this.defaultValue; + }, + /** + * Gets the depends for this field. See {@link #depends}. + * @return {String[]} depends + */ + getDepends: function() { + return this.depends; + }, + /** + * Get the mapping for this field. See {@link #mapping}. + * @return {Object} mapping + */ + getMapping: function() { + return this.mapping; + }, + /** + * Checks if this field has a mapping applied. + * @return {Boolean} `true` if this field has a mapping. + */ + hasMapping: function() { + var map = this.mapping; + return !!(map || map === 0); + }, + /** + * Gets the persist for this field. See {@link #persist}. + * @return {Boolean} persist + */ + getPersist: function() { + return this.persist; + }, + /** + * Gets the sortType for this field. See {@link #sortType}. + * @return {Function} sortType + */ + getSortType: function() { + return this.sortType; + }, + /** + * Gets the summary for this field. See {@link #summary}. + * @return {Ext.data.summary.Base} The summary. + */ + getSummary: function() { + var me = this, + doneSummary = me.doneSummary, + summary = me.summary; + if (!doneSummary) { + me.doneSummary = true; + if (summary) { + me.summary = summary = Ext.Factory.dataSummary(summary); + } + } + return summary || null; + }, + /** + * Gets a string representation of the type of this field. + * @return {String} type + */ + getType: function() { + return 'auto'; + }, + privates: { + getValidators: function() { + var me = this, + validators = me._validators; + if (!validators) { + me._validators = validators = []; + me.constructValidators(me.validators); + me.constructValidators(me.modelValidators); + me.constructValidators(me.instanceValidators); + } + return validators; + } + }, + deprecated: { + 5.1: { + methods: { + /** + * @method getSortDir + * Gets the sortDir for this field. + * @return {String} sortDir + * @deprecated 5.1 Setting sortDir and calling getSortDir were never applied by the + * the Sorter. This functionality does not natively exist on field instances. + */ + getSortDir: function() { + return this.sortDir; + } + } + } + } +}); + +/** + * A data field that automatically {@link #convert converts} its value to a boolean. + * + * @example + * Ext.define('Task', { + * extend: 'Ext.data.Model', + * fields: [ + * { name: 'completed', type: 'boolean' } + * ] + * }); + * + * var record = Ext.create('Task', { completed: true }), + * value = record.get('completed'); + * + * Ext.toast("completed is " + value); + */ +Ext.define('Ext.data.field.Boolean', { + extend: 'Ext.data.field.Field', + alias: [ + 'data.field.bool', + 'data.field.boolean' + ], + isBooleanField: true, + /** + * @property [trueRe] + * Values matching this regular expression are considered `true`. + */ + trueRe: /^\s*(?:true|yes|on|1)\s*$/i, + convert: function(v) { + if (typeof v === 'boolean') { + return v; + } + if (this.allowNull && (v === undefined || v === null || v === '')) { + return null; + } + return this.trueRe.test(String(v)); + }, + getType: function() { + return 'bool'; + } +}); + +/** + * A data field that automatically {@link #convert converts} its value to a date. + * + * @example + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [ + * { name: 'birthDate', type: 'date' } + * ] + * }); + * + * var record = Ext.create('User', { birthDate: 'Tuesday, June 27, 2017' }), + * value = record.get('birthDate'); + * + * Ext.toast("birthDate is " + value); + */ +Ext.define('Ext.data.field.Date', { + extend: 'Ext.data.field.Field', + alias: 'data.field.date', + sortType: 'asDate', + isDateField: true, + /** + * @cfg {String} dateFormat + * + * Serves as a default for the {@link #dateReadFormat} and {@link #dateWriteFormat} config options. This + * will be used in place of those other configurations if not specified. + * + * A format string for the {@link Ext.Date#parse Ext.Date.parse} function, or "timestamp" if the value provided by + * the Reader is a UNIX timestamp, or "time" if the value provided by the Reader is a javascript millisecond + * timestamp. See {@link Ext.Date}. + * + * It is quite important to note that while this config is optional, it will default to using the base + * JavaScript Date object's `parse` function if not specified, rather than {@link Ext.Date#parse Ext.Date.parse}. + * This can cause unexpected issues, especially when converting between timezones, or when converting dates that + * do not have a timezone specified. The behavior of the native `Date.parse` is implementation-specific, and + * depending on the value of the date string, it might return the UTC date or the local date. __For this reason + * it is strongly recommended that you always specify an explicit date format when parsing dates.__ + */ + dateFormat: null, + /** + * @cfg {String} dateReadFormat + * Used when converting received data into a Date when the {@link #type} is specified as `"date"`. + * This configuration takes precedence over {@link #dateFormat}. + * See {@link #dateFormat} for more information. + */ + dateReadFormat: null, + /** + * @cfg {String} dateWriteFormat + * Provides a custom format when serializing dates with a {@link Ext.data.writer.Writer}. + * If this is not specified, the {@link #dateFormat} will be used. If no `dateFormat` + * is specified, 'timestamp' format is used. + * + * See the {@link Ext.data.writer.Writer} docs for more information on writing dates. + * + * **Note** It is not possible to use the standard date serialization pathway or {@link Ext#USE_NATIVE_JSON native browser JSON production} + * to use a {@link Ext.data.JsonWriter JsonWriter} to send Microsoft formated + * "JSON" dates. + * + * To use a {@link Ext.data.JsonWriter JsonWriter} to write dates in a JSON packet in + * the form `"\/Date(1357372800000)\/"` configure the field like this: + * + * { + * type: 'date', + * dateFormat: 'MS', // To parse incoming dates from server correctly + * serialize: null // Avoid formatting or conversion by the Writer + * } + * + * Then override the `Ext.JSON` date serialize function: + * + * Ext.JSON.encodeDate = function (d) { + * return '"' + Ext.Date.format(d, 'MS') + '"'; + * }; + */ + dateWriteFormat: null, + /** + * @cfg {Boolean} useStrict + * @since 6.2.0 + * Used to manually set strict date parsing on a per-field basis. If no `useStrict` + * is specified, will use value of {@link Ext.Date.useStrict} to determine how to + * process dates. + */ + compare: function(lhs, rhs) { + var lhsIsDate = lhs instanceof Date, + rhsIsDate = rhs instanceof Date, + result; + if (rhsIsDate && lhsIsDate) { + result = lhs.getTime() - rhs.getTime(); + if (result === 0) { + result = 0; + } else { + result = result < 0 ? -1 : 1; + } + } else if (lhsIsDate === rhsIsDate) { + result = 0; + } else { + result = lhsIsDate ? 1 : -1; + } + return result; + }, + convert: function(v) { + if (!v) { + return null; + } + // instanceof check ~10 times faster than Ext.isDate. Values here will not be + // cross-document objects + if (v instanceof Date) { + return v; + } + var dateFormat = this.dateReadFormat || this.dateFormat, + parsed; + if (dateFormat) { + return Ext.Date.parse(v, dateFormat, this.useStrict); + } + parsed = Date.parse(v); + return parsed ? new Date(parsed) : null; + }, + serialize: function(value) { + var result = null, + format; + if (Ext.isDate(value)) { + format = this.getDateWriteFormat(); + result = format ? Ext.Date.format(value, format) : value; + } + return result; + }, + /** + * Gets the dateFormat for this field. See {@link #dateFormat}. + * @return {String} dateFormat + */ + getDateFormat: function() { + return this.dateFormat; + }, + /** + * Gets the dateReadFormat for this field. See {@link #dateReadFormat}. + * @return {String} dateReadFormat + */ + getDateReadFormat: function() { + return this.dateReadFormat; + }, + /** + * Gets the dateWriteFormat for this field. See {@link #dateWriteFormat}. + * @return {String} dateWriteFormat + */ + getDateWriteFormat: function() { + var me = this; + if (me.hasOwnProperty('dateWriteFormat')) { + return me.dateWriteFormat; + } + if (me.hasOwnProperty('dateFormat')) { + return me.dateFormat; + } + return me.dateWriteFormat || me.dateFormat || 'timestamp'; + }, + getType: function() { + return 'date'; + } +}); + +/** + * A data field that automatically {@link #convert converts} its value to an integer. + * + * **Note:** As you can see in the example below, casting data as an integer + * can result in a loss of precision. (5.1 is converted to 5). + * + * @example + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [ + * { name: 'age', type: 'integer' } + * ] + * }); + * + * var record = Ext.create('User', { age: "5.1" }), + * value = record.get('age'); + * + * Ext.toast("age is " + value); + */ +Ext.define('Ext.data.field.Integer', { + extend: 'Ext.data.field.Field', + alias: [ + 'data.field.int', + 'data.field.integer' + ], + isNumeric: true, + isIntegerField: true, + numericType: 'int', + convert: function(v) { + // Handle values which are already numbers. + // Value truncation behaviour of parseInt is historic and must be maintained. + // parseInt(35.9) and parseInt("35.9") returns 35 + if (typeof v === 'number') { + return this.getNumber(v); + } + var empty = v == null || v === '', + allowNull = this.allowNull, + out; + if (empty) { + out = allowNull ? null : 0; + } else { + out = this.parse(v); + if (allowNull && isNaN(out)) { + out = null; + } + } + return out; + }, + getNumber: function(v) { + return parseInt(v, 10); + }, + getType: function() { + return this.numericType; + }, + parse: function(v) { + return parseInt(String(v).replace(this.stripRe, ''), 10); + }, + sortType: function(s) { + // If allowNull, null values needed to be sorted last. + if (s == null) { + s = Infinity; + } + return s; + } +}); + +/** + * A data field that automatically {@link #convert converts} its value to a floating-point + * number. + * + * @example + * Ext.define('Product', { + * extend: 'Ext.data.Model', + * fields: [ + * { name: 'price', type: 'number' } + * ] + * }); + * + * var record = Ext.create('Product', { price: "5.1" }), + * value = record.get('price'); + * + * Ext.toast("price is " + value); + */ +Ext.define('Ext.data.field.Number', { + extend: 'Ext.data.field.Integer', + alias: [ + 'data.field.float', + 'data.field.number' + ], + isIntegerField: false, + isNumberField: true, + numericType: 'float', + getNumber: Ext.identityFn, + parse: function(v) { + return parseFloat(String(v).replace(this.stripRe, '')); + } +}); + +/** + * A data field that automatically {@link #convert converts} its value to a string. + * + * @example + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [ + * { name: 'firstName', type: 'string' } + * ] + * }); + * + * var record = Ext.create('User', { firstName: "Phil" }), + * value = record.get('firstName'); + * + * Ext.toast("firstName is " + value); + */ +Ext.define('Ext.data.field.String', { + extend: 'Ext.data.field.Field', + alias: 'data.field.string', + sortType: 'asUCString', + isStringField: true, + convert: function(v) { + var defaultValue = this.allowNull ? null : ''; + return (v === undefined || v === null) ? defaultValue : String(v); + }, + getType: function() { + return 'string'; + } +}); + +/** + * This class is a base for all id generators. It also provides lookup of id generators by + * their id. + * + * Generally, id generators are used to generate a primary key for new model instances. There + * are different approaches to solving this problem, so this mechanism has both simple use + * cases and is open to custom implementations. A {@link Ext.data.Model} requests id generation + * using the {@link Ext.data.Model#identifier} property. + * + * The following types of `identifiers` are provided: + * + * * `{@link Ext.data.identifier.Sequential sequential}` + * * `{@link Ext.data.identifier.Negative negative}` + * * `{@link Ext.data.identifier.Uuid uuid}` + * + * In most cases (other than `uuid`), the server is the only party that can generate + * authoritative id values. This means that any id generated by an `identifier` should be + * consider "provisional" and must eventually be reconciled with the server. This makes a + * `uuid` very attractive as an `identifier` because they are designed to be generated in + * a distributed manner and therefore never require reconciliation. + * + * It is common for id values to be generated as increasing integer values (1, 2, etc.) by + * the server when records are inserted. A `{@link Ext.data.identifier.Negative negative}` + * `identifier` may be useful as it generates client-side values of -1, -2, etc.. These + * values are of the same data type (integer) and so can typically be read by servers + * using typed languages (such as Java or C#) and easily recognized as provisional. + * + * In the end, the choice of `identifier` strategy requires agreement between client and + * server. + * + * # Identity, Type and Shared Generators + * + * It is often desirable to share Generators to ensure uniqueness or common configuration. + * This is done by giving Generator instances an id property by which they can be looked + * up using the {@link Ext.Factory#dataIdentifier dataIdentifier} method. To configure two {@link Ext.data.Model Model} classes + * to share one {@link Ext.data.identifier.Sequential sequential} id generator, you simply + * assign them the same id: + * + * Ext.define('MyApp.data.MyModelA', { + * extend: 'Ext.data.Model', + * identifier: { + * type: 'sequential', + * id: 'foo' + * } + * }); + * + * Ext.define('MyApp.data.MyModelB', { + * extend: 'Ext.data.Model', + * identifier: { + * type: 'sequential', + * id: 'foo' + * } + * }); + * + * To make this as simple as possible for generator types that are shared by many (or all) + * Models, the Generator types (such as 'sequential' or 'uuid') are also reserved as + * generator ids. This is used by the {@link Ext.data.identifier.Uuid} which has an id equal + * to its type ('uuid'). In other words, the following Models share the same generator: + * + * Ext.define('MyApp.data.MyModelX', { + * extend: 'Ext.data.Model', + * identifier: 'uuid' + * }); + * + * Ext.define('MyApp.data.MyModelY', { + * extend: 'Ext.data.Model', + * identifier: 'uuid' + * }); + * + * This can be overridden (by specifying the id explicitly), but there is no particularly + * good reason to do so for this generator type. + * + * # Creating Custom Generators + * + * An id generator should derive from this class and implement the {@link #generate} method. + * + * To register an id generator type, a derived class should provide an `alias` like so: + * + * Ext.define('MyApp.data.identifier.Custom', { + * extend: 'Ext.data.identifier.Generator', + * alias: 'data.identifier.custom', + * config: { + * configProp: 42 // some config property w/default value + * } + * + * generate: function () { + * return ... // a new id + * } + * }); + * + * Using the custom id generator is then straightforward: + * + * Ext.define('MyApp.data.MyModel', { + * extend: 'Ext.data.Model', + * identifier: 'custom' + * }); + * // or... + * + * Ext.define('MyApp.data.MyModel', { + * extend: 'Ext.data.Model', + * identifier: { + * type: 'custom', + * configProp: value + * } + * }); + * + * It is not recommended to mix shared generators with generator configuration. This leads + * to unpredictable results unless all configurations match (which is also redundant). In + * such cases, a custom generator with a default id is the best approach. + * + * Ext.define('MyApp.data.identifier.Custom', { + * extend: 'Ext.data.identifier.Sequential', + * alias: 'data.identifier.custom', + * + * config: { + * id: 'custom', + * prefix: 'ID_', + * seed: 1000 + * } + * }); + * + * Ext.define('MyApp.data.MyModelX', { + * extend: 'Ext.data.Model', + * identifier: 'custom' + * }); + * + * Ext.define('MyApp.data.MyModelY', { + * extend: 'Ext.data.Model', + * identifier: 'custom' + * }); + * + * // the above models share a generator that produces ID_1000, ID_1001, etc.. + * + */ +Ext.define('Ext.data.identifier.Generator', { + 'abstract': true, + mixins: [ + 'Ext.mixin.Factoryable' + ], + alias: 'data.identifier.default', + // this is used by Factoryable + factoryConfig: { + defaultType: 'sequential' + }, + // this is not a suitable type to create + /** + * @property {Boolean} isGenerator + * `true` in this class to identify an object as an instantiated IdGenerator, or subclass thereof. + */ + isGenerator: true, + config: { + /** + * @cfg {String} id + * The id for this generator. + */ + id: null + }, + /** + * Initializes a new instance. + * @param {Object} config (optional) Configuration object to be applied to the new instance. + */ + constructor: function(config) { + var me = this, + id; + me.initConfig(config); + id = me.getId(); + if (id) { + Ext.data.identifier.Generator.all[id] = me; + } + }, + /** + * Generates and returns the next id. This method must be implemented by the derived + * class. + * + * @return {Number/String} The next id. + * @method generate + * @abstract + */ + privates: { + /** + * Create a copy of this identifier. + * @private + * @return {Ext.data.identifier.Generator} The clone + */ + clone: function(config) { + var cfg = this.getInitialConfig(); + cfg = config ? Ext.apply({}, config, cfg) : cfg; + return new this.self(cfg); + }, + statics: { + /** + * @property {Object} all + * This object is keyed by id to lookup instances. + * @private + * @static + */ + all: {} + } + } +}, function() { + var Generator = this, + Factory = Ext.Factory, + factory = Factory.dataIdentifier; + // If there is an id property passed we need to lookup that id in the cache. If that + // produces a cache miss, call the normal factory. + /** + * @member Ext.Factory + * @method dataIdentifier + * Returns an instance of an ID generator based on the ID you pass in. + * @param {String/Object} config The config object or `id` to lookup. + * @return {Object} Ext.data.identifier.* The data identifier + */ + Factory.dataIdentifier = function(config) { + var id = Ext.isString(config) ? config : (config && config.id), + existing = id && Generator.all[id]; + return existing || factory(config); + }; +}); + +/** + * This class is a sequential id generator. A simple use of this class would be like so: + * + * Ext.define('MyApp.data.MyModel', { + * extend: 'Ext.data.Model', + * identifier: 'sequential' + * }); + * // assign id's of 1, 2, 3, etc. + * + * An example of a configured generator would be: + * + * Ext.define('MyApp.data.MyModel', { + * extend: 'Ext.data.Model', + * identifier: { + * type: 'sequential', + * prefix: 'ID_', + * seed: 1000, + * increment: 10 + * } + * }); + * // assign id's of ID_1000, ID_1010, ID_1020, etc. + * + */ +Ext.define('Ext.data.identifier.Sequential', { + extend: 'Ext.data.identifier.Generator', + alias: 'data.identifier.sequential', + config: { + /** + * @cfg {Number} increment + * The number by which to adjust the `seed` after for the next sequential id. + */ + increment: 1, + /** + * @cfg {String} prefix + * The string to place in front of the sequential number for each generated id. + */ + prefix: null, + /** + * @cfg {Number} seed + * The number at which to start generating sequential id's. + */ + seed: 1 + }, + /** + * Generates and returns the next id. + * @return {String/Number} The next id. If a {@link #prefix} was specified, returns + * a String, otherwise returns a Number. + */ + generate: function() { + var me = this, + seed = me._seed, + prefix = me._prefix; + me._seed += me._increment; + return (prefix !== null) ? prefix + seed : seed; + } +}); + +/** + * A Model or Entity represents some object that your application manages. For example, one + * might define a Model for Users, Products, Cars, or other real-world object that we want + * to model in the system. Models are used by {@link Ext.data.Store stores}, which are in + * turn used by many of the data-bound components in Ext. + * + * # Fields + * + * Models are defined as a set of fields and any arbitrary methods and properties relevant + * to the model. For example: + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'name', type: 'string'}, + * {name: 'age', type: 'int', convert: null}, + * {name: 'phone', type: 'string'}, + * {name: 'alive', type: 'boolean', defaultValue: true, convert: null} + * ], + * + * changeName: function() { + * var oldName = this.get('name'), + * newName = oldName + " The Barbarian"; + * + * this.set('name', newName); + * } + * }); + * + * Now we can create instances of our User model and call any model logic we defined: + * + * var user = Ext.create('User', { + * id : 'ABCD12345', + * name : 'Conan', + * age : 24, + * phone: '555-555-5555' + * }); + * + * user.changeName(); + * user.get('name'); //returns "Conan The Barbarian" + * + * By default, the built in field types such as number and boolean coerce string values + * in the raw data by virtue of their {@link Ext.data.field.Field#method-convert} method. + * When the server can be relied upon to send data in a format that does not need to be + * converted, disabling this can improve performance. The {@link Ext.data.reader.Json Json} + * and {@link Ext.data.reader.Array Array} readers are likely candidates for this + * optimization. To disable field conversions you simply specify `null` for the field's + * {@link Ext.data.field.Field#cfg-convert convert config}. + * + * ## The "id" Field and `idProperty` + * + * A Model definition always has an *identifying field* which should yield a unique key + * for each instance. By default, a field named "id" will be created with a + * {@link Ext.data.Field#mapping mapping} of "id". This happens because of the default + * {@link #idProperty} provided in Model definitions. + * + * To alter which field is the identifying field, use the {@link #idProperty} config. + * + * # Validators + * + * Models have built-in support for field validators. Validators are added to models as in + * the follow example: + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [ + * { name: 'name', type: 'string' }, + * { name: 'age', type: 'int' }, + * { name: 'phone', type: 'string' }, + * { name: 'gender', type: 'string' }, + * { name: 'username', type: 'string' }, + * { name: 'alive', type: 'boolean', defaultValue: true } + * ], + * + * validators: { + * age: 'presence', + * name: { type: 'length', min: 2 }, + * gender: { type: 'inclusion', list: ['Male', 'Female'] }, + * username: [ + * { type: 'exclusion', list: ['Admin', 'Operator'] }, + * { type: 'format', matcher: /([a-z]+)[0-9]{2,3}/i } + * ] + * } + * }); + * + * The derived type of `Ext.data.field.Field` can also provide validation. If `validators` + * need to be duplicated on multiple fields, instead consider creating a custom field type. + * + * ## Validation + * + * The results of the validators can be retrieved via the "associated" validation record: + * + * var instance = Ext.create('User', { + * name: 'Ed', + * gender: 'Male', + * username: 'edspencer' + * }); + * + * var validation = instance.getValidation(); + * + * The returned object is an instance of `Ext.data.Validation` and has as its fields the + * result of the field `validators`. The validation object is "dirty" if there are one or + * more validation errors present. + * + * This record is also available when using data binding as a "pseudo-association" called + * "validation". This pseudo-association can be hidden by an explicitly declared + * association by the same name (for compatibility reasons), but doing so is not + * recommended. + * + * The `{@link Ext.Component#modelValidation}` config can be used to enable automatic + * binding from the "validation" of a record to the form fields that may be bound to its + * values. + * + * # Associations + * + * Models often have associations with other Models. These associations can be defined by + * fields (often called "foreign keys") or by other data such as a many-to-many (or "matrix"). + * See {@link Ext.data.schema.Association} for information about configuring and using associations. + * + * # Using a Proxy + * + * Models are great for representing types of data and relationships, but sooner or later we're going to want to load or + * save that data somewhere. All loading and saving of data is handled via a {@link Ext.data.proxy.Proxy Proxy}, which + * can be set directly on the Model: + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: ['id', 'name', 'email'], + * + * proxy: { + * type: 'rest', + * url : '/users' + * } + * }); + * + * Here we've set up a {@link Ext.data.proxy.Rest Rest Proxy}, which knows how to load and save data to and from a + * RESTful backend. Let's see how this works: + * + * var user = Ext.create('User', {name: 'Ed Spencer', email: 'ed@sencha.com'}); + * + * user.save(); //POST /users + * + * Calling {@link #save} on the new Model instance tells the configured RestProxy that we wish to persist this Model's + * data onto our server. RestProxy figures out that this Model hasn't been saved before because it doesn't have an id, + * and performs the appropriate action - in this case issuing a POST request to the url we configured (/users). We + * configure any Proxy on any Model and always follow this API - see {@link Ext.data.proxy.Proxy} for a full list. + * + * Loading data via the Proxy is accomplished with the static `load` method: + * + * //Uses the configured RestProxy to make a GET request to /users/123 + * User.load(123, { + * success: function(user) { + * console.log(user.getId()); //logs 123 + * } + * }); + * + * Models can also be updated and destroyed easily: + * + * //the user Model we loaded in the last snippet: + * user.set('name', 'Edward Spencer'); + * + * //tells the Proxy to save the Model. In this case it will perform a PUT request to /users/123 as this Model already has an id + * user.save({ + * success: function() { + * console.log('The User was updated'); + * } + * }); + * + * //tells the Proxy to destroy the Model. Performs a DELETE request to /users/123 + * user.erase({ + * success: function() { + * console.log('The User was destroyed!'); + * } + * }); + * + * # HTTP Parameter names when using a {@link Ext.data.proxy.Ajax Ajax proxy} + * + * By default, the model ID is specified in an HTTP parameter named `id`. To change the + * name of this parameter use the Proxy's {@link Ext.data.proxy.Ajax#idParam idParam} + * configuration. + * + * Parameters for other commonly passed values such as + * {@link Ext.data.proxy.Ajax#pageParam page number} or + * {@link Ext.data.proxy.Ajax#startParam start row} may also be configured. + * + * # Usage in Stores + * + * It is very common to want to load a set of Model instances to be displayed and manipulated in the UI. We do this by + * creating a {@link Ext.data.Store Store}: + * + * var store = Ext.create('Ext.data.Store', { + * model: 'User' + * }); + * + * //uses the Proxy we set up on Model to load the Store data + * store.load(); + * + * A Store is just a collection of Model instances - usually loaded from a server somewhere. Store can also maintain a + * set of added, updated and removed Model instances to be synchronized with the server via the Proxy. See the {@link + * Ext.data.Store Store docs} for more information on Stores. + */ +Ext.define('Ext.data.Model', { + alternateClassName: 'Ext.data.Record', + requires: [ + 'Ext.data.ErrorCollection', + 'Ext.data.operation.*', + 'Ext.data.field.*', + 'Ext.data.validator.Validator', + 'Ext.data.schema.Schema', + 'Ext.data.identifier.Generator', + 'Ext.data.identifier.Sequential' + ], + uses: [ + 'Ext.data.Validation' + ], + /** + * @property {Boolean} isEntity + * The value `true` to identify this class and its subclasses. + * @readonly + */ + isEntity: true, + /** + * @property {Boolean} isModel + * The value `true` to identify this class and its subclasses. + * @readonly + */ + isModel: true, + // Record ids are more flexible. + validIdRe: null, + erasing: false, + loadOperation: null, + loadCount: 0, + observableType: 'record', + /** + * @property {"C"/"R"/"U"/"D"} crudState + * This value is initially "R" or "C" indicating the initial CRUD state. As the + * record changes and the various joined parties (stores, sessions, etc.) are notified + * this value is updated prior to these calls. In other words, the joined parties + * are notified after the `crudState` is updated. This means that the `crudState` + * property may be briefly out of sync with underlying changes if this state is used + * outside of these notifications. + * + * The possible states have these meanings: + * + * * "R" - The record is in a cleanly retrieved (unmodified) state. + * * "C" - The record is in a newly created (`phantom`) state. + * * "U" - The record is in an updated, `modified` (`dirty`) state. + * * "D" - The record is in a `dropped` state. + * + * @readonly + * @protected + * @since 6.2.0 + */ + crudState: 'R', + /** + * @property {"C"/"R"/"U"/"D"} crudStateWas + * This value is initially `null` indicating there is no previous CRUD state. As the + * record changes and the various joined parties (stores, sessions, etc.) are notified + * this value is updated for the *subsequent* calls. In other words, the joined parties + * are notified and then `crudStateWas` is modified for the next update. + * + * The value of this property has the same meaning as `crudState`. + * + * @readonly + * @protected + * @since 6.2.0 + */ + crudStateWas: null, + constructor: function(data, session) { + var me = this, + cls = me.self, + identifier = cls.identifier, + Model = Ext.data.Model, + modelIdentifier = Model.identifier, + idProperty = me.idField.name, + array, id, initializeFn, internalId, len, i, fields; + // Yes, this is here on purpose. See EXTJS-16494. The second + // assignment seems to work around a strange JIT issue that prevents + // this.data being assigned in random scenarios, even though the data + // is passed into the constructor. The issue occurs on 4th gen iPads and + // lower, possibly other older iOS devices. + // A similar issue can occur with the hasListeners property of Observable + // (see the constructor of Ext.mixin.Observable) + me.data = me.data = data || (data = {}); + me.internalId = internalId = modelIdentifier.generate(); + var dataId = data[idProperty]; + if (session && !session.isSession) { + Ext.raise('Bad Model constructor argument 2 - "session" is not a Session'); + } + if ((array = data) instanceof Array) { + me.data = data = {}; + fields = me.getFields(); + len = Math.min(fields.length, array.length); + for (i = 0; i < len; ++i) { + data[fields[i].name] = array[i]; + } + } + if (!(initializeFn = cls.initializeFn)) { + cls.initializeFn = initializeFn = Model.makeInitializeFn(cls); + } + if (!initializeFn.$nullFn) { + cls.initializeFn(me); + } + // Must do this after running the initializeFn due to converters on idField + if (!me.isSummaryModel) { + if (!(me.id = id = data[idProperty]) && id !== 0) { + if (dataId) { + Ext.raise('The model ID configured in data ("' + dataId + '") has been rejected by the ' + me.fieldsMap[idProperty].type + ' field converter for the ' + idProperty + ' field'); + } + if (session) { + identifier = session.getIdentifier(cls); + id = identifier.generate(); + } else if (modelIdentifier === identifier) { + id = internalId; + } else { + id = identifier.generate(); + } + data[idProperty] = me.id = id; + me.phantom = true; + me.crudState = 'C'; + } + if (session) { + session.add(me); + } + // Needs to be set after the add to the session + if (me.phantom) { + me.crudStateWas = 'C'; + } + } + if (me.init && Ext.isFunction(me.init)) { + me.init(); + } + }, + /** + * @property {String} entityName + * The short name of this entity class. This name is derived from the `namespace` of + * the associated `schema` and this class name. By default, a class is not given a + * shortened name. + * + * All entities in a given `schema` must have a unique `entityName`. + * + * For more details see "Relative Naming" in {@link Ext.data.schema.Schema}. + */ + /** + * @property {Boolean} editing + * Internal flag used to track whether or not the model instance is currently being edited. + * @readonly + */ + editing: false, + /** + * @property {Boolean} dirty + * True if this record has been modified. + * @readonly + */ + dirty: false, + /** + * @property {Ext.data.Session} session + * The {@link Ext.data.Session} for this record. + * @readonly + */ + session: null, + /** + * @property {Boolean} dropped + * True if this record is pending delete on the server. This is set by the `drop` + * method and transmitted to the server by the `save` method. + * @readonly + */ + dropped: false, + /** + * @property {Boolean} erased + * True if this record has been erased on the server. This flag is set of the `erase` + * method. + * @readonly + */ + erased: false, + /** + * @cfg {String} clientIdProperty + * The name of the property a server will use to send back a client-generated id in a + * `create` or `update` `{@link Ext.data.operation.Operation operation}`. + * + * If specified, this property cannot have the same name as any other field. + * + * For example: + * + * Ext.define('Person', { + * idProperty: 'id', // this is the default value (for clarity) + * + * clientIdProperty: 'clientId', + * + * identifier: 'negative', // to generate -1, -2 etc on the client + * + * fields: [ 'name' ] + * }); + * + * var person = new Person({ + * // no id provided, so -1 is generated + * name: 'Clark Kent' + * }); + * + * The server is given this data during the `create`: + * + * { + * id: -1, + * name: 'Clark Kent' + * } + * + * The server allocates a real id and responds like so: + * + * { + * id: 427, + * clientId: -1 + * } + * + * This property is most useful when creating multiple entities in a single call to + * the server in a `{@link Ext.data.operation.Create create operation}`. Alternatively, + * the server could respond with records that correspond one-to-one to those sent in + * the `operation`. + * + * For example the client could send a `create` with this data: + * + * [ { id: -1, name: 'Clark Kent' }, + * { id: -2, name: 'Peter Parker' }, + * { id: -3, name: 'Bruce Banner' } ] + * + * And the server could respond in the same order: + * + * [ { id: 427 }, // updates id = -1 + * { id: 428 }, // updates id = -2 + * { id: 429 } ] // updates id = -3 + * + * Or using `clientIdProperty` the server could respond in arbitrary order: + * + * [ { id: 427, clientId: -3 }, + * { id: 428, clientId: -1 }, + * { id: 429, clientId: -2 } ] + * + * **IMPORTANT:** When upgrading from previous versions be aware that this property + * used to perform the role of `{@link Ext.data.writer.Writer#clientIdProperty}` as + * well as that described above. To continue send a client-generated id as other than + * the `idProperty`, set `clientIdProperty` on the `writer`. A better solution, however, + * is most likely a properly configured `identifier` as that would work better with + * associations. + */ + clientIdProperty: null, + evented: false, + /** + * @property {Boolean} phantom + * True when the record does not yet exist in a server-side database. Any record which + * has a real database identity set as its `idProperty` is NOT a phantom -- it's real. + */ + phantom: false, + /** + * @cfg {String} idProperty + * The name of the field treated as this Model's unique id. + * + * If changing the idProperty in a subclass, the generated id field will replace the + * one generated by the superclass, for example; + * + * Ext.define('Super', { + * extend: 'Ext.data.Model', + * fields: ['name'] + * }); + * + * Ext.define('Sub', { + * extend: 'Super', + * idProperty: 'customId' + * }); + * + * var fields = Super.getFields(); + * // Has 2 fields, "name" & "id" + * console.log(fields[0].name, fields[1].name, fields.length); + * + * fields = Sub.getFields(); + * // Has 2 fields, "name" & "customId", "id" is replaced + * console.log(fields[0].name, fields[1].name, fields.length); + * + * The data values for this field must be unique or there will be id value collisions + * in the {@link Ext.data.Store Store}. + */ + idProperty: 'id', + /** + * @cfg {Object} manyToMany + * A config object for a {@link Ext.data.schema.ManyToMany ManyToMany} association. + * See the class description for {@link Ext.data.schema.ManyToMany ManyToMany} for + * configuration examples. + */ + manyToMany: null, + /** + * @cfg {String/Object} identifier + * The id generator to use for this model. The `identifier` generates values for the + * {@link #idProperty} when no value is given. Records with client-side generated + * values for {@link #idProperty} are called {@link #phantom} records since they are + * not yet known to the server. + * + * This can be overridden at the model level to provide a custom generator for a + * model. The simplest form of this would be: + * + * Ext.define('MyApp.data.MyModel', { + * extend: 'Ext.data.Model', + * requires: ['Ext.data.identifier.Sequential'], + * identifier: 'sequential', + * ... + * }); + * + * The above would generate {@link Ext.data.identifier.Sequential sequential} id's + * such as 1, 2, 3 etc.. + * + * Another useful id generator is {@link Ext.data.identifier.Uuid}: + * + * Ext.define('MyApp.data.MyModel', { + * extend: 'Ext.data.Model', + * requires: ['Ext.data.identifier.Uuid'], + * identifier: 'uuid', + * ... + * }); + * + * An id generator can also be further configured: + * + * Ext.define('MyApp.data.MyModel', { + * extend: 'Ext.data.Model', + * identifier: { + * type: 'sequential', + * seed: 1000, + * prefix: 'ID_' + * } + * }); + * + * The above would generate id's such as ID_1000, ID_1001, ID_1002 etc.. + * + * If multiple models share an id space, a single generator can be shared: + * + * Ext.define('MyApp.data.MyModelX', { + * extend: 'Ext.data.Model', + * identifier: { + * type: 'sequential', + * id: 'xy' + * } + * }); + * + * Ext.define('MyApp.data.MyModelY', { + * extend: 'Ext.data.Model', + * identifier: { + * type: 'sequential', + * id: 'xy' + * } + * }); + * + * For more complex, shared id generators, a custom generator is the best approach. + * See {@link Ext.data.identifier.Generator} for details on creating custom id + * generators. + */ + identifier: null, + // Fields config and property + // @cmd-auto-dependency {aliasPrefix: "data.field."} + /** + * @cfg {Object[]/String[]} fields + * An Array of `Ext.data.field.Field` config objects, simply the field + * {@link Ext.data.field.Field#name name}, or a mix of config objects and strings. + * If just a name is given, the field type defaults to `auto`. + * + * In a {@link Ext.data.field.Field Field} config object you may pass the alias of + * the `Ext.data.field.*` type using the `type` config option. + * + * // two fields are set: + * // - an 'auto' field with a name of 'firstName' + * // - and an Ext.data.field.Integer field with a name of 'age' + * fields: ['firstName', { + * type: 'int', + * name: 'age' + * }] + * + * Fields will automatically be created at read time for any for any keys in the + * data passed to the Model's {@link #proxy proxy's} + * {@link Ext.data.reader.Reader reader} whose name is not explicitly configured in + * the `fields` config. + * + * Extending a Model class will inherit all the `fields` from the superclass / + * ancestor classes. + */ + /** + * @property {Ext.data.field.Field[]} fields + * An array fields defined for this Model (including fields defined in superclasses) + * in ordinal order; that is in declaration order. + * @private + * @readonly + */ + /** + * @property {Object} fieldOrdinals + * This property is indexed by field name and contains the ordinal of that field. The + * ordinal often has meaning to servers and is derived based on the position in the + * `fields` array. + * + * This can be used like so: + * + * Ext.define('MyApp.models.User', { + * extend: 'Ext.data.Model', + * + * fields: [ + * { name: 'name' } + * ] + * }); + * + * var nameOrdinal = MyApp.models.User.fieldOrdinals.name; + * + * // or, if you have an instance: + * + * var user = new MyApp.models.User(); + * var nameOrdinal = user.fieldOrdinals.name; + * + * @private + * @readonly + */ + /** + * @property {Object} modified + * A hash of field values which holds the initial values of fields before a set of + * edits are {@link #commit committed}. + */ + /** + * @property {Object} previousValues + * This object is similar to the `modified` object except it holds the data values as + * they were prior to the most recent change. + * @readonly + * @private + */ + previousValues: undefined, + // Not "null" so getPrevious returns undefined first time + // @cmd-auto-dependency { aliasPrefix : "proxy.", defaultPropertyName : "defaultProxyType"} + /** + * @cfg {String/Object/Ext.data.proxy.Proxy} proxy + * The {@link Ext.data.proxy.Proxy proxy} to use for this class. + * + * By default, the proxy is configured from the {@link Ext.data.schema.Schema schema}. + * You can ignore the schema defaults by setting `schema: false` on the `proxy` config. + * + * Ext.define('MyApp.data.CustomProxy', { + * extend: 'Ext.data.proxy.Ajax', + * alias: 'proxy.customproxy', + * + * url: 'users.json' + * }); + * + * Ext.define('MyApp.models.CustomModel', { + * extend: 'Ext.data.Model', + * + * fields: ['name'], + * proxy: { + * type: 'customproxy, + * schema: false + * } + * }); + * + * With `schema: false`, the `url` of the proxy will be used instead of what has been defined + * on the schema. + */ + proxy: undefined, + /** + * @cfg {String/Object} [schema='default'] + * The name of the {@link Ext.data.schema.Schema schema} to which this entity and its + * associations belong. For details on custom schemas see `Ext.data.schema.Schema`. + */ + /** + * @property {Ext.data.schema.Schema} schema + * The `Ext.data.schema.Schema` to which this entity and its associations belong. + * @readonly + */ + schema: 'default', + /** + * @cfg {Object} summary + * Summary fields are a special kind of field that is used to assist in creating an + * aggregation for this model. A new model type that extends this model will be + * created, accessible via {@link #method-getSummaryModel}. This summary model will + * have these virtual aggregate fields in the fields collection like a normal model. + * Each key in the object is the field name. The value for each field should mirror + * the {@link #cfg-fields}, excluding the `name` option. The summary model generated + * will have 2 fields, 'rate', which will aggregate using an average and maxRate, + * which will aggregate using the maximum value. + * + * See {@link Ext.data.summary.Base} for more information. + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [{ + * name: 'rate', + * summary: 'avg' + * }], + * + * summary: { + * maxRate: { + * field: 'rate', // calculated from rate field + * summary: 'max' + * } + * } + * }); + * + * @since 6.5.0 + */ + summary: null, + /** + * @cfg {String} versionProperty + * If specified, this is the name of the property that contains the entity "version". + * The version property is used to manage a long-running transaction and allows the + * detection of simultaneous modification. + * + * The way a version property is used is that the client receives the version as it + * would any other entity property. When saving an entity, this property is always + * included in the request and the server uses the value in a "conditional update". + * If the current version of the entity on the server matches the version property + * sent by the client, the update is allowed. Otherwise, the update fails. + * + * On successful update, both the client and server increment the version. This is + * done on the server in the conditional update and on the client when it receives a + * success on its update request. + */ + versionProperty: null, + /** + * @property {Number} generation + * This property is incremented on each modification of a record. + * @readonly + * @since 5.0.0 + */ + generation: 1, + /** + * @cfg {Object[]} validators + * An array of {@link Ext.data.validator.Validator validators} for this model. + */ + /** + * @cfg {String} validationSeparator + * If specified this property is used to concatenate multiple errors for each field + * as reported by the `validators`. + */ + validationSeparator: null, + /** + * @cfg {Boolean} convertOnSet + * Set to `false` to prevent any converters from being called on fields specified in + * a {@link Ext.data.Model#set set} operation. + * + * **Note:** Setting the config to `false` will only prevent the convert / calculate + * call when the set `fieldName` param matches the field's `{@link #name}`. In the + * following example the calls to set `salary` will not execute the convert method + * on `set` while the calls to set `vested` will execute the convert method on the + * initial read as well as on `set`. + * + * Example model definition: + * + * Ext.define('MyApp.model.Employee', { + * extend: 'Ext.data.Model', + * fields: ['yearsOfService', { + * name: 'salary', + * convert: function (val) { + * var startingBonus = val * .1; + * return val + startingBonus; + * } + * }, { + * name: 'vested', + * convert: function (val, record) { + * return record.get('yearsOfService') >= 4; + * }, + * depends: 'yearsOfService' + * }], + * convertOnSet: false + * }); + * + * var tina = Ext.create('MyApp.model.Employee', { + * salary: 50000, + * yearsOfService: 3 + * }); + * + * console.log(tina.get('salary')); // logs 55000 + * console.log(tina.get('vested')); // logs false + * + * tina.set({ + * salary: 60000, + * yearsOfService: 4 + * }); + * console.log(tina.get('salary')); // logs 60000 + * console.log(tina.get('vested')); // logs true + */ + convertOnSet: true, + // Associations configs and properties + /** + * @cfg {Object[]} associations + * An array of {@link Ext.data.schema.Association associations} for this model. + * + * For further documentation, see {@link Ext.data.schema.Association}. + * + * @deprecated 6.2.0 Use `hasMany/hasOne/belongsTo`. + */ + /** + * @cfg {String/Object/String[]/Object[]} hasMany + * One or more `Ext.data.schema.HasMany` associations for this model. + */ + /** + * @cfg {String/Object/String[]/Object[]} hasOne + * One or more `Ext.data.schema.HasOne` associations for this model. + */ + /** + * @cfg {String/Object/String[]/Object[]} belongsTo + * One or more `Ext.data.schema.BelongsTo` associations for this model. + */ + /** + * Begins an edit. While in edit mode, no events (e.g.. the `update` event) are + * relayed to the containing store. When an edit has begun, it must be followed by + * either `endEdit` or `cancelEdit`. + */ + beginEdit: function() { + var me = this, + modified = me.modified, + previousValues = me.previousValues; + if (!me.editing) { + me.editing = true; + me.editMemento = { + dirty: me.dirty, + data: Ext.apply({}, me.data), + generation: me.generation, + modified: modified && Ext.apply({}, modified), + previousValues: previousValues && Ext.apply({}, previousValues) + }; + } + }, + /** + * Calculate all summary fields on this record. + * @param {Ext.data.Model[]} records The records to use for calculation. + * + * @since 6.5.0 + */ + calculateSummary: function(records) { + var fields = this.getFields(), + len = fields.length, + recLen = records.length, + i, result, summary, prop, name, field; + for (i = 0; i < len; ++i) { + field = fields[i]; + summary = field.getSummary(); + if (summary) { + result = result || {}; + name = field.name; + prop = field.summaryField || name; + result[name] = summary.calculate(records, prop, 'data', 0, recLen); + } + } + if (result) { + this.set(result, this._commitOptions); + } + }, + /** + * Cancels all changes made in the current edit operation. + */ + cancelEdit: function() { + var me = this, + editMemento = me.editMemento, + validation = me.validation; + if (editMemento) { + me.editing = false; + // reset the modified state, nothing changed since the edit began + Ext.apply(me, editMemento); + me.editMemento = null; + if (validation && validation.syncGeneration !== me.generation) { + validation.syncGeneration = 0; + } + } + }, + /** + * Ends an edit. If any data was modified, the containing store is notified + * (ie, the store's `update` event will fire). + * @param {Boolean} [silent] True to not notify any stores of the change. + * @param {String[]} [modifiedFieldNames] Array of field names changed during edit. + */ + endEdit: function(silent, modifiedFieldNames) { + var me = this, + editMemento = me.editMemento; + if (editMemento) { + me.editing = false; + me.editMemento = null; + // Since these reflect changes we never notified others about, the real set + // of "previousValues" is what we captured in the memento: + me.previousValues = editMemento.previousValues; + if (!silent) { + if (!modifiedFieldNames) { + modifiedFieldNames = me.getModifiedFieldNames(editMemento.data); + } + if (me.dirty || (modifiedFieldNames && modifiedFieldNames.length)) { + me.callJoined('afterEdit', [ + modifiedFieldNames + ]); + } + } + } + }, + getField: function(name) { + return this.self.getField(name); + }, + /** + * Get the fields array for this model. + * @return {Ext.data.field.Field[]} The fields array + */ + getFields: function() { + return this.self.getFields(); + }, + getFieldsMap: function() { + return this.fieldsMap; + }, + /** + * Get the idProperty for this model. + * @return {String} The idProperty + */ + getIdProperty: function() { + return this.idProperty; + }, + /** + * Returns the unique ID allocated to this model instance as defined by `idProperty`. + * @return {Number/String} The id + */ + getId: function() { + return this.id; + }, + /** + * Return a unique observable ID. Model is not observable but tree nodes (`Ext.data.NodeInterface`) are, so + * they must be globally unique within the {@link #observableType}. + * @protected + */ + getObservableId: function() { + return this.internalId; + }, + /** + * Sets the model instance's id field to the given id. + * @param {Number/String} id The new id. + * @param {Object} [options] See {@link #set}. + */ + setId: function(id, options) { + this.set(this.idProperty, id, options); + }, + /** + * This method returns the value of a field given its name prior to its most recent + * change. + * @param {String} fieldName The field's {@link Ext.data.field.Field#name name}. + * @return {Object} The value of the given field prior to its current value. `undefined` + * if there is no previous value; + */ + getPrevious: function(fieldName) { + var previousValues = this.previousValues; + return previousValues && previousValues[fieldName]; + }, + /** + * Returns true if the passed field name has been `{@link #modified}` since the load or last commit. + * @param {String} fieldName The field's {@link Ext.data.field.Field#name name}. + * @return {Boolean} + */ + isModified: function(fieldName) { + var modified = this.modified; + return !!(modified && modified.hasOwnProperty(fieldName)); + }, + /** + * Returns the original value of a modified field. If there is no modified value, + * `undefined` will be return. Also see {@link #isModified}. + * @param {String} fieldName The name of the field for which to return the original value. + * @return {Object} modified + */ + getModified: function(fieldName) { + var out; + if (this.isModified(fieldName)) { + out = this.modified[fieldName]; + } + return out; + }, + /** + * Returns the value of the given field. + * @param {String} fieldName The name of the field. + * @return {Object} The value of the specified field. + */ + get: function(fieldName) { + return this.data[fieldName]; + }, + // This object is used whenever the set() method is called and given a string as the + // first argument. This approach saves memory (and GC costs) since we could be called + // a lot. + _singleProp: {}, + _rejectOptions: { + convert: false, + silent: true + }, + /** + * Sets the given field to the given value. For example: + * + * record.set('name', 'value'); + * + * This method can also be passed an object containing multiple values to set at once. + * For example: + * + * record.set({ + * name: 'value', + * age: 42 + * }); + * + * The following store events are fired when the modified record belongs to a store: + * + * - {@link Ext.data.Store#event-beginupdate beginupdate} + * - {@link Ext.data.Store#event-update update} + * - {@link Ext.data.Store#event-endupdate endupdate} + * + * @param {String/Object} fieldName The field to set, or an object containing key/value + * pairs. + * @param {Object} newValue The value for the field (if `fieldName` is a string). + * @param {Object} [options] Options for governing this update. + * @param {Boolean} [options.convert=true] Set to `false` to prevent any converters from + * being called during the set operation. This may be useful when setting a large bunch of + * raw values. + * @param {Boolean} [options.dirty=true] Pass `false` if the field values are to be + * understood as non-dirty (fresh from the server). When `true`, this change will be + * reflected in the `modified` collection. + * @param {Boolean} [options.commit=false] Pass `true` to call the {@link #commit} method + * after setting fields. If this option is passed, the usual after change processing will + * be bypassed. {@link #commit Commit} will be called even if there are no field changes. + * @param {Boolean} [options.silent=false] Pass `true` to suppress notification of any + * changes made by this call. Use with caution. + * @return {String[]} The array of modified field names or null if nothing was modified. + */ + set: function(fieldName, newValue, options) { + var me = this, + cls = me.self, + data = me.data, + modified = me.modified, + prevVals = me.previousValues, + session = me.session, + single = Ext.isString(fieldName), + opt = (single ? options : newValue), + convertOnSet = opt ? opt.convert !== false : me.convertOnSet, + fieldsMap = me.fieldsMap, + silent = opt && opt.silent, + commit = opt && opt.commit, + updateRefs = !(opt && opt.refs === false) && session, + // Don't need to do dirty processing with commit, since we'll always + // end up with nothing modified and not dirty + dirty = !(opt && opt.dirty === false && !commit), + modifiedFieldNames = null, + dirtyRank = 0, + associations = me.associations, + currentValue, field, idChanged, key, name, oldId, comparator, dep, dependents, i, numFields, newId, rankedFields, reference, value, values, roleName; + if (single) { + values = me._singleProp; + values[fieldName] = newValue; + } else { + values = fieldName; + } + if (!(rankedFields = cls.rankedFields)) { + // On the first edit of a record of this type we need to ensure we have the + // topo-sort done: + rankedFields = cls.rankFields(); + } + numFields = rankedFields.length; + do { + for (name in values) { + value = values[name]; + currentValue = data[name]; + comparator = me; + field = fieldsMap[name]; + if (field) { + if (convertOnSet && field.convert) { + value = field.convert(value, me); + } + comparator = field; + reference = field.reference; + } else { + reference = null; + } + if (comparator.isEqual(currentValue, value)) { + + continue; + } + data[name] = value; + (modifiedFieldNames || (modifiedFieldNames = [])).push(name); + (prevVals || (me.previousValues = prevVals = {}))[name] = currentValue; + if (reference && reference.cls) { + if (updateRefs) { + session.updateReference(me, field, value, currentValue); + } + reference.onValueChange(me, session, value, currentValue); + } + i = (dependents = field && field.dependents) && dependents.length; + while (i-- > 0) { + (dep = dependents[i]).dirty = true; + dirtyRank = dirtyRank ? Math.min(dirtyRank, dep.rank) : dep.rank; + } + if (!field || field.persist) { + if (modified && modified.hasOwnProperty(name)) { + if (!dirty || comparator.isEqual(modified[name], value)) { + delete modified[name]; + me.dirty = -1; + } + } else if (dirty) { + if (!modified) { + me.modified = modified = {}; + } + me.dirty = true; + modified[name] = currentValue; + } + } + if (name === me.idField.name) { + idChanged = true; + oldId = currentValue; + newId = value; + } + } + if (!dirtyRank) { + break; + } + field = rankedFields[dirtyRank - 1]; + field.dirty = false; + if (single) { + delete values[fieldName]; + } else { + values = me._singleProp; + single = true; + } + fieldName = field.name; + values[fieldName] = data[fieldName]; + convertOnSet = true; + for (; dirtyRank < numFields; ++dirtyRank) { + if (rankedFields[dirtyRank].dirty) { + break; + } + } + if (dirtyRank < numFields) { + ++dirtyRank; + } else { + dirtyRank = 0; + } + } while (// new value is the same, so no change... + // We need the cls to be present because it means the association class is loaded, + // otherwise it could be pending. + // we use the field instance to hold the dirty bit to avoid any + // extra allocations... we'll clear this before we depart. We do + // this so we can perform the fewest recalculations possible as + // each dependent field only needs to be recalculated once. + // The original value in me.modified equals the new value, so + // the field is no longer modified: + // fix me.dirty later (still truthy) + // create only when needed + // Unless there are dependent fields to process we can break now. This is + // what will happen for all code pre-dating the depends or simply not + // using it, so it will add very little overhead when not used. + // dirtyRank has the minimum rank (a 1-based value) of any dependent field + // that needs recalculating due to changes above. The way we go about this + // is to use our helper object for processing single argument invocations + // to process just this one field. This is because the act of setting it + // may cause another field to be invalidated, so while we cannot know at + // this moment all the fields we need to recalculate, we know that only + // those following this field in rankedFields can possibly be among them. + // dirtyRank is 1-based + // clear just this field's dirty state + // cleanup last value + // switch over + // We are now processing a dependent field, so we want to force a + // convert to occur because it's the only way it will get a value + // Since dirtyRank is 1-based and refers to the field we need to handle + // on this pass, we can treat it like an index for a minute and look at + // the next field on towards the end to find the index of the next dirty + // field. + // We found a field after this one marked as dirty so make the index + // a proper 1-based rank: + // We did not find any more dirty fields after this one, so clear the + // dirtyRank and we will perhaps fall out after the next update + 1); + if (me.dirty < 0) { + // We might have removed the last modified field, so check to see if there + // are any modified fields remaining and correct me.dirty: + me.dirty = false; + for (key in modified) { + if (modified.hasOwnProperty(key)) { + me.dirty = true; + break; + } + } + } + if (single) { + // cleanup our reused object for next time... important to do this before + // we fire any events or call anyone else (like afterEdit)! + delete values[fieldName]; + } + ++me.generation; + if (idChanged) { + me.id = newId; + me.onIdChanged(newId, oldId); + me.callJoined('onIdChanged', [ + oldId, + newId + ]); + if (associations) { + for (roleName in associations) { + associations[roleName].onIdChanged(me, oldId, newId); + } + } + } + if (commit) { + me.commit(silent, modifiedFieldNames); + } else if (!silent && !me.editing && modifiedFieldNames) { + me.callJoined('afterEdit', [ + modifiedFieldNames + ]); + } + return modifiedFieldNames; + }, + /** + * Usually called by the {@link Ext.data.Store} to which this model instance has been {@link #join joined}. Rejects + * all changes made to the model instance since either creation, or the last commit operation. Modified fields are + * reverted to their original values. + * + * Developers should subscribe to the {@link Ext.data.Store#event-update} event to have their code notified of reject + * operations. + * + * @param {Boolean} [silent=false] `true` to skip notification of the owning store of the change. + */ + reject: function(silent) { + var me = this, + modified = me.modified; + if (me.erased) { + Ext.raise('Cannot reject once a record has been erased.'); + } + if (modified) { + me.set(modified, me._rejectOptions); + } + me.dropped = false; + me.clearState(); + if (!silent) { + me.callJoined('afterReject'); + } + }, + /** + * Usually called by the {@link Ext.data.Store} which owns the model instance. Commits all changes made to the + * instance since either creation or the last commit operation. + * + * Developers should subscribe to the {@link Ext.data.Store#event-update} event to have their code notified of commit + * operations. + * + * @param {Boolean} [silent=false] Pass `true` to skip notification of the owning store of the change. + * @param {String[]} [modifiedFieldNames] Array of field names changed during sync with server if known. + * Omit or pass `null` if unknown. An empty array means that it is known that no fields were modified + * by the server's response. + * Defaults to false. + */ + commit: function(silent, modifiedFieldNames) { + var me = this, + versionProperty = me.versionProperty, + data = me.data, + erased; + me.clearState(); + if (versionProperty && !me.phantom && !isNaN(data[versionProperty])) { + ++data[versionProperty]; + } + me.phantom = false; + if (me.dropped) { + me.erased = erased = true; + } + if (!silent) { + if (erased) { + me.callJoined('afterErase'); + } else { + me.callJoined('afterCommit', [ + modifiedFieldNames + ]); + } + } + }, + clearState: function() { + var me = this; + me.dirty = me.editing = false; + me.editMemento = me.modified = null; + }, + /** + * Marks this record as `dropped` and waiting to be deleted on the server. When a + * record is dropped, it is automatically removed from all association stores and + * any child records associated to this record are also dropped (a "cascade delete") + * depending on the `cascade` parameter. + * + * @param {Boolean} [cascade=true] Pass `false` to disable the cascade to drop child + * records. + * @since 5.0.0 + */ + drop: function(cascade) { + var me = this, + associations = me.associations, + session = me.session, + roleName; + if (me.erased || me.dropped) { + return; + } + me.dropped = true; + if (associations && cascade !== false) { + for (roleName in associations) { + associations[roleName].onDrop(me, session); + } + } + me.callJoined('afterDrop'); + if (me.phantom) { + me.setErased(); + } + }, + /** + * Tells this model instance that an observer is looking at it. + * @param {Ext.data.Store} owner The store or other owner object to which this model + * has been added. + */ + join: function(owner) { + var me = this, + joined = me.joined; + // Optimize this, gets called a lot + if (!joined) { + joined = me.joined = [ + owner + ]; + } else if (!joined.length) { + joined[0] = owner; + } else { + // TODO: do we need joined here? Perhaps push will do. + Ext.Array.include(joined, owner); + } + if (owner.isStore && !me.store) { + /** + * @property {Ext.data.Store} store + * The {@link Ext.data.Store Store} to which this instance belongs. + * + * **Note:** If this instance is bound to multiple stores, this property + * will reference only the first. + */ + me.store = owner; + } + }, + /** + * Tells this model instance that it has been removed from the store. + * @param {Ext.data.Store} owner The store or other owner object from which this + * model has been removed. + */ + unjoin: function(owner) { + var me = this, + joined = me.joined, + // TreeModels are never joined to their TreeStore. + // But unjoin is called by the base class's onCollectionRemove, so joined may be undefined. + len = joined && joined.length, + store = me.store, + i; + if (owner === me.session) { + me.session = null; + } else { + if (len === 1 && joined[0] === owner) { + joined.length = 0; + } else if (len) { + Ext.Array.remove(joined, owner); + } + if (store === owner) { + store = null; + if (joined) { + for (i = 0 , len = joined.length; i < len; ++i) { + owner = joined[i]; + if (owner.isStore) { + store = owner; + break; + } + } + } + me.store = store; + } + } + }, + /** + * Creates a clone of this record. States like `dropped`, `phantom` and `dirty` are + * all preserved in the cloned record. + * + * @param {Ext.data.Session} [session] The session to which the new record + * belongs. + * @return {Ext.data.Model} The cloned record. + */ + clone: function(session) { + var me = this, + modified = me.modified, + ret = me.copy(me.id, session); + if (modified) { + // Restore the modified fields state + ret.modified = Ext.apply({}, modified); + } + ret.dirty = me.dirty; + ret.dropped = me.dropped; + ret.phantom = me.phantom; + return ret; + }, + /** + * Creates a clean copy of this record. The returned record will not consider any its + * fields as modified. + * + * To generate a phantom instance with a new id pass `null`: + * + * var rec = record.copy(null); // clone the record but no id (one is generated) + * + * @param {String} [newId] A new id, defaults to the id of the instance being copied. + * See `{@link Ext.data.Model#idProperty idProperty}`. + * @param {Ext.data.Session} [session] The session to which the new record + * belongs. + * + * @return {Ext.data.Model} + */ + copy: function(newId, session) { + var me = this, + data = Ext.apply({}, me.data), + idProperty = me.idProperty, + T = me.self; + if (newId || newId === 0) { + data[idProperty] = newId; + } else if (newId === null) { + delete data[idProperty]; + } + return new T(data, session); + }, + /** + * Returns the configured Proxy for this Model. + * @return {Ext.data.proxy.Proxy} The proxy + */ + getProxy: function() { + return this.self.getProxy(); + }, + /** + * Returns the `Ext.data.Validation` record holding the results of this record's + * `validators`. This record is lazily created on first request and is then kept on + * this record to be updated later. + * + * See the class description for more about `validators`. + * + * @param {Boolean} [refresh] Pass `false` to not call the `refresh` method on the + * validation instance prior to returning it. Pass `true` to force a `refresh` of the + * validation instance. By default the returned record is only refreshed if changes + * have been made to this record. + * @return {Ext.data.Validation} The `Validation` record for this record. + * @since 5.0.0 + */ + getValidation: function(refresh) { + var me = this, + ret = me.validation; + if (!ret) { + me.validation = ret = new Ext.data.Validation(); + ret.attach(me); + } + if (refresh === true || (refresh !== false && ret.syncGeneration !== me.generation)) { + ret.refresh(refresh); + } + return ret; + }, + /** + * Validates the current data against all of its configured {@link #validators}. The + * returned collection holds an object for each reported problem from a `validator`. + * + * @return {Ext.data.ErrorCollection} The errors collection. + * @deprecated 5.0 Use `getValidation` instead. + */ + validate: function() { + return new Ext.data.ErrorCollection().init(this); + }, + /** + * Checks if the model is valid. See {@link #getValidation}. + * @return {Boolean} True if the model is valid. + */ + isValid: function() { + return this.getValidation().isValid(); + }, + /** + * Returns a url-suitable string for this model instance. By default this just returns the name of the Model class + * followed by the instance ID - for example an instance of MyApp.model.User with ID 123 will return 'user/123'. + * @return {String} The url string for this model instance. + */ + toUrl: function() { + var pieces = this.$className.split('.'), + name = pieces[pieces.length - 1].toLowerCase(); + return name + '/' + this.getId(); + }, + /** + * @method erase + * @localdoc Destroys the model using the configured proxy. The erase action is + * asynchronous. Any processing of the erased record should be done in a callback. + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'id', type: 'int'}, + * {name: 'name', type: 'string'} + * ], + * proxy: { + * type: 'ajax', + * url: 'server.url' + * } + * }); + * + * var user = new MyApp.model.User({ + * name: 'Foo' + * }); + * + * // pass the phantom record data to the server to be saved + * user.save({ + * success: function(record, operation) { + * // do something if the save succeeded + * // erase the created record + * record.erase({ + * failure: function(record, operation) { + * // do something if the erase failed + * }, + * success: function(record, operation) { + * // do something if the erase succeeded + * }, + * callback: function(record, operation, success) { + * // do something if the erase succeeded or failed + * } + * }); + * } + * }); + * + * **NOTE:** If a {@link #phantom} record is erased it will not be processed via the + * proxy. However, any passed `success` or `callback` functions will be called. + * + * The options param is an {@link Ext.data.operation.Destroy} config object + * containing success, failure and callback functions, plus optional scope. + * + * @inheritdoc #method-load + * @return {Ext.data.operation.Destroy} The destroy operation + */ + erase: function(options) { + var me = this; + me.erasing = true; + // Drop causes a removal from the backing Collection. + // The store's onCollectionRemove will respond to this by adding the record to + // its "to remove" stack and setting its needsSync + // flag unless the above "erasing" flag is set. + me.drop(); + me.erasing = false; + return me.save(options); + }, + setErased: function() { + this.erased = true; + this.callJoined('afterErase'); + }, + /** + * Gets an object of only the fields that have been modified since this record was + * created or committed. Only persistent fields are tracked in the `modified` set so + * this method will only return changes to persistent fields. + * + * For more control over the returned data, see `{@link #getData}`. + * @return {Object} + */ + getChanges: function() { + return this.getData(this._getChangesOptions); + }, + /** + * Returns the array of fields that are declared as critical (must always send). + * @return {Ext.data.field.Field[]} + */ + getCriticalFields: function() { + var cls = this.self, + ret = cls.criticalFields; + if (!ret) { + cls.rankFields(); + ret = cls.criticalFields; + } + return ret; + }, + /** + * This method is called by the {@link Ext.data.reader.Reader} after loading a model from + * the server. This is after processing any inline associations that are available. + * + * @method onLoad + * + * @protected + * @template + */ + /** + * Gets all of the data from this Models *loaded* associations. It does this + * recursively. For example if we have a User which hasMany Orders, and each Order + * hasMany OrderItems, it will return an object like this: + * + * { + * orders: [ + * { + * id: 123, + * status: 'shipped', + * orderItems: [ + * ... + * ] + * } + * ] + * } + * + * @param {Object} [result] The object on to which the associations will be added. If + * no object is passed one is created. This object is then returned. + * @param {Boolean/Object} [options] An object containing options describing the data + * desired. + * @param {Boolean} [options.associated=true] Pass `true` to include associated data from + * other associated records. + * @param {Boolean} [options.changes=false] Pass `true` to only include fields that + * have been modified. Note that field modifications are only tracked for fields that + * are not declared with `persist` set to `false`. In other words, only persistent + * fields have changes tracked so passing `true` for this means `options.persist` is + * redundant. + * @param {Boolean} [options.critical] Pass `true` to include fields set as `critical`. + * This is only meaningful when `options.changes` is `true` since critical fields may + * not have been modified. + * @param {Boolean} [options.persist] Pass `true` to only return persistent fields. + * This is implied when `options.changes` is set to `true`. + * @param {Boolean} [options.serialize=false] Pass `true` to invoke the `serialize` + * method on the returned fields. + * @return {Object} The nested data set for the Model's loaded associations. + */ + getAssociatedData: function(result, options) { + var me = this, + associations = me.associations, + deep, i, item, items, itemData, length, record, role, roleName, opts, clear, associated; + result = result || {}; + me.$gathering = 1; + if (options) { + options = Ext.apply({}, options); + } + for (roleName in associations) { + role = associations[roleName]; + item = role.getAssociatedItem(me); + if (!item || item.$gathering) { + + continue; + } + if (item.isStore) { + item.$gathering = 1; + items = item.getData().items; + // get the records for the store + length = items.length; + itemData = []; + for (i = 0; i < length; ++i) { + // NOTE - we don't check whether the record is gathering here because + // we cannot remove it from the store (it would invalidate the index + // values and misrepresent the content). Instead we tell getData to + // only get the fields vs descend further. + record = items[i]; + deep = !record.$gathering; + record.$gathering = 1; + if (options) { + associated = options.associated; + if (associated === undefined) { + options.associated = deep; + clear = true; + } else if (!deep) { + options.associated = false; + clear = true; + } + opts = options; + } else { + opts = deep ? me._getAssociatedOptions : me._getNotAssociatedOptions; + } + itemData.push(record.getData(opts)); + if (clear) { + options.associated = associated; + clear = false; + } + delete record.$gathering; + } + delete item.$gathering; + } else { + opts = options || me._getAssociatedOptions; + if (options && options.associated === undefined) { + opts.associated = true; + } + itemData = item.getData(opts); + } + result[roleName] = itemData; + } + delete me.$gathering; + return result; + }, + /** + * Gets all values for each field in this model and returns an object containing the + * current data. This can be tuned by passing an `options` object with various + * properties describing the desired result. Passing `true` simply returns all fields + * *and* all associated record data. + * + * To selectively gather some associated data, the `options` object can be used as + * follows: + * + * var data = order.getData({ + * associated: { + * orderItems: true + * } + * }); + * + * This will include all data fields as well as an "orderItems" array with the data + * for each `OrderItem`. To include the associated `Item` for each `OrderItem`, the + * call would look like: + * + * var data = order.getData({ + * associated: { + * orderItems: { + * item: true + * } + * } + * }); + * + * @param {Boolean/Object} [options] An object containing options describing the data + * desired. If `true` is passed it is treated as an object with `associated` set to + * `true`. + * @param {Boolean/Object} [options.associated=false] Pass `true` to recursively + * include all associated data. This is equivalent to pass `true` as the only argument. + * See `getAssociatedData`. If `associated` is an object, it describes the specific + * associations to gather. + * @param {Boolean} [options.changes=false] Pass `true` to only include fields that + * have been modified. Note that field modifications are only tracked for fields that + * are not declared with `persist` set to `false`. In other words, only persistent + * fields have changes tracked so passing `true` for this means `options.persist` is + * redundant. + * @param {Boolean} [options.critical] Pass `true` to include fields set as `critical`. + * This is only meaningful when `options.changes` is `true` since critical fields may + * not have been modified. + * @param {Boolean} [options.persist] Pass `true` to only return persistent fields. + * This is implied when `options.changes` is set to `true`. + * @param {Boolean} [options.serialize=false] Pass `true` to invoke the `serialize` + * method on the returned fields. + * @return {Object} An object containing all the values in this model. + */ + getData: function(options) { + var me = this, + ret = {}, + opts = (options === true) ? me._getAssociatedOptions : (options || ret), + //cheat + data = me.data, + associated = opts.associated, + changes = opts.changes, + critical = changes && opts.critical, + content = changes ? me.modified : data, + fieldsMap = me.fieldsMap, + persist = opts.persist, + serialize = opts.serialize, + criticalFields, field, n, name, value; + // DON'T use "opts" from here on... + // Keep in mind the two legacy use cases: + // - getData() ==> Ext.apply({}, me.data) + // - getData(true) ==> Ext.apply(Ext.apply({}, me.data), me.getAssociatedData()) + if (content) { + // when processing only changes, me.modified could be null + for (name in content) { + value = data[name]; + field = fieldsMap[name]; + if (field) { + if (persist && !field.persist) { + + continue; + } + if (serialize && field.serialize) { + value = field.serialize(value, me); + } + } + ret[name] = value; + } + } + if (critical) { + criticalFields = me.self.criticalFields || me.getCriticalFields(); + for (n = criticalFields.length; n-- > 0; ) { + name = (field = criticalFields[n]).name; + if (!(name in ret)) { + value = data[name]; + if (serialize && field.serialize) { + value = field.serialize(value, me); + } + ret[name] = value; + } + } + } + if (associated) { + if (typeof associated === 'object') { + me.getNestedData(opts, ret); + } else { + me.getAssociatedData(ret, opts); + } + } + return ret; + }, + getNestedData: function(options, result) { + var me = this, + associations = me.associations, + graph = options.associated, + i, item, items, itemData, length, record, role, roleName, opts; + result = result || {}; + // For example: + // + // associated: { + // orderItems: true + // } + // + // associated: { + // orderItems: { + // item: true + // } + // } + // + for (roleName in graph) { + role = associations[roleName]; + opts = graph[roleName]; + if (opts === true) { + delete options.associated; + } else { + options.associated = opts; + } + item = role.getAssociatedItem(me); + if (item.isStore) { + items = item.getData().items; + // get the records for the store + length = items.length; + itemData = []; + for (i = 0; i < length; ++i) { + record = items[i]; + itemData.push(record.getData(options)); + } + } else { + itemData = item.getData(options); + } + result[roleName] = itemData; + } + options.associated = graph; + // restore the original value + return result; + }, + /** + * Returns the array of fields that are declared as non-persist or "transient". + * @return {Ext.data.field.Field[]} + * @since 5.0.0 + */ + getTransientFields: function() { + var cls = this.self, + ret = cls.transientFields; + if (!ret) { + cls.rankFields(); + // populates transientFields as well as rank + ret = cls.transientFields; + } + return ret; + }, + /** + * Checks whether this model is loading data from the {@link #proxy}. + * @return {Boolean} `true` if in a loading state. + */ + isLoading: function() { + return !!this.loadOperation; + }, + /** + * Aborts a pending {@link #method!load} operation. If the record is not loading, this does nothing. + */ + abort: function() { + var operation = this.loadOperation; + if (operation) { + operation.abort(); + } + }, + /** + * @localdoc Loads the model instance using the configured proxy. The load action + * is asynchronous. Any processing of the loaded record should be done in a + * callback. + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'id', type: 'int'}, + * {name: 'name', type: 'string'} + * ], + * proxy: { + * type: 'ajax', + * url: 'server.url' + * } + * }); + * + * var user = new MyApp.model.User(); + * user.load({ + * scope: this, + * failure: function(record, operation) { + * // do something if the load failed + * }, + * success: function(record, operation) { + * // do something if the load succeeded + * }, + * callback: function(record, operation, success) { + * // do something whether the load succeeded or failed + * } + * }); + * + * The options param is an {@link Ext.data.operation.Read} config object containing + * success, failure and callback functions, plus optional scope. + * + * @param {Object} [options] Options to pass to the proxy. + * @param {Function} options.success A function to be called when the + * model is processed by the proxy successfully. + * The callback is passed the following parameters: + * @param {Ext.data.Model} options.success.record The record. + * @param {Ext.data.operation.Operation} options.success.operation The operation. + * + * @param {Function} options.failure A function to be called when the + * model is unable to be processed by the server. + * The callback is passed the following parameters: + * @param {Ext.data.Model} options.failure.record The record. + * @param {Ext.data.operation.Operation} options.failure.operation The operation. + * + * @param {Function} options.callback A function to be called whether the proxy + * transaction was successful or not. + * The callback is passed the following parameters: + * @param {Ext.data.Model} options.callback.record The record. + * @param {Ext.data.operation.Operation} options.callback.operation The operation. + * @param {Boolean} options.callback.success `true` if the operation was successful. + * + * @param {Object} options.scope The scope in which to execute the callback + * functions. Defaults to the model instance. + * + * @return {Ext.data.operation.Read} The read operation. + */ + load: function(options) { + options = Ext.apply({}, options); + var me = this, + scope = options.scope || me, + proxy = me.getProxy(), + callback = options.callback, + operation = me.loadOperation, + id = me.getId(), + extras; + if (operation) { + // Already loading, push any callbacks on and jump out + extras = operation.extraCalls; + if (!extras) { + extras = operation.extraCalls = []; + } + extras.push(options); + return operation; + } + var doIdCheck = true; + if (me.phantom) { + doIdCheck = false; + } + options.id = id; + // Always set the recordCreator. If we have a session, we're already + // part of said session, so we don't need to handle that. + options.recordCreator = function(data, type, readOptions) { + // Important to change this here, because we might be loading associations, + // so we do not want this to propagate down. If we have a session, use that + // so that we end up getting the same record. Otherwise, just remove it. + var session = me.session; + if (readOptions) { + readOptions.recordCreator = session ? session.recordCreator : null; + } + me.set(data, me._commitOptions); + // Do the id check after set since converters may have run + if (doIdCheck && me.getId() !== id) { + Ext.raise('Invalid record id returned for ' + id + '@' + me.entityName); + } + return me; + }; + options.internalCallback = function(operation) { + var success = operation.wasSuccessful() && operation.getRecords().length > 0, + op = me.loadOperation, + extras = op.extraCalls, + successFailArgs = [ + me, + operation + ], + callbackArgs = [ + me, + operation, + success + ], + i, len; + me.loadOperation = null; + ++me.loadCount; + if (success) { + Ext.callback(options.success, scope, successFailArgs); + } else { + Ext.callback(options.failure, scope, successFailArgs); + } + Ext.callback(callback, scope, callbackArgs); + // Some code repetition here, however in a vast majority of cases + // we'll only have a single callback, so optimize for that case rather + // than setup arrays for all the callback options + if (extras) { + for (i = 0 , len = extras.length; i < len; ++i) { + options = extras[i]; + if (success) { + Ext.callback(options.success, scope, successFailArgs); + } else { + Ext.callback(options.failure, scope, successFailArgs); + } + Ext.callback(options.callback, scope, callbackArgs); + } + } + me.callJoined('afterLoad'); + }; + delete options.callback; + me.loadOperation = operation = proxy.createOperation('read', options); + operation.execute(); + return operation; + }, + /** + * Merge incoming data from the server when this record exists + * in an active session. This method is not called if this record is + * loaded directly via {@link #method!load}. The default behaviour is to use incoming + * data if the record is not {@link #dirty}, otherwise the data is + * discarded. This method should be overridden in subclasses to + * provide a different behavior. + * @param {Object} data The model data retrieved from the server. + * + * @protected + * + * @since 6.5.0 + */ + mergeData: function(data) { + if (!this.dirty) { + this.set(data, this._commitOptions); + } + }, + /** + * @method save + * @localdoc Saves the model instance using the configured proxy. The save action + * is asynchronous. Any processing of the saved record should be done in a callback. + * + * Create example: + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'id', type: 'int'}, + * {name: 'name', type: 'string'} + * ], + * proxy: { + * type: 'ajax', + * url: 'server.url' + * } + * }); + * + * var user = new MyApp.model.User({ + * name: 'Foo' + * }); + * + * // pass the phantom record data to the server to be saved + * user.save({ + * failure: function(record, operation) { + * // do something if the save failed + * }, + * success: function(record, operation) { + * // do something if the save succeeded + * }, + * callback: function(record, operation, success) { + * // do something whether the save succeeded or failed + * } + * }); + * + * The response from a create operation should include the ID for the newly created + * record: + * + * // sample response + * { + * success: true, + * id: 1 + * } + * + * // the id may be nested if the proxy's reader has a rootProperty config + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * proxy: { + * type: 'ajax', + * url: 'server.url', + * reader: { + * type: 'ajax', + * rootProperty: 'data' + * } + * } + * }); + * + * // sample nested response + * { + * success: true, + * data: { + * id: 1 + * } + * } + * + * (Create + ) Update example: + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'id', type: 'int'}, + * {name: 'name', type: 'string'} + * ], + * proxy: { + * type: 'ajax', + * url: 'server.url' + * } + * }); + * + * var user = new MyApp.model.User({ + * name: 'Foo' + * }); + * user.save({ + * success: function(record, operation) { + * record.set('name', 'Bar'); + * // updates the remote record via the proxy + * record.save(); + * } + * }); + * + * (Create + ) Destroy example - see also {@link #erase}: + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'id', type: 'int'}, + * {name: 'name', type: 'string'} + * ], + * proxy: { + * type: 'ajax', + * url: 'server.url' + * } + * }); + * + * var user = new MyApp.model.User({ + * name: 'Foo' + * }); + * user.save({ + * success: function(record, operation) { + * record.drop(); + * // destroys the remote record via the proxy + * record.save(); + * } + * }); + * + * **NOTE:** If a {@link #phantom} record is {@link #drop dropped} and subsequently + * saved it will not be processed via the proxy. However, any passed `success` + * or `callback` functions will be called. + * + * The options param is an Operation config object containing success, failure and + * callback functions, plus optional scope. The type of Operation depends on the + * state of the model being saved. + * + * - {@link #phantom} model - {@link Ext.data.operation.Create} + * - {@link #isModified modified} model - {@link Ext.data.operation.Update} + * - {@link #dropped} model - {@link Ext.data.operation.Destroy} + * + * @inheritdoc #method-load + * @return {Ext.data.operation.Create/Ext.data.operation.Update/Ext.data.operation.Destroy} + * The operation instance for saving this model. The type of operation returned + * depends on the model state at the time of the action. + * + * - {@link #phantom} model - {@link Ext.data.operation.Create} + * - {@link #isModified modified} model - {@link Ext.data.operation.Update} + * - {@link #dropped} model - {@link Ext.data.operation.Destroy} + */ + save: function(options) { + options = Ext.apply({}, options); + var me = this, + phantom = me.phantom, + dropped = me.dropped, + action = dropped ? 'destroy' : (phantom ? 'create' : 'update'), + scope = options.scope || me, + callback = options.callback, + proxy = me.getProxy(), + operation; + options.records = [ + me + ]; + options.internalCallback = function(operation) { + var args = [ + me, + operation + ], + success = operation.wasSuccessful(); + if (success) { + Ext.callback(options.success, scope, args); + } else { + Ext.callback(options.failure, scope, args); + } + args.push(success); + Ext.callback(callback, scope, args); + }; + delete options.callback; + operation = proxy.createOperation(action, options); + // Not a phantom, then we must perform this operation on the remote datasource. + // Record will be removed from the store in the callback upon a success response + if (dropped && phantom) { + // If it's a phantom, then call the callback directly with a dummy successful ResultSet + operation.setResultSet(Ext.data.reader.Reader.prototype.nullResultSet); + me.setErased(); + operation.setSuccessful(true); + } else { + operation.execute(); + } + return operation; + }, + //------------------------------------------------------------------------- + // Statics + statics: { + /** + * @property {String/Object} + * The default proxy to use for instances of this Model when no proxy is configured + * on the instance. When specified, the model will use this proxy instead of + * requesting one from the {@link Ext.data.Session Session}. + * + * Can be a string "type", or a {@link Ext.data.proxy.Proxy Proxy} config object. + * + * This proxy is not inherited by subclasses. + * @static + * @protected + */ + defaultProxy: 'memory' + }, + inheritableStatics: { + /** + * @property {Object} _associatedReadOptions + * The options for the proxy reader for loadData. + * + * @private + */ + _associatedReadOptions: { + recordsOnly: true, + asRoot: true + }, + /** + * Create a model while also parsing any data for associations. + * @param {Object} data The model data, including any associated data if required. The type of + * data should correspond to what the configured data reader would expect. + * @param {Ext.data.Session} [session] The session. + * @return {Ext.data.Model} The model. + * + * @static + * @inheritable + * @since 6.5.0 + */ + loadData: function(data, session) { + var rec; + if (data) { + rec = this.getProxy().getReader().readRecords([ + data + ], session ? { + recordCreator: session.recordCreator + } : undefined, this._associatedReadOptions)[0]; + } else { + rec = new this(data, session); + } + return rec; + }, + /** + * Get the summary model type. If {@link #summary} is specified, it is + * a new type that extends from this type. If not, then it is the same + * model type. + * @return {Ext.Class} The summary model type. + * + * @static + * @inheritable + * @since 6.5.0 + */ + getSummaryModel: function() { + var me = this, + proto = me.prototype, + summaryModel = me.summaryModel; + if (!summaryModel) { + summaryModel = Ext.define(null, { + extend: me, + fields: proto.summaryFields || [], + isSummaryModel: true + }); + summaryModel.isSummaryModel = true; + me.summaryModel = proto.summaryModel = summaryModel; + } + return summaryModel || null; + }, + /** + * This method adds the given set of fields to this model class. + * + * @param {String[]/Object[]} newFields The new fields to add. Based on the `name` + * of a field this may replace a previous field definition. + * + * @protected + * @static + * @inheritable + * @since 5.0.0 + */ + addFields: function(newFields) { + this.replaceFields(newFields); + }, + /** + * This method replaces the specified set of fields with a given set of new fields. + * Fields should normally be considered immutable, but if the timing is right (that + * is, before derived classes are declared), it is permissible to change the fields + * collection. + * + * @param {String[]/Object[]} newFields The new fields to add. Based on the `name` + * of a field this may replace a previous field definition. + * @param {Boolean/String[]} removeFields The names of fields to remove or `true` + * to remove all existing fields. Removes are processed first followed by adds so + * if a field name appears in `newFields` as well that field will effectively be + * added (however, in that case there is no need to include the field in this + * array). + * + * @protected + * @static + * @inheritable + * @since 5.0.0 + */ + replaceFields: function(newFields, removeFields) { + var me = this, + proto = me.prototype, + Field = Ext.data.field.Field, + fields = me.fields, + fieldsMap = me.fieldsMap, + ordinals = me.fieldOrdinals, + field, i, idField, len, name, ordinal, cleared; + if (removeFields === true) { + fields.length = 0; + me.fieldsMap = fieldsMap = {}; + me.fieldOrdinals = ordinals = {}; + cleared = true; + } else if (removeFields) { + for (i = removeFields.length; i-- > 0; ) { + name = removeFields[i]; + if (name in ordinals) { + delete ordinals[name]; + delete fieldsMap[name]; + } + } + for (i = 0 , len = fields.length; i < len; ++i) { + name = (field = fields[i]).name; + if (name in ordinals) { + ordinals[name] = i; + } else { + // This field is being removed (it is no longer in ordinals). + fields.splice(i, 1); + --i; + --len; + } + } + } + // we need to do this forwards so that ordinals don't become + // invalid due to a splice + for (i = 0 , len = newFields ? newFields.length : 0; i < len; i++) { + name = (field = newFields[i]).name; + if (!(name in ordinals)) { + ordinals[name] = ordinal = fields.length; + // 0-based + fields.push(field = Field.create(field)); + fieldsMap[name] = field; + field.ordinal = ordinal; + field.definedBy = field.owner = this; + } + } + // Ext.data.NodeInterface + // Reset all ranks if we didn't get cleared, since this could + // alter the dependencies + if (!cleared) { + for (i = 0 , len = fields.length; i < len; ++i) { + fields[i].rank = null; + } + } + // The idField could have been replaced, so reacquire it. + me.idField = proto.idField = idField = fieldsMap[proto.idProperty]; + idField.allowNull = idField.critical = idField.identifier = true; + idField.defaultValue = null; + // In case we've created the initializer we need to zap it so we recreate it + // next time. Likewise with field ranking. + me.initializeFn = me.rankedFields = me.transientFields = me.criticalFields = null; + }, + /** + * Removes the given set of fields from this model. + * + * @param {Boolean/String[]} removeFields The names of fields to remove or `true` + * to remove all existing fields. Removes are processed first followed by adds so + * if a field name appears in `newFields` as well that field will effectively be + * added (however, in that case there is no need to include the field in this + * array). + * + * @protected + * @static + * @inheritable + * @since 5.0.0 + */ + removeFields: function(removeFields) { + this.replaceFields(null, removeFields); + }, + /** + * @private + * @static + * @inheritable + */ + getIdFromData: function(data) { + var T = this, + idField = T.idField, + id = idField.calculated ? (new T(data)).id : data[idField.name]; + return id; + }, + /** + * @private + * @static + * @inheritable + */ + createWithId: function(id, data, session) { + var d = data, + T = this; + if (id || id === 0) { + d = {}; + if (data) { + Ext.apply(d, data); + } + d[T.idField.name] = id; + } + return new T(d, session); + }, + /** + * @private + * @static + * @inheritable + */ + getFields: function() { + return this.fields; + }, + /** + * @private + * @static + * @inheritable + */ + getFieldsMap: function() { + return this.fieldsMap; + }, + /** + * @private + * @static + * @inheritable + */ + getField: function(name) { + return this.fieldsMap[name] || null; + }, + /** + * Returns the configured Proxy for this Model. + * @return {Ext.data.proxy.Proxy} The proxy + * @static + * @inheritable + */ + getProxy: function() { + var me = this, + proxy = me.proxy, + defaultProxy = me.defaultProxy, + defaults; + if (!proxy) { + // Check what was defined by the class (via onClassExtended): + proxy = me.proxyConfig; + if (!proxy && defaultProxy) { + proxy = defaultProxy; + } + if (!proxy || !proxy.isProxy) { + if (typeof proxy === 'string') { + proxy = { + type: proxy + }; + } + // We have nothing or a config for the proxy. Get some defaults from + // the Schema and smash anything we've provided over the top. + defaults = Ext.merge(me.schema.constructProxy(me), proxy); + if (proxy && proxy.type) { + proxy = proxy.schema === false ? proxy : defaults; + } else { + proxy = defaults; + } + } + proxy = me.setProxy(proxy); + } + return proxy; + }, + /** + * Sets the Proxy to use for this model. Accepts any options that can be accepted by + * {@link Ext#createByAlias Ext.createByAlias}. + * @param {String/Object/Ext.data.proxy.Proxy} proxy The proxy + * @return {Ext.data.proxy.Proxy} + * @static + * @inheritable + */ + setProxy: function(proxy) { + var me = this, + model; + if (proxy) { + if (!proxy.isProxy) { + proxy = Ext.Factory.proxy(proxy); + } else { + model = proxy.getModel(); + if (model && model !== me) { + proxy = proxy.clone(); + } + } + proxy.setModel(me); + } + return (me.prototype.proxy = me.proxy = proxy); + }, + /** + * Asynchronously loads a model instance by id. Any processing of the loaded + * record should be done in a callback. + * + * Sample usage: + * + * Ext.define('MyApp.User', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'id', type: 'int'}, + * {name: 'name', type: 'string'} + * ] + * }); + * + * MyApp.User.load(10, { + * scope: this, + * failure: function(record, operation) { + * //do something if the load failed + * }, + * success: function(record, operation) { + * //do something if the load succeeded + * }, + * callback: function(record, operation, success) { + * //do something whether the load succeeded or failed + * } + * }); + * + * @param {Number/String} id The ID of the model to load. + * **NOTE:** The model returned must have an ID matching the param in the load + * request. + * + * @param {Object} [options] The options param is an + * {@link Ext.data.operation.Read} config object containing success, failure and + * callback functions, plus optional scope. + * + * @param {Function} options.success A function to be called when the + * model is processed by the proxy successfully. + * The callback is passed the following parameters: + * @param {Ext.data.Model} options.success.record The record. + * @param {Ext.data.operation.Operation} options.success.operation The operation. + * + * @param {Function} options.failure A function to be called when the + * model is unable to be processed by the server. + * The callback is passed the following parameters: + * @param {Ext.data.Model} options.failure.record The record. + * @param {Ext.data.operation.Operation} options.failure.operation The operation. + * + * @param {Function} options.callback A function to be called whether the proxy + * transaction was successful or not. + * The callback is passed the following parameters: + * @param {Ext.data.Model} options.callback.record The record. + * @param {Ext.data.operation.Operation} options.callback.operation The + * operation. + * @param {Boolean} options.callback.success `true` if the operation was + * successful. + * + * @param {Object} options.scope The scope in which to execute the callback + * functions. Defaults to the model instance. + * + * @param {Ext.data.Session} [session] The session for this record. + * + * @return {Ext.data.Model} The newly created model. Note that the model will + * (probably) still be loading once it is returned from this method. To do any + * post-processing on the data, the appropriate place to do see is in the + * callback. + * + * @static + * @inheritable + */ + load: function(id, options, session) { + var data = {}, + rec; + if (session) { + rec = session.peekRecord(this, id); + } + if (!rec) { + data[this.prototype.idProperty] = id; + rec = new this(data, session); + } + rec.load(options); + return rec; + } + }, + deprecated: { + 5: { + methods: { + hasId: null, + markDirty: null, + setDirty: null, + eachStore: function(callback, scope) { + var me = this, + stores = me.stores, + len = stores.length, + i; + for (i = 0; i < len; ++i) { + callback.call(scope, stores[i]); + } + }, + join: function(item) { + var me = this, + stores = me.stores, + joined = me.joined; + if (!joined) { + joined = me.joined = [ + item + ]; + } else { + joined.push(item); + } + if (item.isStore) { + me.store = me.store || item; + if (!stores) { + stores = me.stores = []; + } + stores.push(item); + } + }, + unjoin: function(item) { + var me = this, + stores = me.stores, + joined = me.joined; + if (joined.length === 1) { + joined.length = 0; + } else { + Ext.Array.remove(joined, item); + } + if (item.isStore) { + Ext.Array.remove(stores, item); + me.store = stores[0] || null; + } + } + }, + properties: { + persistenceProperty: null + }, + inheritableStatics: { + methods: { + setFields: null + } + } + } + }, + //------------------------------------------------------------------------- + privates: { + _commitOptions: { + commit: true + }, + _getChangesOptions: { + changes: true + }, + _getAssociatedOptions: { + associated: true + }, + _getNotAssociatedOptions: { + associated: false + }, + _metaProperties: { + dirty: 'isDirty', + phantom: 'isPhantom', + valid: 'isValid' + }, + /** + * Copies data from the passed record into this record. If the passed record is undefined, does nothing. + * + * If this is a phantom record (represented only in the client, with no corresponding database entry), and + * the source record is not a phantom, then this record acquires the id of the source record. + * + * @param {Ext.data.Model} sourceRecord The record to copy data from. + * @return {String[]} The names of the fields which changed value. + * @private + */ + copyFrom: function(sourceRecord) { + var me = this, + fields = me.fields, + fieldCount = fields.length, + modifiedFieldNames = [], + field, + i = 0, + myData, sourceData, + idProperty = me.idProperty, + name, value; + if (sourceRecord) { + myData = me.data; + sourceData = sourceRecord.data; + for (; i < fieldCount; i++) { + field = fields[i]; + name = field.name; + // Do not use setters. + // Copy returned values in directly from the data object. + // Converters have already been called because new Records + // have been created to copy from. + // This is a direct record-to-record value copy operation. + // don't copy the id, we'll do it at the end + if (name !== idProperty) { + value = sourceData[name]; + // If source property is specified, and value is different + // copy field value in and build updatedFields + if (value !== undefined && !me.isEqual(myData[name], value)) { + myData[name] = value; + modifiedFieldNames.push(name); + } + } + } + // If this is a phantom record being updated from a concrete record, copy the ID in. + if (me.phantom && !sourceRecord.phantom) { + // beginEdit to prevent events firing + // commit at the end to prevent dirty being set + me.beginEdit(); + me.setId(sourceRecord.getId()); + me.endEdit(true); + me.commit(true); + } + } + return modifiedFieldNames; + }, + /** + * Helper function used by afterEdit, afterReject and afterCommit. Calls the given + * method on the `Ext.data.Store` that this instance has {@link #join joined}, if any. + * The store function will always be called with the model instance as its single + * argument. If this model is joined to a Ext.data.NodeStore, then this method calls + * the given method on the NodeStore and the associated Ext.data.TreeStore. + * @param {String} funcName The name function to call on each store. + * @param {Array} [args] The arguments to pass to the method. This instance is + * always inserted as the first argument. + * @private + */ + callJoined: function(funcName, args) { + var me = this, + joined = me.joined, + session = me.session, + state = me.dropped ? 'D' : (me.phantom ? 'C' : (me.dirty ? 'U' : 'R')), + i, len, fn, item; + me.crudState = state; + if (joined || session) { + if (args) { + args.unshift(me); + } else { + args = [ + me + ]; + } + fn = session && session[funcName]; + if (fn) { + fn.apply(session, args); + } + if (joined) { + for (i = 0 , len = joined.length; i < len; ++i) { + item = joined[i]; + if (item && (fn = item[funcName])) { + fn.apply(item, args); + } + } + } + } + me.crudStateWas = state; + }, + /** + * Currently this only checks the loading state, this method exists for API + * parity with stores. + * @return {Boolean} `true` if the model is loading or has a pending load. + * + * @private + */ + hasPendingLoad: function() { + return this.isLoading(); + }, + interpret: function(name) { + var me = this, + accessor = me._metaProperties[name]; + if (!accessor) { + accessor = me.associations; + // e.g. "orderItems" + accessor = accessor && accessor[name] && accessor[name].getterName; + } + if (accessor) { + return me[accessor](); + } + // e.g., me.isPhantom() + return me.data[name]; + }, + /** + * Gets the dirty state of this record. + * @return {Boolean} The dirty state. + * + * @private + */ + isDirty: function() { + // Added as a method to be used by data binding + return this.dirty; + }, + /** + * Gets the phantom state of this record. + * @return {Boolean} The phantom state. + * + * @private + */ + isPhantom: function() { + // Added as a method to be used by data binding + return this.phantom; + }, + /** + * Called when an associated record instance has been set. + * @param {Ext.data.Model} record The record. + * @param {Ext.data.schema.Role} role The role. + * + * @private + */ + onAssociatedRecordSet: function(record, role) { + this.callJoined('afterAssociatedRecordSet', [ + record, + role + ]); + }, + /** + * @method + * Called when the model id is changed. + * @param {Object} id The new id. + * @param {Object} oldId The old id. + */ + onIdChanged: Ext.privateFn, + /** + * Set the session for this record. + * @param {Ext.data.Session} session The session + */ + setSession: function(session) { + if (session) { + if (this.session) { + Ext.raise('This model already belongs to a session.'); + } + if (!this.id) { + Ext.raise('The model must have an id to participate in a session.'); + } + } + this.session = session; + if (session) { + session.add(this); + } + }, + /** + * Gets the names of all the fields that were modified during an edit. + * @param {Object} [old] The saved data from `beginEdit`. + * @return {String[]} The array of modified field names. + * @private + */ + getModifiedFieldNames: function(old) { + var me = this, + data = me.data, + modified = [], + oldData = old || me.editMemento.data, + key; + for (key in data) { + if (data.hasOwnProperty(key)) { + if (!me.isEqual(data[key], oldData[key], key)) { + modified.push(key); + } + } + } + return modified; + }, + /** + * Checks if two values are equal, taking into account certain special factors, for + * example dates. + * @param {Object} lhs The first value. + * @param {Object} rhs The second value. + * @param {String/Ext.data.Field} [field] The field name or instance. + * @return {Boolean} True if the values are equal. + * @private + */ + isEqual: function(lhs, rhs, field) { + var f; + if (field) { + f = field.isField ? field : this.fieldsMap[field]; + if (f) { + return f.isEqual(lhs, rhs); + } + } + // instanceof is ~10 times faster then Ext.isDate. Values here will not be + // cross-document objects + if (lhs instanceof Date && rhs instanceof Date) { + return lhs.getTime() === rhs.getTime(); + } + return lhs === rhs; + }, + statics: { + /** + * @property + * @static + * @private + * @readonly + * @deprecated 5.0 Use the string `"edit"` directly. + * The update operation of type 'edit'. Used by the + * {@link Ext.data.Store#event-update Store.update} event. + */ + EDIT: 'edit', + /** + * @property + * @static + * @private + * @readonly + * @deprecated 5.0 Use the string `"reject"` directly. + * The update operation of type 'reject'. Used by the + * {@link Ext.data.Store#event-update Store.update} event. + */ + REJECT: 'reject', + /** + * @property + * @static + * @private + * @readonly + * @deprecated 5.0 Use the string `"commit"` directly. + * The update operation of type 'commit'. Used by the + * {@link Ext.data.Store#event-update Store.update} event. + */ + COMMIT: 'commit', + rankFields: function() { + var cls = this, + prototype = cls.prototype, + fields = cls.fields, + length = fields.length, + rankedFields = [], + criticalFields = [], + transientFields = [], + evilFields, field, i; + cls.rankedFields = prototype.rankedFields = rankedFields; + cls.criticalFields = prototype.criticalFields = criticalFields; + cls.transientFields = prototype.transientFields = transientFields; + // This first pass brings over any fields that have no dependencies at all + // and gathers the evil fields to the side (the fields that could depend on + // anything). This avoids the call to topoAdd that we must perform on all of + // the fields that do have depends (which is good since most fields will be + // handled here). + for (i = 0; i < length; ++i) { + field = fields[i]; + if (field.critical) { + criticalFields.push(field); + } + if (!field.persist) { + transientFields.push(field); + } + if (field.evil) { + (evilFields || (evilFields = [])).push(field); + } else if (!field.depends) { + rankedFields.push(field); + field.rank = rankedFields.length; + } + } + // 1-based + for (i = 0; i < length; ++i) { + if (!(field = fields[i]).rank && !field.evil) { + cls.topoAdd(field); + } + } + if (evilFields) { + for (i = 0 , length = evilFields.length; i < length; ++i) { + rankedFields.push(field = evilFields[i]); + field.rank = rankedFields.length; + } + } + // 1-based + cls.topoStack = null; + // cleanup diagnostic stack + return rankedFields; + }, + topoAdd: function(field) { + var cls = this, + dep = field.depends, + dependsLength = dep ? dep.length : 0, + rankedFields = cls.rankedFields, + i, targetField; + var topoStack = cls.topoStack || (cls.topoStack = []); + topoStack.push(field.name); + if (field.rank === 0) { + // if (adding) + Ext.raise(cls.$className + " has circular field dependencies: " + topoStack.join(" --> ")); + } + if (topoStack.length && field.evil) { + Ext.raise(cls.$className + ": Field " + topoStack[topoStack.length - 1] + " cannot depend on depends-less field " + field.name); + } + field.rank = 0; + // adding (falsey but we can still detect cycles) + for (i = 0; i < dependsLength; ++i) { + // Get the targetField on which we depend and add this field to the + // targetField.dependents[] + targetField = cls.fieldsMap[dep[i]]; + if (!targetField) { + Ext.raise(cls.$className + ": Field " + field.name + " depends on undefined field " + dep[i]); + } + (targetField.dependents || (targetField.dependents = [])).push(field); + if (!targetField.rank) { + // if (!added) + cls.topoAdd(targetField); + } + } + rankedFields.push(field); + field.rank = rankedFields.length; + // 1-based (truthy to track "added" state) + topoStack.pop(); + }, + initFields: function(data, cls, proto) { + var Field = Ext.data.field.Field, + fieldDefs = data.fields, + // allocate fields [] and ordinals {} for the new class: + fields = [], + fieldOrdinals = {}, + fieldsMap = {}, + references = [], + superFields = proto.fields, + versionProperty = data.versionProperty || proto.versionProperty, + idProperty = cls.idProperty, + idField, field, i, length, name, ordinal, reference, superIdField, superIdFieldName, idDeclared; + // Process any inherited fields to produce a fields [] and ordinals {} for + // this class: + cls.fields = proto.fields = fields; + cls.fieldOrdinals = proto.fieldOrdinals = fieldOrdinals; + cls.fieldsMap = proto.fieldsMap = fieldsMap; + cls.references = proto.references = references; + if (superFields) { + // We chain the super field so we can write to it + for (i = 0 , length = superFields.length; i < length; ++i) { + fields[i] = field = Ext.Object.chain(superFields[i]); + field.dependents = null; + // we need to recalculate these + field.owner = cls; + fieldOrdinals[name = field.name] = i; + fieldsMap[name] = field; + // Clear the rank because it needs to be set on the first pass through + // the fields in the subclass, don't inherit it from the parent + field.rank = null; + if (field.generated) { + superIdField = field; + superIdFieldName = field.name; + } + } + } + // Merge in any fields from this class: + delete data.fields; + if (fieldDefs) { + for (i = 0 , length = fieldDefs.length; i < length; ++i) { + field = fieldDefs[i]; + reference = field.reference; + // Create a copy of the reference since we'll modify + // the reference on the field. Needed for subclasses + if (reference && typeof reference !== 'string') { + // Can have child objects, so merge it deeply + reference = Ext.merge({}, reference); + } + field.$reference = reference; + field = Field.create(fieldDefs[i]); + name = field.name; + ordinal = fieldOrdinals[name]; + if (ordinal === undefined) { + // If the field is new, add it to the end of the fields[] + fieldOrdinals[name] = ordinal = fields.length; + } + // else, overwrite the field at the established ordinal + fieldsMap[name] = field; + fields[ordinal] = field; + field.definedBy = field.owner = cls; + field.ordinal = ordinal; + if (name === idProperty) { + idDeclared = field; + } + } + } + // Lookup the idProperty in the ordinals map and create a synthetic field if + // we don't have one. + idField = fieldsMap[idProperty]; + if (!idField) { + if (superIdField && superIdField.generated) { + ordinal = superIdField.ordinal; + } else { + ordinal = fields.length; + } + delete fieldsMap[superIdFieldName]; + delete fieldOrdinals[superIdFieldName]; + idField = new Field(idProperty); + fields[ordinal] = idField; + fieldOrdinals[idProperty] = ordinal; + fieldsMap[idProperty] = idField; + idField.definedBy = cls; + idField.ordinal = ordinal; + idField.generated = true; + } else if (idDeclared && superIdField && superIdField.generated) { + // If we're declaring the id as a field in our fields array and it's different to + // the super id field that has been generated, pull it out and fix up the ordinals. This + // likely won't happen often, to do it earlier we would need to know the contents of the fields + // which would mean iterating over them twice. + Ext.Array.remove(fields, superIdField); + delete fieldsMap[superIdFieldName]; + delete fieldOrdinals[superIdFieldName]; + fieldsMap[idProperty] = idDeclared; + for (i = 0 , length = fields.length; i < length; ++i) { + field = fields[i]; + fields.ordinal = i; + fieldOrdinals[field.name] = i; + } + } + idField.allowNull = idField.critical = idField.identifier = true; + idField.defaultValue = null; + cls.idField = proto.idField = idField; + if (versionProperty) { + field = fieldsMap[versionProperty]; + if (!field) { + ordinal = fields.length; + field = new Field({ + name: versionProperty, + type: 'int' + }); + fields[ordinal] = field; + fieldOrdinals[versionProperty] = ordinal; + fieldsMap[versionProperty] = field; + field.definedBy = cls; + field.ordinal = ordinal; + field.generated = true; + } + field.defaultValue = 1; + field.critical = true; + } + }, + // NOTE: Be aware that the one fellow that manipulates these after this + // point is Ext.data.NodeInterface. + initSummaries: function(data, cls, proto) { + var summaryDefs = data.summary, + superSummaries = proto.summaryFields, + summaries, summaryMap, name, summary, len, i, index, field; + if (superSummaries) { + summaries = []; + summaryMap = {}; + for (i = 0 , len = superSummaries.length; i < len; ++i) { + summary = superSummaries[i]; + summaries.push(summary); + summaries[summary.name] = i; + } + } + if (summaryDefs) { + delete data.summary; + summaries = summaries || []; + summaryMap = summaryMap || {}; + for (name in summaryDefs) { + summary = summaryDefs[name]; + if (typeof summary === 'function') { + summary = { + summary: summary + }; + } + // If it's not in the summaries, it's new here. We've already + // applied when copying down so this is safe to do + index = summaryMap[name]; + summary = Ext.apply({ + name: name + }, summary); + field = summary.field; + if (field) { + delete summary.field; + summary.summaryField = field; + } + if (index === undefined) { + index = summaries.length; + summaryMap[name] = summary; + } + summaries[index] = summary; + } + } + if (summaries) { + for (i = 0 , len = summaries.length; i < len; ++i) { + if (summaries[i].name in proto.fieldsMap) { + Ext.raise('Cannot redefine field, use the summary property on the field.'); + } + } + // Store these in an array so we have a predictable order when subclassing + proto.summaryFields = summaries; + } + }, + initValidators: function(data, cls, proto) { + var superValidators = proto.validators, + validators, field, copy, validatorDefs, i, length, fieldValidator, name, validator, item; + if (superValidators) { + validators = {}; + for (field in superValidators) { + validators[field] = Ext.Array.clone(superValidators[field]); + } + } + validatorDefs = data.validators || data.validations; + if (data.validations) { + delete data.validations; + Ext.log.warn((cls.$className || 'Ext.data.Model') + ': validations has been deprecated. Please use validators instead.'); + } + if (validatorDefs) { + delete data.validators; + validators = validators || {}; + // Support older array syntax + if (Ext.isArray(validatorDefs)) { + copy = {}; + for (i = 0 , length = validatorDefs.length; i < length; ++i) { + item = validatorDefs[i]; + name = item.field; + if (!copy[name]) { + copy[name] = []; + } + // Check for function form + item = item.fn || item; + copy[name].push(item); + } + validatorDefs = copy; + } + for (name in validatorDefs) { + fieldValidator = validatorDefs[name]; + if (!Ext.isArray(fieldValidator)) { + fieldValidator = [ + fieldValidator + ]; + } + validator = validators[name]; + if (validator) { + // Declared in super + Ext.Array.push(validator, fieldValidator); + } else { + validators[name] = fieldValidator; + } + } + } + if (validators) { + for (name in validators) { + field = cls.getField(name); + if (field) { + field.setModelValidators(validators[name]); + } + } + } + cls.validators = proto.validators = validators; + }, + initAssociations: function(schema, data, cls) { + // Handle keyless associations + var associations = data.associations, + belongsTo = data.belongsTo, + hasMany = data.hasMany, + hasOne = data.hasOne, + // manyToMany can't be declared via reference + matrices = data.manyToMany, + i, length, assoc, o; + delete data.associations; + delete data.belongsTo; + delete data.hasMany; + delete data.hasOne; + delete data.manyToMany; + if (matrices) { + schema.addMatrices(cls, matrices); + } + if (associations) { + associations = Ext.isArray(associations) ? associations : [ + associations + ]; + for (i = 0 , length = associations.length; i < length; ++i) { + assoc = associations[i]; + o = Ext.apply({}, assoc); + delete o.type; + switch (assoc.type) { + case 'belongsTo': + schema.addBelongsTo(cls, o); + break; + case 'hasMany': + schema.addHasMany(cls, o); + break; + case 'hasOne': + schema.addHasOne(cls, o); + break; + default: + Ext.raise('Invalid association type: "' + assoc.type + '"'); + } + } + } + if (belongsTo) { + belongsTo = Ext.isArray(belongsTo) ? belongsTo : [ + belongsTo + ]; + for (i = 0 , length = belongsTo.length; i < length; ++i) { + schema.addBelongsTo(cls, belongsTo[i]); + } + } + if (hasMany) { + hasMany = Ext.isArray(hasMany) ? hasMany : [ + hasMany + ]; + for (i = 0 , length = hasMany.length; i < length; ++i) { + schema.addHasMany(cls, hasMany[i]); + } + } + if (hasOne) { + hasOne = Ext.isArray(hasOne) ? hasOne : [ + hasOne + ]; + for (i = 0 , length = hasOne.length; i < length; ++i) { + schema.addHasOne(cls, hasOne[i]); + } + } + schema.afterKeylessAssociations(cls); + }, + initIdentifier: function(data, cls, proto) { + var identifier = data.identifier || data.idgen, + superIdent = proto.identifier || cls.schema._defaultIdentifier, + generatorPrefix; + if (data.idgen) { + Ext.log.warn('Ext.data.Model: idgen has been deprecated. Please use identifier instead.'); + } + if (identifier) { + delete data.identifier; + delete data.idgen; + // An idgen was specified on the definition, use it explicitly. + identifier = Ext.Factory.dataIdentifier(identifier); + } else if (superIdent) { + // If we have a cloneable instance, and we don't have an id + // clone it. If we have an id, then we should use the same + // instance since it's the same as looking it up via id. + if (superIdent.clone && !superIdent.getId()) { + identifier = superIdent.clone(); + } else if (superIdent.isGenerator) { + identifier = superIdent; + } else { + identifier = Ext.Factory.dataIdentifier(superIdent); + } + } + cls.identifier = proto.identifier = identifier; + if (!identifier) { + // If we didn't find one, create it and push it onto the class. + // Don't put it on the prototype, so a subclass will create + // it's own generator. If we have an anonymous model, go ahead and + // generate a unique prefix for it. + generatorPrefix = cls.entityName; + if (!generatorPrefix) { + generatorPrefix = Ext.id(null, 'extModel'); + } + cls.identifier = Ext.Factory.dataIdentifier({ + type: 'sequential', + prefix: generatorPrefix + '-' + }); + } + }, + findValidator: function(validators, name, cfg) { + var type = cfg.type || cfg, + field = validators[name], + len, i, item; + if (field) { + for (i = 0 , len = field.length; i < len; ++i) { + item = field[i]; + if (item.type === type) { + return item; + } + } + } + return null; + }, + /** + * This method produces the `initializeFn` for this class. If there are no fields + * requiring {@link Ext.data.field.Field#cfg-convert conversion} and no fields requiring + * a {@link Ext.data.field.Field#defaultValue default value} then this method will + * return `null`. + * @return {Function} The `initializeFn` for this class (or null). + * @private + */ + makeInitializeFn: function(cls) { + var code = [ + 'var ' + ], + body = [ + '\nreturn function (e) {\n var data = e.data, v;\n' + ], + work = 0, + bc, ec, // == beginClone, endClone + convert, expr, factory, field, fields, fs, hasDefValue, i, length; + if (!(fields = cls.rankedFields)) { + // On the first edit of a record of this type we need to ensure we have the + // topo-sort done: + fields = cls.rankFields(); + } + for (i = 0 , length = fields.length; i < length; ++i) { + // The generated method declares vars for each field using "f0".."fN' as the + // name. These are used to access properties of the field (e.g., the convert + // method or defaultValue). + field = fields[i]; + fs = 'f' + i; + convert = field.convert; + if (i) { + code.push(', \n '); + } + code.push(fs, ' = $fields[' + i + ']'); + // this can be helpful when debugging (at least in Chrome): + code.push(' /* ', field.name, ' */'); + // NOTE: added string literals are "folded" by the compiler so we + // are better off doing an "'foo' + 'bar'" then "'foo', 'bar'". But + // for variables we are better off pushing them into the array for + // the final join. + if ((hasDefValue = (field.defaultValue !== undefined)) || convert) { + // For non-calculated fields that have some work required (a convert method + // and/or defaultValue), generate a chunk of logic appropriate for the + // field. + //expr = data["fieldName"]; + expr = 'data["' + field.name + '"]'; + ++work; + bc = ec = ''; + if (field.cloneDefaultValue) { + bc = 'Ext.clone('; + ec = ')'; + } + body.push('\n'); + if (convert && hasDefValue) { + // v = data.fieldName; + // if (v !== undefined) { + // v = f2.convert(v, e); + // } + // if (v === undefined) { + // v = f2.defaultValue; + // // or + // v = Ext.clone(f2.defaultValue); + // } + // data.fieldName = v; + // + body.push(' v = ', expr, ';\n' + ' if (v !== undefined) {\n' + ' v = ', fs, '.convert(v, e);\n' + ' }\n' + ' if (v === undefined) {\n' + ' v = ', bc, fs, '.defaultValue', ec, ';\n' + ' }\n' + ' ', expr, ' = v;'); + } else if (convert) { + // no defaultValue + // v = f2.convert(data.fieldName,e); + // if (v !== undefined) { + // data.fieldName = v; + // } + // + body.push(' v = ', fs, '.convert(', expr, ',e);\n' + ' if (v !== undefined) {\n' + ' ', expr, ' = v;\n' + ' }\n'); + } else if (hasDefValue) { + // no convert + // if (data.fieldName === undefined) { + // data.fieldName = f2.defaultValue; + // // or + // data.fieldName = Ext.clone(f2.defaultValue); + // } + // + body.push(' if (', expr, ' === undefined) {\n' + ' ', expr, ' = ', bc, fs, '.defaultValue', ec, ';\n' + ' }\n'); + } + } + } + if (!work) { + // There are no fields that need special processing + return Ext.emptyFn; + } + code.push(';\n'); + code.push.apply(code, body); + code.push('}'); + code = code.join(''); + // Ensure that Ext in the function code refers to the same Ext that we are using here. + // If we are in a sandbox, global.Ext might be different. + factory = new Function('$fields', 'Ext', code); + return factory(fields, Ext); + } + } + } +}, // static +// privates +function() { + var Model = this, + proto = Model.prototype, + Schema = Ext.data.schema.Schema, + defaultSchema; + Model.proxyConfig = proto.proxy; + delete proto.proxy; + // Base Model class may be used. It needs an empty fields array. + Model.fields = []; + // Base Model class may be used. It needs an empty fieldsMap hash. + Model.fieldsMap = proto.fieldsMap = {}; + Model.schema = proto.schema = Schema.get(proto.schema); + proto.idField = new Ext.data.field.Field(proto.idProperty); + Model.identifier = new Ext.data.identifier.Sequential(); + Model.onExtended(function(cls, data) { + var proto = cls.prototype, + schemaName = data.schema, + superCls = proto.superclass.self, + schema, entityName, proxy; + cls.idProperty = data.idProperty || proto.idProperty; + if (schemaName) { + delete data.schema; + schema = Schema.get(schemaName); + } else if (!(schema = proto.schema)) { + schema = defaultSchema || (defaultSchema = Schema.get('default')); + } + // These are in "privates" so we manually make them inherited: + cls.rankFields = Model.rankFields; + cls.topoAdd = Model.topoAdd; + // if we picked up a schema from cls.prototype.schema, it is because it was found + // in the prototype chain on a base class. + proto.schema = cls.schema = schema; + // Unless specified on the declaration data, we need to provide the entityName of + // the new Entity-derived class. Store it on the prototype and the class. + if (!(entityName = data.entityName)) { + proto.entityName = entityName = schema.getEntityName(cls); + if (!entityName) { + if (data.associations) { + Ext.raise('Anonymous entities cannot specify "associations"'); + } + if (data.belongsTo) { + Ext.raise('Anonymous entities cannot specify "belongsTo"'); + } + if (data.hasMany) { + Ext.raise('Anonymous entities cannot specify "hasMany"'); + } + if (data.hasOne) { + Ext.raise('Anonymous entities cannot specify "hasOne"'); + } + if (data.matrices) { + Ext.raise('Anonymous entities cannot specify "manyToMany"'); + } + } + } + cls.entityName = entityName; + cls.fieldExtractors = {}; + Model.initIdentifier(data, cls, proto); + Model.initFields(data, cls, proto); + Model.initValidators(data, cls, proto); + if (!data.isSummaryModel) { + Model.initSummaries(data, cls, proto); + } + // This is a compat hack to allow "rec.fields.items" to work as it used to when + // fields was a MixedCollection + cls.fields.items = cls.fields; + if (entityName) { + schema.addEntity(cls); + Model.initAssociations(schema, data, cls); + } + proxy = data.proxy; + if (proxy) { + delete data.proxy; + } else if (superCls !== Model) { + proxy = superCls.proxyConfig || superCls.proxy; + } + cls.proxyConfig = proxy; + }); +}); + +/** + * @protected + * Simple wrapper class that represents a set of records returned by a Proxy. + */ +Ext.define('Ext.data.ResultSet', { + /** + * @property {Boolean} isResultSet + * Identifies this class as a result set. + */ + isResultSet: true, + $configPrefixed: false, + config: { + /** + * @cfg {Boolean} loaded + * True if the records have already been loaded. This is only meaningful when dealing with + * SQL-backed proxies. + */ + loaded: true, + /** + * @cfg {Number} count + * The number of records in this ResultSet. Note that total may differ from this number. + */ + count: null, + /** + * @cfg {Number} total + * The total number of records reported by the data source. This ResultSet may form a subset of + * those records (see {@link #count}). + */ + total: null, + /** + * @cfg {Number} remoteTotal + * The total number of records reported by the remote data source. + */ + remoteTotal: null, + /** + * @cfg {Boolean} success + * True if the ResultSet loaded successfully, false if any errors were encountered. + */ + success: false, + /** + * @cfg {Ext.data.Model[]/Object[]} records (required) + * The array of record instances or record config objects. + */ + records: null, + /** + * @cfg {String} message + * The message that was read in from the data + */ + message: null, + /** + * @cfg {Object} metadata + * The metadata object from a server sourced JSON data packet. + */ + metadata: null, + /** + * @cfg {Ext.data.Model[]} groupData + * The grouping data. + */ + groupData: null, + /** + * @cfg {Ext.data.Model} summaryData + * The summary data. + */ + summaryData: null + }, + /** + * Creates the resultSet + * @param {Object} [config] Config object. + */ + constructor: function(config) { + this.initConfig(config); + }, + getCount: function() { + var count = this.callParent(), + records; + if (!count) { + records = this.getRecords(); + if (records) { + count = records.length; + } + } + return count; + } +}); + +/** + * Readers are used to interpret data to be loaded into a {@link Ext.data.Model Model} instance or a {@link + * Ext.data.Store Store} - often in response to an AJAX request. In general there is usually no need to create + * a Reader instance directly, since a Reader is almost always used together with a {@link Ext.data.proxy.Proxy Proxy}, + * and is configured using the Proxy's {@link Ext.data.proxy.Proxy#cfg-reader reader} configuration property: + * + * Ext.create('Ext.data.Store', { + * model: 'User', + * proxy: { + * type: 'ajax', + * url : 'users.json', + * reader: { + * type: 'json', + * rootProperty: 'users' + * } + * }, + * }); + * + * The above reader is configured to consume a JSON string that looks something like this: + * + * { + * "success": true, + * "users": [ + * { "name": "User 1" }, + * { "name": "User 2" } + * ] + * } + * + * + * # Loading Nested Data + * + * Readers have the ability to automatically load deeply-nested data objects based on the {@link Ext.data.schema.Association associations} + * configured on each Model. Below is an example demonstrating the flexibility of these associations in a + * fictional CRM system which manages a User, their Orders, OrderItems and Products. First we'll define the models: + * + * Ext.define("User", { + * extend: 'Ext.data.Model', + * fields: [ + * 'id', 'name' + * ], + * + * hasMany: {model: 'Order', name: 'orders'}, + * + * proxy: { + * type: 'rest', + * url : 'users.json', + * reader: { + * type: 'json', + * rootProperty: 'users' + * } + * } + * }); + * + * Ext.define("Order", { + * extend: 'Ext.data.Model', + * fields: [ + * 'id', 'total' + * ], + * + * hasMany : {model: 'OrderItem', name: 'orderItems', associationKey: 'order_items'}, + * belongsTo: 'User' + * }); + * + * Ext.define("OrderItem", { + * extend: 'Ext.data.Model', + * fields: [ + * 'id', 'price', 'quantity', 'order_id', 'product_id' + * ], + * + * belongsTo: ['Order', {model: 'Product', associationKey: 'product'}] + * }); + * + * Ext.define("Product", { + * extend: 'Ext.data.Model', + * fields: [ + * 'id', 'name' + * ], + * + * hasMany: 'OrderItem' + * }); + * + * This may be a lot to take in - basically a User has many Orders, each of which is composed of several OrderItems. + * Finally, each OrderItem has a single Product. This allows us to consume data like this: + * + * { + * "users": [ + * { + * "id": 123, + * "name": "Ed", + * "orders": [ + * { + * "id": 50, + * "total": 100, + * "order_items": [ + * { + * "id" : 20, + * "price" : 40, + * "quantity": 2, + * "product" : { + * "id": 1000, + * "name": "MacBook Pro" + * } + * }, + * { + * "id" : 21, + * "price" : 20, + * "quantity": 3, + * "product" : { + * "id": 1001, + * "name": "iPhone" + * } + * } + * ] + * } + * ] + * } + * ] + * } + * + * The JSON response is deeply nested - it returns all Users (in this case just 1 for simplicity's sake), all of the + * Orders for each User (again just 1 in this case), all of the OrderItems for each Order (2 order items in this case), + * and finally the Product associated with each OrderItem. Now we can read the data and use it as follows: + * + * var store = Ext.create('Ext.data.Store', { + * model: "User" + * }); + * + * store.load({ + * callback: function() { + * //the user that was loaded + * var user = store.first(); + * + * console.log("Orders for " + user.get('name') + ":") + * + * //iterate over the Orders for each User + * user.orders().each(function(order) { + * console.log("Order ID: " + order.getId() + ", which contains items:"); + * + * //iterate over the OrderItems for each Order + * order.orderItems().each(function(orderItem) { + * //we know that the Product data is already loaded, so we can use the synchronous getProduct + * //usually, we would use the asynchronous version (see #belongsTo) + * var product = orderItem.getProduct(); + * + * console.log(orderItem.get('quantity') + ' orders of ' + product.get('name')); + * }); + * }); + * } + * }); + * + * Running the code above results in the following: + * + * Orders for Ed: + * Order ID: 50, which contains items: + * 2 orders of MacBook Pro + * 3 orders of iPhone + */ +Ext.define('Ext.data.reader.Reader', { + alternateClassName: [ + 'Ext.data.Reader', + 'Ext.data.DataReader' + ], + requires: [ + 'Ext.data.ResultSet', + 'Ext.XTemplate', + 'Ext.util.LruCache' + ], + mixins: [ + 'Ext.mixin.Observable', + 'Ext.mixin.Factoryable' + ], + alias: 'reader.base', + factoryConfig: { + defaultType: null + }, + config: { + /** + * @cfg {String/Function} [groupRootProperty] + * Name of the property from which to retrieve remote grouping summary information. + * There should be an item for each group. + * + * The remote summary data should be parseable as a {@link #model} used by this reader. + */ + groupRootProperty: '', + /** + * @cfg {Boolean} [implicitIncludes] + * True to automatically parse models nested within other models in a response object. See the + * Ext.data.reader.Reader intro docs for full explanation. + */ + implicitIncludes: true, + /** + * @cfg {Boolean} [keepRawData] Determines if the Reader will keep raw data + * received from the server in the {@link #rawData} property. + * + * While this might seem useful to do additional data processing, keeping raw data + * might cause adverse effects such as memory leaks. It is recommended to set + * `keepRawData` to `false` if you do not need the raw data. + * + * If you need to process data packet to extract additional data such as row summaries, + * it is recommended to use {@link #transform} function for that purpose. + * + * Note that starting with Ext JS 6.0 the default behavior has been changed to + * **not** keep the raw data because of the high potential for memory leaks. + * @since 5.1.1 + */ + keepRawData: null, + /** + * @cfg {String/Function} messageProperty + * The name of the property which contains a response message for exception handling. If you want to return a false success + * response from the server, maybe due to some server-side validation, the messageProperty can hold the error message. For + * example: + * + * { + * "success": false, + * "error": "There was an error with your request" + * } + * + * You can retrieve this error message in a callback when loading a {@link Ext.data.Store Store} or {@link Ext.data.Model Model} like: + * + * var store = new Ext.data.Store({ + * fields : ['foo'], + * proxy : { + * type : 'ajax', + * url : 'data.json', + * reader : { + * type : 'json', + * rootProperty : 'data', + * messageProperty : 'error' + * } + * } + * }); + * + * store.load({ + * callback: function(records, operation, success) { + * if (success) { + * // ... + * } else { + * var error = operation.getError(); + * + * Ext.Msg.alert('Error', error); + * } + * } + * }); + * + * In this example, the callback will execute with `success` being `false` and will therefore show the {@link Ext.MessageBox#alert Ext.Msg.alert} with + * the error string returned in the response. + */ + messageProperty: '', + /** + * @cfg {String/Ext.data.Model} [model] + * The model to use for this reader. This config is only required if the reader is being used + * without a proxy, otherwise the proxy will automatically set the model. + */ + model: null, + /** + * @cfg {Ext.data.proxy.Proxy} [proxy] + * The proxy attached to this reader. Typically only needed onMetaChange so that + * we can set the new model on the proxy. + * @private + */ + proxy: null, + /** + * @cfg {Boolean} [readRecordsOnFailure] + * True to extract the records from a data packet even if the {@link #successProperty} returns false. + */ + readRecordsOnFailure: true, + /** + * @cfg {String/Function} rootProperty + * The property that contains data items corresponding to the + * Model(s) of the configured Reader. `rootProperty` varies by Reader type. + * + * ##JSON Reader + * `rootProperty` is a property name. It may also be a dot-separated + * list of property names if the root is nested. The root JSON array will be + * used by default. + * + * // rootPropety config + * rootProperty: 'embedded.myresults' + * + * // server response + * { + * embedded: { + * myresults: [{ + * name: 'Scott', + * age: 22 + * }, { + * name: 'Ramona', + * age: 24 + * }] + * }, + * success: true + * } + * + * ##XML Reader + * `rootProperty` is a CSS selector. The root XML element will be used + * by default. + * + * // rootProperty config (plus record config) + * rootProperty: 'myresults', + * record: 'user' + * + * // server response + * + * + * + * + * Scott + * 22 + * + * + * Ramona + * 24 + * + * + * + * + * ##Array Reader + * `rootProperty` is not typically applicable since the data is assumed to be a + * single-level array of arrays. However, if the array of records is returned + * within a JSON response a `rootProperty` config may be used: + * + * // rootProperty config + * rootProperty: 'embedded.myresults' + * + * // server response + * { + * embedded: { + * myresults: [['Scott', 22], ['Ramona', 24]] + * }, + * success: true + * } + * + * ##rootProperty as a function + * The `rootProperty` may also be a function that returns the root node from + * the dataset. For example: + * + * var store = Ext.create('Ext.data.TreeStore', { + * proxy: { + * type: 'memory', + * reader: { + * type: 'json', + * rootProperty: function(data){ + * // Extract child nodes from the items or children property in the dataset + * return data.items || data.children; + * } + * } + * }, + * data: { + * items: [{ + * text: 'item 1', + * children: [{ + * text: 'child A', + * leaf: true + * }] + * }] + * } + * }); + * + * Ext.create('Ext.tree.Panel', { + * title: 'rootProperty as a function', + * width: 200, + * height:150, + * store: store, + * rootVisible: false, + * renderTo: Ext.getBody() + * }); + */ + rootProperty: '', + /** + * @cfg {String} [successProperty] + * Name of the property from which to retrieve the `success` attribute, the value of which indicates + * whether a given request succeeded or failed (typically a boolean or 'true'|'false'). See + * {@link Ext.data.proxy.Server}.{@link Ext.data.proxy.Server#exception exception} for additional information. + */ + successProperty: 'success', + /** + * @cfg {String/Function} [summaryRootProperty] + * Name of the property from which to retrieve remote summary information. + * + * The remote summary data should be parseable as a {@link #model} used by this reader. + */ + summaryRootProperty: '', + /** + * @cfg {String} [totalProperty] + * Name of the property from which to retrieve the total number of records in the dataset. This is only needed if + * the whole dataset is not passed in one go, but is being paged from the remote server. + */ + totalProperty: 'total', + /** + * @cfg {Function|String|Object} [transform] + * If a transform function is set, it will be invoked just before {@link #readRecords} executes. + * It is passed the raw (deserialized) data object. The transform function returns a data object, which can be + * a modified version of the original data object, or a completely new data object. The transform can + * be a function, or a method name on the Reader instance, or an object with a 'fn' key + * and an optional 'scope' key. + * + * Example usage: + * + * Ext.create('Ext.data.Store', { + * model: 'User', + * proxy: { + * type: 'ajax', + * url : 'users.json', + * reader: { + * type: 'json', + * transform: { + * fn: function(data) { + * // do some manipulation of the raw data object + * return data; + * }, + * scope: this + * } + * } + * }, + * }); + * + */ + transform: null, + /** + * @cfg {String} [typeProperty] + * The name of the property in a node raw data block which indicates the type of the model to be created from that raw data. Useful for heterogeneous trees. + * + * For example, hierarchical geographical data may look like this: + * + * { + * nodeType: 'Territory', + * name: 'EMEA', + * children: [{ + * nodeType: 'Country', + * name: 'United Kingdon', + * children: [{ + * nodeType: 'City', + * name: 'London' + * }] + * }] + * } + * + * You would configure the typeProperty in this case to be `"nodeType"` which would cause the models named "Territory", "Country" and "City" to + * be used. + */ + typeProperty: '' + }, + /** + * @property {Object} rawData + * The raw data object that was last passed to {@link #readRecords}. rawData is populated + * based on the results of {@link Ext.data.proxy.Server#processResponse}. rawData will + * maintain a cached copy of the last successfully returned records. In other words, + * if processResponse is unsuccessful, the records from the last successful response + * will remain cached in rawData. + * + * Since Ext JS 5.1.1 you can use the {@link #keepRawData} config option to + * control this behavior. + */ + /** + * @property {Object} metaData + * The raw meta data that was most recently read, if any. Meta data can include existing + * Reader config options like {@link #totalProperty}, etc. that get + * automatically applied to the Reader, and those can still be accessed directly from the Reader + * if needed. However, meta data is also often used to pass other custom data to be processed + * by application code. For example, it is common when reconfiguring the data model of a grid to + * also pass a corresponding column model config to be applied to the grid. Any such data will + * not get applied to the Reader directly (it just gets passed through and is ignored by Ext). + * This metaData property gives you access to all meta data that was passed, including any such + * custom data ignored by the reader. + * + * This is a read-only property, and it will get replaced each time a new meta data object is + * passed to the reader. Note that typically you would handle proxy's + * {@link Ext.data.proxy.Proxy#metachange metachange} event which passes this exact same meta + * object to listeners. However this property is available if it's more convenient to access it + * via the reader directly in certain cases. + * @readonly + */ + /** + * @property {Boolean} isReader + * `true` in this class to identify an object as an instantiated Reader, or subclass thereof. + **/ + isReader: true, + /** + * @event exception + * Fires when the reader receives improperly encoded data from the server + * @param {Ext.data.reader.Reader} reader A reference to this reader + * @param {XMLHttpRequest} response The XMLHttpRequest response object + * @param {Ext.data.ResultSet} error The error object + */ + /** + * Creates new Reader. + * @param {Object} [config] Config object. + */ + constructor: function(config) { + if (config && config.hasOwnProperty('root')) { + config = Ext.apply({}, config); + config.rootProperty = config.root; + delete config.root; + Ext.log.error('Ext.data.reader.Reader: Using the deprecated "root" configuration. Use "rootProperty" instead.'); + } + var me = this; + me.duringInit = 1; + // Will call initConfig + me.mixins.observable.constructor.call(me, config); + --me.duringInit; + me.buildExtractors(); + }, + forceBuildExtractors: function() { + if (!this.duringInit) { + this.buildExtractors(true); + } + }, + updateGroupRootProperty: function() { + this.forceBuildExtractors(); + }, + updateMessageProperty: function() { + this.forceBuildExtractors(); + }, + applyModel: function(model) { + return Ext.data.schema.Schema.lookupEntity(model); + }, + updateSuccessProperty: function() { + this.forceBuildExtractors(); + }, + updateTotalProperty: function() { + this.forceBuildExtractors(); + }, + applyTransform: function(transform) { + if (transform) { + if (Ext.isFunction(transform)) { + transform = { + fn: transform + }; + } else if (transform.charAt) { + // faster than Ext.isString() + transform = { + fn: this[transform] + }; + } + return transform.fn.bind(transform.scope || this); + } + return transform; + }, + /** + * Reads the given response object. This method normalizes the different types of response object that may be passed to it. + * If it's an XMLHttpRequest object, hand off to the subclass' {@link #getResponseData} method. + * Else, hand off the reading of records to the {@link #readRecords} method. + * @param {Object} response The response object. This may be either an XMLHttpRequest object or a plain JS object + * @param {Object} [readOptions] Various options that instruct the reader on how to read the data + * @param {Function} [readOptions.recordCreator] A function to construct the model based on the processed data. By default, + * this just calls the model constructor and passes the raw data. + * @return {Ext.data.ResultSet} The parsed or default ResultSet object + */ + read: function(response, readOptions) { + var data, result, responseText; + if (response) { + responseText = response.responseText; + if (responseText) { + result = this.getResponseData(response); + if (result && result.__$isError) { + return new Ext.data.ResultSet({ + total: 0, + count: 0, + records: [], + success: false, + message: result.msg + }); + } else { + data = this.readRecords(result, readOptions); + } + } else if (responseText !== '') { + data = this.readRecords(response, readOptions); + } + } + return data || this.nullResultSet; + }, + /** + * Returns the shared null result set. + * @return {Ext.data.ResultSet} The null result set. + * + * @private + */ + getNullResultSet: function() { + return this.nullResultSet; + }, + /** + * Creates an object that identifies a read error occurred. + * @param {String} msg An error message to include + * @return {Object} An error object + * + * @private + */ + createReadError: function(msg) { + return { + __$isError: true, + msg: msg + }; + }, + /** + * Abstracts common functionality used by all Reader subclasses. Each subclass is expected to call this function + * before running its own logic and returning the Ext.data.ResultSet instance. For most Readers additional + * processing should not be needed. + * @param {Object} data The raw data object + * @param {Object} [readOptions] See {@link #read} for details. + * @param {Object} [internalReadOptions] (private) + * @return {Ext.data.ResultSet} A ResultSet object + */ + readRecords: function(data, readOptions, internalReadOptions) { + var me = this, + recordsOnly = internalReadOptions && internalReadOptions.recordsOnly, + asRoot = internalReadOptions && internalReadOptions.asRoot, + groupData = null, + summaryData = null, + success, recordCount, records, root, remoteTotal, total, value, message, transform, meta, summaryOptions; + // Extract the metadata to return with the ResultSet. + // If found reconfigure accordingly. + // The calling Proxy fires its metachange event if it finds metadata in the ResultSet. + meta = me.getMeta ? me.getMeta(data) : data.metaData; + if (meta) { + me.onMetaChange(meta); + } + transform = me.getTransform(); + if (transform) { + data = transform(data); + } + me.buildExtractors(); + if (me.getKeepRawData()) { + me.rawData = data; + } + if (me.hasListeners.rawdata) { + me.fireEventArgs('rawdata', [ + data + ]); + } + data = me.getData(data); + success = true; + recordCount = 0; + records = []; + if (me.getSuccessProperty()) { + value = me.getSuccess(data); + if (value === false || value === 'false') { + success = false; + } + } + if (me.getMessageProperty()) { + message = me.getMessage(data); + } + // Only try and extract other data if call was successful + if (success || me.getReadRecordsOnFailure()) { + // If we pass an array as the data, we don't use getRoot on the data. + // Instead the root equals to the data. + root = (asRoot || Ext.isArray(data)) ? data : me.getRoot(data); + if (root) { + total = root.length; + } + if (me.getTotalProperty()) { + value = parseInt(me.getTotal(data), 10); + if (!isNaN(value)) { + remoteTotal = total = value; + } + } + if (root) { + records = me.extractData(root, readOptions); + recordCount = records.length; + } + if (me.getGroupRootProperty()) { + root = me.getGroupRoot(data); + if (root) { + summaryOptions = { + includes: false, + model: me.getModel().getSummaryModel() + }; + groupData = me.extractData(root, summaryOptions) || null; + } + } + if (me.getSummaryRootProperty()) { + root = me.getSummaryRoot(data); + if (root) { + summaryOptions = summaryOptions || { + includes: false, + model: me.getModel().getSummaryModel() + }; + summaryData = me.extractData(root, summaryOptions) || null; + // This always returns an array, so transform it + if (summaryData) { + summaryData = summaryData[0]; + } + } + } + } + return recordsOnly ? records : new Ext.data.ResultSet({ + total: total || recordCount, + remoteTotal: remoteTotal, + metadata: meta, + count: recordCount, + records: records, + success: success, + message: message, + groupData: groupData, + summaryData: summaryData + }); + }, + /** + * Returns extracted, type-cast rows of data. + * @param {Object[]/Object} root from server response + * @param {Object} [readOptions] An object containing extra options. + * @param {Function} [readOptions.model] The Model constructor to use. + * @param {Function} [readOptions.recordCreator] A function to use to create and initialize records. By default a function + * is supplied which creates *non-phantom* records on the assumnption that a Reader is going to be used to read server-supplied data. + * @param {Object} [readOptions.recordCreator.data] The raw data used to create a record. + * @param {Function} [readOptions.recordCreator.Model] The Model constructor to use to create the record. + * @return {Array} An array of records containing the extracted data + * @private + */ + extractData: function(root, readOptions) { + var me = this, + entityType = readOptions && readOptions.model ? Ext.data.schema.Schema.lookupEntity(readOptions.model) : me.getModel(), + schema = entityType.schema, + includes = readOptions && 'includes' in readOptions ? readOptions.includes : schema.hasAssociations(entityType) && me.getImplicitIncludes(), + fieldExtractorInfo = me.getFieldExtractorInfo(entityType), + length = root.length, + records = new Array(length), + typeProperty = me.getTypeProperty(), + reader, node, nodeType, record, i; + if (!length && Ext.isObject(root)) { + root = [ + root + ]; + length = 1; + } + for (i = 0; i < length; i++) { + record = root[i]; + if (!record.isModel) { + // If we're given a model instance in the data, just push it on + // without doing any conversion. Otherwise, create a record. + node = record; + // This Reader may be configured to produce different model types based on + // a differentiator field in the incoming data: + // typeProperty name be a string, a function which yields the child type, or an object: { + // name: 'mtype', + // namespace: 'MyApp' + // } + if (typeProperty && (nodeType = me.getChildType(schema, node, typeProperty))) { + reader = nodeType.getProxy().getReader(); + record = reader.extractRecord(node, readOptions, nodeType, schema.hasAssociations(nodeType) && reader.getImplicitIncludes(), reader.getFieldExtractorInfo(nodeType)); + } else { + record = me.extractRecord(node, readOptions, entityType, includes, fieldExtractorInfo); + } + // Generally we don't want to have references to XML documents + // or XML nodes to hang around in memory but Trees need to be able + // to access the raw XML node data in order to process its children. + // See https://sencha.jira.com/browse/EXTJS-15785 and + // https://sencha.jira.com/browse/EXTJS-14286 + if (record.isModel && record.isNode) { + record.raw = node; + } + } + if (record.onLoad) { + record.onLoad(); + } + records[i] = record; + } + return records; + }, + // Based upon a Reader's typeProperty config, determine the type of child node to create from the raw data + getChildType: function(schema, rawNode, typeProperty) { + var namespace; + switch (typeof typeProperty) { + case 'string': + return schema.getEntity(rawNode[typeProperty]); + case 'object': + namespace = typeProperty.namespace; + return schema.getEntity((namespace ? namespace + '.' : '') + rawNode[typeProperty.name]); + case 'function': + return schema.getEntity(typeProperty(rawNode)); + } + }, + extractRecordData: function(node, readOptions) { + var entityType = readOptions && readOptions.model ? Ext.data.schema.Schema.lookupEntity(readOptions.model) : this.getModel(), + fieldExtractorInfo = this.getFieldExtractorInfo(entityType); + return this.extractRecord(node, readOptions, entityType, false, fieldExtractorInfo); + }, + extractRecord: function(node, readOptions, entityType, includes, fieldExtractorInfo) { + var me = this, + creatorFn = (readOptions && readOptions.recordCreator) || me.defaultRecordCreator, + modelData, record; + // Create a record with an empty data object. + // Populate that data object by extracting and converting field values from raw data. + // Must pass the ID to use because we pass no data for the constructor to pluck an ID from + modelData = me.extractModelData(node, fieldExtractorInfo); + record = creatorFn.call(me, modelData, entityType || me.getModel(), readOptions); + if (includes && record.isModel) { + me.readAssociated(record, node, readOptions); + } + return record; + }, + getFieldExtractorInfo: function(entityType) { + var extractors = entityType.fieldExtractors, + type, extractor; + // If the base Ext.data.Model class is being used, there will be no extractor info + // The raw data block will be imported unchanged. + if (!extractors) { + return; + } + type = this.$className; + extractor = extractors[type]; + // If we have no extractors, buildFieldExtractors will return null, + // so we never need to rebuild them + if (extractor === undefined) { + extractors[type] = extractor = this.buildFieldExtractors(entityType); + } + return extractor; + }, + buildFieldExtractors: function(entityType) { + var fields = entityType.getFields(), + len = fields.length, + buffer = [], + extractors = [], + out = null, + cnt = 0, + field, name, i, extractor; + for (i = 0; i < len; ++i) { + field = fields[i]; + extractor = this.createFieldAccessor(field); + if (extractor) { + name = field.name; + // Use [] property access since we may have non-JS looking field names + buffer.push('val = extractors[' + cnt + '](raw, self); if (val !== undefined) { data[\'' + name + '\'] = val; }'); + extractors.push(extractor); + ++cnt; + } + } + if (buffer.length) { + out = { + extractors: extractors, + fn: new Function('raw', 'data', 'extractors', 'self', 'var val;' + buffer.join('\n')) + }; + } + return out; + }, + defaultRecordCreator: function(data, Model) { + return new Model(data); + }, + defaultRecordCreatorFromServer: function(data, Model) { + var record = new Model(data); + // If the server did not include an id in the response data, the Model constructor will mark the record as phantom. + // We need to set phantom to false here because records created from a server response using a reader by definition are not phantom records. + record.phantom = false; + return record; + }, + getModelData: function(raw) { + return {}; + }, + extractModelData: function(raw, fieldExtractorInfo) { + var data = this.getModelData(raw), + fn; + // We may not have any mappings to process + if (fieldExtractorInfo) { + fn = fieldExtractorInfo.fn; + fn(raw, data, fieldExtractorInfo.extractors, this); + } + return data; + }, + /** + * Loads the record associations from the data object. + * @param {Ext.data.Model} record The record to load associations for. + * @param {Object} data The raw data object. + * @param {Object} readOptions See {@link #read}. + * + * @private + */ + readAssociated: function(record, data, readOptions) { + var roles = record.associations, + key, role; + for (key in roles) { + if (roles.hasOwnProperty(key)) { + role = roles[key]; + // The class for the other role may not have loaded yet + if (role.cls) { + role.read(record, data, this, readOptions); + } + } + } + }, + /** + * @method + * This method provides a hook to do any data transformation before the reading process + * begins. By default this function just returns what is passed to it. It can be + * overridden in a subclass to return something else. + * See {@link Ext.data.reader.Xml XmlReader} for an example. + * + * @param {Object} data The data object + * @return {Object} The normalized data object + * @protected + * @template + */ + getData: Ext.identityFn, + /** + * @method + * This will usually need to be implemented in a subclass. Given a generic data object (the type depends on the type + * of data we are reading), this function should return the object as configured by the Reader's 'root' meta data config. + * See XmlReader's getRoot implementation for an example. By default the same data object will simply be returned. + * + * @param {Object} data The data object + * @return {Object} The same data object + * @private + */ + getRoot: Ext.identityFn, + /** + * Takes a raw response object (as passed to the {@link #read} method) and returns the useful data + * segment from it. This must be implemented by each subclass. + * @param {Object} response The response object + * @return {Object} The extracted data from the response. For example, a JSON object or an XML document. + */ + getResponseData: function(response) { + Ext.raise("getResponseData must be implemented in the Ext.data.reader.Reader subclass"); + }, + /** + * @private + * Reconfigures the meta data tied to this Reader + */ + onMetaChange: function(meta) { + var me = this, + fields = meta.fields, + model, newModel, clientIdProperty, proxy; + // save off the raw meta data + me.metaData = meta; + // set any reader-specific configs from meta if available + if (meta.root) { + me.setRootProperty(meta.root); + } + if (meta.totalProperty) { + me.setTotalProperty(meta.totalProperty); + } + if (meta.successProperty) { + me.setSuccessProperty(meta.successProperty); + } + if (meta.messageProperty) { + me.setMessageProperty(meta.messageProperty); + } + clientIdProperty = meta.clientIdProperty; + if (fields) { + newModel = Ext.define(null, { + extend: 'Ext.data.Model', + fields: fields, + clientIdProperty: clientIdProperty + }); + me.setModel(newModel); + proxy = me.getProxy(); + if (proxy) { + proxy.setModel(newModel); + } + } else if (clientIdProperty) { + model = me.getModel(); + if (model) { + model.self.prototype.clientIdProperty = clientIdProperty; + } + } + }, + /** + * @private + * This builds optimized functions for retrieving record data and meta data from an object. + * Subclasses may need to implement their own getRoot function. + * @param {Boolean} [force=false] True to automatically remove existing extractor functions first + */ + buildExtractors: function(force) { + var me = this, + totalProp, successProp, messageProp; + if (force || !me.hasExtractors) { + totalProp = me.getTotalProperty(); + successProp = me.getSuccessProperty(); + messageProp = me.getMessageProperty(); + //build the extractors for all the meta data + if (totalProp) { + me.getTotal = me.getAccessor(totalProp); + } + if (successProp) { + me.getSuccess = me.getAccessor(successProp); + } + if (messageProp) { + me.getMessage = me.getAccessor(messageProp); + } + me.hasExtractors = true; + return true; + } + }, + getAccessor: function(prop) { + var me = this, + cache = me.extractorCache, + ret, key; + if (typeof prop === 'string') { + key = me.getAccessorKey(prop); + if (key) { + ret = cache.get(key); + } + if (!ret) { + ret = me.createAccessor(prop); + if (key) { + cache.add(key, ret); + } + } + } else { + ret = me.createAccessor(prop); + } + return ret; + }, + getAccessorKey: function(prop) { + var className = this.$className; + return className ? className + prop : ''; + }, + createAccessor: Ext.emptyFn, + createFieldAccessor: Ext.emptyFn, + destroy: function() { + var me = this; + me.model = me.getTotal = me.getSuccess = me.getMessage = me.rawData = null; + // Proxy could have created a sequence + me.onMetaChange = null; + // Transform function can be bound + me.transform = null; + me.callParent(); + }, + privates: { + copyFrom: function(reader) { + var me = this; + reader.buildExtractors(); + me.getTotal = reader.getTotal; + me.getSuccess = reader.getSuccess; + me.getMessage = reader.getMessage; + ++me.duringInit; + me.setConfig(reader.getConfig()); + --me.duringInit; + me.hasExtractors = true; + }, + getGroupRoot: Ext.privateFn, + getSummaryRoot: Ext.privateFn + } +}, function(Cls) { + var proto = Cls.prototype; + Ext.apply(proto, { + // Private. Empty ResultSet to return when response is falsy (null|undefined|empty string) + nullResultSet: new Ext.data.ResultSet({ + total: 0, + count: 0, + records: [], + success: true, + message: '' + }) + }); + proto.extractorCache = new Ext.util.LruCache(); +}); + +/** + * Base Writer class used by most subclasses of {@link Ext.data.proxy.Server}. This class + * is responsible for taking a set of {@link Ext.data.operation.Operation} objects and a + * {@link Ext.data.Request} object and modifying that request based on the Operations. + * + * For example a Ext.data.writer.Json would format the Operations and their + * {@link Ext.data.Model} instances based on the config options passed to the JsonWriter's + * constructor. + * + * Writers are not needed for any kind of local storage - whether via a + * {@link Ext.data.proxy.WebStorage Web Storage proxy} (see + * {@link Ext.data.proxy.LocalStorage localStorage} and + * {@link Ext.data.proxy.SessionStorage sessionStorage}) + * or just in memory via a {@link Ext.data.proxy.Memory MemoryProxy}. + * + * # Dates + * + * Before sending dates to the server, they can be formatted using an {@link Ext.Date} + * format. These formats can be specified both on the field and the writer itself. In terms + * of precedence, from highest to lowest: + * + * - {@link #dateFormat Writer.dateFormat} The writer `dateFormat` will always have the + * highest precedence. + * - {@link Ext.data.field.Date#dateWriteFormat} The `dateWriteFormat` given to the field + * instance. This is handled by {@link Ext.data.field.Date#method-serialize}. + * - {@link Ext.data.field.Date#dateFormat Field.dateFormat} This is handled by the field's + * `serialize` method. + * - {@link Ext.data.field.Date#dateReadFormat Field.dateReadFormat} Also handled by the + * field's `serialize` method. + */ +Ext.define('Ext.data.writer.Writer', { + mixins: [ + 'Ext.mixin.Factoryable' + ], + alias: 'writer.base', + factoryConfig: { + defaultType: null + }, + alternateClassName: [ + 'Ext.data.DataWriter', + 'Ext.data.Writer' + ], + config: { + /** + * @cfg {String} clientIdProperty + * When specified this property causes the `{@link Ext.data.Model#idProperty}` of + * newly created records to be sent to the server as this name instead of the + * value of the `idProperty`. + * + * For example, by default, the following code: + * + * Ext.define('Person', { + * idProperty: 'id', // this is the default value (for clarity) + * + * fields: [ 'name' ] + * }); + * + * var person = new Person({ + * // no id provided, so one is generated + * name: 'Clark Kent' + * }); + * + * Will send this to the server: + * + * { + * id: 'Person-1', + * name: 'Clark Kent' + * } + * + * This can be an issue if the server expects an integer for the "id" property. + * You can use `{@link Ext.data.Model#identifier}` to produce identifiers that + * the server would recognize or use this config to send the client's id in a + * different property. + * + * Ext.define('Person', { + * idProperty: 'id', // this is the default value (for clarity) + * + * proxy: { + * writer: { + * clientIdProperty: 'clientId' + * } + * }, + * + * fields: [ 'name' ] + * }); + * + * Given the above, the server is sent this data now: + * + * { + * clientId: 'Person-1', + * name: 'Clark Kent' + * } + * + * While this config provides the behavior of `{@link Ext.data.Model#clientIdProperty}` + * from previous releases, this property is not as useful as a suitable + * `{@link Ext.data.Model#identifier}` due to id's appearing in foreign-key fields + * and in `{@link Ext.data.Model#manyToMany}` associations. + * + * See `{@link Ext.data.Model#identifier}` for more on id generation. + */ + clientIdProperty: null, + /** + * @cfg {Object} allDataOptions + * This object contains the options passed to `{@link Ext.data.Model#getData}` when + * writing `{@link Ext.data.Model#phantom}` records or when `writeAllFields` is set + * to `true`. + * + * *NOTE:* The `serialize` option cannot be used here. + */ + allDataOptions: { + persist: true + }, + /** + * @cfg {Object} partialDataOptions + * This object contains the options passed to `{@link Ext.data.Model#getData}` when + * writing non `{@link Ext.data.Model#phantom}` records or when `writeAllFields` is + * set to `false`. + * + * *NOTE:* The `serialize` option cannot be used here. + */ + partialDataOptions: { + changes: true, + critical: true + }, + /** + * @cfg {Boolean} writeAllFields `true` to write all fields from the record to the + * server. If set to `false` it will only send the fields that were modified. Note + * that any fields that have `{@link Ext.data.field.Field#persist}` set to `false` + * will still be ignored while those with `{@link Ext.data.field.Field#critical}` + * set to `true` will be included. + * + * The exact set of fields written is determined by `allDataOptions` (when `true`) + * or `partialDataOptions` (when `false`). This option is ignored and treated as + * `true` when writing `{@link Ext.data.Model#phantom}` records. + * + * It is seldom a good idea to use this config. Rather use `allDataOptions` or + * `partialDataOptions` to control what fields are sent for records based on their + * `{@link Ext.data.Model#phantom}` state. + * + * In the previous release, this was default `true`. + */ + writeAllFields: false, + /** + * @cfg {String} dateFormat + * This is used for each field of type date in the model to format the value before + * it is sent to the server. + */ + dateFormat: null, + /** + * @cfg {String} nameProperty + * This property is used to read the key for each value that will be sent to the + * server. + * + * For example: + * + * Ext.define('Person', { + * extend: 'Ext.data.Model', + * fields: [{ + * name: 'first', + * mapping: 'firstName' + * }, { + * name: 'last', + * mapping: 'lastName' + * }, { + * name: 'age' + * }] + * }); + * + * new Ext.data.writer.Writer({ + * nameProperty: 'mapping' + * }); + * + * // This will be sent to the server + * { + * firstName: 'first name value', + * lastName: 'last name value', + * age: 1 + * } + * + * If the value is not present, the field name will always be used. + */ + nameProperty: 'name', + /** + * @cfg {Boolean} [writeRecordId] + * By default, each record's id is always included in the output for non-phantom + * records since in most cases the id will be required on the server to process + * the record action. This is helpful since the id will normally not be modified, + * and so would not be sent to the server unless {@link #writeAllFields} was + * explicitly enabled. + * + * However, there are cases where it is not desirable for the record id to be passed + * in the data directly. For example, when using a RESTful API the record id would + * typically be appended to the url instead. + */ + writeRecordId: true, + /** + * @cfg {Function|Object} [transform] + * If a transform function is set, it will be invoked just before {@link #writeRecords} + * executes. It is passed the unserialized data object and the {@link Ext.data.Request request} + * object. The transform function returns a data object, which can be a modified version of the original + * data object, or a completely new data object. The transform can be a function, or an object + * with a 'fn' key and an optional 'scope' key. Example usage: + * + * Ext.create('Ext.data.Store', { + * model: 'User', + * proxy: { + * type: 'ajax', + * url : 'users.json', + * writer: { + * type: 'json', + * transform: { + * fn: function(data, request) { + * // do some manipulation of the unserialized data object + * return data; + * }, + * scope: this + * } + * } + * }, + * }); + * + */ + transform: null + }, + /** + * @property {Boolean} isWriter + * `true` in this class to identify an object as an instantiated Writer, or subclass thereof. + */ + isWriter: true, + /** + * Creates new Writer. + * @param {Object} [config] Config object. + */ + constructor: function(config) { + this.initConfig(config); + }, + applyTransform: function(transform) { + if (transform) { + if (Ext.isFunction(transform)) { + transform = { + fn: transform + }; + } + return transform.fn.bind(transform.scope || this); + } + return transform; + }, + /** + * Prepares a Proxy's Ext.data.Request object. + * @param {Ext.data.Request} request The request object. + * @return {Ext.data.Request} The modified request object. + */ + write: function(request) { + var operation = request.getOperation(), + records = operation.getRecords() || [], + len = records.length, + data = [], + i; + for (i = 0; i < len; i++) { + data.push(this.getRecordData(records[i], operation)); + } + return this.writeRecords(request, data); + }, + /** + * @method + * + * Write the record data to the request in the appropriate format. + * @protected + * @param {Ext.data.Request} request The request. + * @param {Array} data An array of objects containing data. + * @return {Ext.data.Request} The request. + */ + writeRecords: Ext.emptyFn, + /** + * Formats the data for each record before sending it to the server. This method should + * be overridden to format the data in a way that differs from the default. + * + * @param {Ext.data.Model} record The record that we are writing to the server. + * @param {Ext.data.operation.Operation} [operation] An operation object. + * @return {Object} An object literal of name/value keys to be written to the server. + * By default this method returns the data property on the record. + */ + getRecordData: function(record, operation) { + var me = this, + nameProperty = me.getNameProperty(), + mapping = nameProperty !== 'name', + idField = record.self.idField, + key = idField[nameProperty] || idField.name, + // setup for idField first + value = record.id, + writeAll = me.getWriteAllFields(), + ret, dateFormat, phantom, options, clientIdProperty, fieldsMap, data, field; + if (idField.serialize) { + value = idField.serialize(value); + } + if (!writeAll && operation && operation.isDestroyOperation) { + ret = {}; + ret[key] = value; + } else { + dateFormat = me.getDateFormat(); + phantom = record.phantom; + options = (phantom || writeAll) ? me.getAllDataOptions() : me.getPartialDataOptions(); + clientIdProperty = phantom && me.getClientIdProperty(); + fieldsMap = record.getFieldsMap(); + options.serialize = false; + // we must take over this here + data = record.getData(options); + // If we are mapping we need to pour data into a new object, otherwise we do + // our work in-place: + ret = mapping ? {} : data; + if (clientIdProperty) { + // if (phantom and have clientIdProperty) + ret[clientIdProperty] = value; + // must read data and write ret + delete data[key]; + } + // in case ret === data (must not send "id") + else if (!me.getWriteRecordId()) { + delete data[key]; + } + for (key in data) { + value = data[key]; + if (!(field = fieldsMap[key])) { + // No defined field, so clearly no nameProperty to look up for this field + // but if we are mapping we need to copy over the value. Also there is no + // serializer to call in this case. + if (mapping) { + ret[key] = value; + } + } else { + // Allow this Writer to take over formatting date values if it has a + // dateFormat specified. Only check isDate on fields declared as dates + // for efficiency. + if (field.isDateField && dateFormat && Ext.isDate(value)) { + value = Ext.Date.format(value, dateFormat); + } else if (field.serialize) { + value = field.serialize(value, record); + } + if (mapping) { + key = field[nameProperty] || key; + } + ret[key] = value; + } + } + } + return ret; + } +}); + +/** + * Proxies are used by {@link Ext.data.Store Stores} to handle the loading and saving of {@link Ext.data.Model Model} + * data. Usually developers will not need to create or interact with proxies directly. + * + * # Types of Proxy + * + * There are two main types of Proxy - {@link Ext.data.proxy.Client Client} and {@link Ext.data.proxy.Server Server}. + * The Client proxies save their data locally and include the following subclasses: + * + * - {@link Ext.data.proxy.LocalStorage LocalStorageProxy} - saves its data to localStorage if the browser supports it + * - {@link Ext.data.proxy.SessionStorage SessionStorageProxy} - saves its data to sessionStorage if the browsers supports it + * - {@link Ext.data.proxy.Memory MemoryProxy} - holds data in memory only, any data is lost when the page is refreshed + * + * The Server proxies save their data by sending requests to some remote server. These proxies include: + * + * - {@link Ext.data.proxy.Ajax Ajax} - sends requests to a server on the same domain + * - {@link Ext.data.proxy.JsonP JsonP} - uses JSON-P to send requests to a server on a different domain + * - {@link Ext.data.proxy.Rest Rest} - uses RESTful HTTP methods (GET/PUT/POST/DELETE) to communicate with server + * - {@link Ext.data.proxy.Direct Direct} - uses {@link Ext.direct.Manager} to send requests + * + * Proxies operate on the principle that all operations performed are either Create, Read, Update or Delete. These four + * operations are mapped to the methods {@link #method!create}, {@link #method!read}, + * {@link #method!update} and {@link #method!erase} respectively. Each Proxy subclass + * implements these functions. + * + * The CRUD methods each expect an {@link Ext.data.operation.Operation Operation} object as the sole argument. The Operation + * encapsulates information about the action the Store wishes to perform, the {@link Ext.data.Model model} instances + * that are to be modified, etc. See the {@link Ext.data.operation.Operation Operation} documentation for more details. Each CRUD + * method also accepts a callback function to be called asynchronously on completion. + * + * Proxies also support batching of Operations via a {@link Ext.data.Batch batch} object, invoked by the {@link #batch} + * method. + */ +Ext.define('Ext.data.proxy.Proxy', { + mixins: [ + 'Ext.mixin.Factoryable', + 'Ext.mixin.Observable' + ], + $configPrefixed: false, + alias: 'proxy.proxy', + // also configures Factoryable + alternateClassName: [ + 'Ext.data.DataProxy', + 'Ext.data.Proxy' + ], + requires: [ + 'Ext.data.schema.Schema', + 'Ext.data.reader.Reader', + 'Ext.data.writer.Writer' + ], + uses: [ + 'Ext.data.Batch', + 'Ext.data.operation.*', + 'Ext.data.Model' + ], + config: { + /** + * @cfg {String} batchOrder + * Comma-separated ordering 'create', 'update' and 'destroy' actions when batching. Override this to set a different + * order for the batched CRUD actions to be executed in. Defaults to 'create,update,destroy'. + */ + batchOrder: 'create,update,destroy', + /** + * @cfg {Boolean} batchActions + * True to batch actions of a particular type when synchronizing the store. Defaults to true. + */ + batchActions: true, + /** + * @cfg {String/Ext.data.Model} model + * The name of the Model to tie to this Proxy. Can be either the string name of the Model, or a reference to the + * Model constructor. Required. + */ + model: undefined, + // @cmd-auto-dependency {aliasPrefix : "reader.", defaultPropertyName : "defaultReaderType"} + /** + * @cfg {Object/String/Ext.data.reader.Reader} reader + * The Ext.data.reader.Reader to use to decode the server's response or data read + * from client. This can either be a Reader instance, a config object or just a + * valid Reader type name (e.g. 'json', 'xml'). + */ + reader: { + type: 'json' + }, + // @cmd-auto-dependency {aliasPrefix : "writer.", defaultPropertyName : "defaultWriterType"} + /** + * @cfg {Object/String/Ext.data.writer.Writer} writer + * The Ext.data.writer.Writer to use to encode any request sent to the server or + * saved to client. This can either be a Writer instance, a config object or just + * a valid Writer type name (e.g. 'json', 'xml'). + */ + writer: { + type: 'json' + } + }, + /** + * @property {Boolean} isProxy + * `true` in this class to identify an object as an instantiated Proxy, or subclass thereof. + */ + isProxy: true, + /** + * @property {Boolean} [isSynchronous=false] + * Identifies the proxy as (a)synchronous. + */ + isSynchronous: false, + /** + * @event metachange + * Fires when this proxy's reader provides new metadata. Metadata usually consists + * of new field definitions, but can include any configuration data required by an + * application, and can be processed as needed in the event handler. + * This event is currently only fired for JsonReaders. Note that this event is also + * propagated by {@link Ext.data.Store}, which is typically where it would be handled. + * @param {Ext.data.proxy.Proxy} this + * @param {Object} meta The JSON metadata + */ + /** + * Creates the Proxy + * @param {Object} [config] Config object. + */ + constructor: function(config) { + // Will call initConfig + this.mixins.observable.constructor.call(this, config); + // We need to abort all pending operations when destroying + this.pendingOperations = {}; + }, + applyModel: function(model) { + return Ext.data.schema.Schema.lookupEntity(model); + }, + updateModel: function(model) { + if (model) { + var reader = this.getReader(); + if (reader && !reader.getModel()) { + reader.setModel(model); + } + } + }, + applyReader: function(reader) { + // Synchronous proxies need to force keepRawData to allow Grid features + // like Summary and Grouping access rawData after the Reader processed records. + // It doesn't do much harm since synchronous proxies are Client side ones, + // which will keep their datasets in memory or local storage anyway. + if (this.isSynchronous) { + reader = reader || {}; + reader.keepRawData = true; + } + return Ext.Factory.reader(reader); + }, + updateReader: function(reader) { + if (reader) { + var me = this, + model = me.getModel(); + if (!model) { + model = reader.getModel(); + if (model) { + me.setModel(model); + } + } else { + reader.setModel(model); + } + } + }, + applyWriter: function(writer) { + var reader = this.getReader(); + writer = Ext.Factory.writer(writer); + // XML Writers may have a record config to define the node name of each record tag. + // If not set, but the Reader has a record config, use the Reader's record config. + if (writer.getRecord && !writer.getRecord() && reader && reader.getRecord) { + reader = reader.getRecord(); + if (reader) { + writer.setRecord(reader); + } + } + return writer; + }, + abort: Ext.emptyFn, + /** + * @private + * Called each time the reader's onMetaChange is called so that the proxy can fire the metachange event + */ + onMetaChange: function(meta) { + this.fireEvent('metachange', this, meta); + }, + /** + * Performs the given create operation. + * @param {Ext.data.operation.Operation} operation The Operation to perform + * @method + */ + create: Ext.emptyFn, + /** + * Performs the given read operation. + * @param {Ext.data.operation.Operation} operation The Operation to perform + * @method + */ + read: Ext.emptyFn, + /** + * Performs the given update operation. + * @param {Ext.data.operation.Operation} operation The Operation to perform + * @method + */ + update: Ext.emptyFn, + /** + * Performs the given destroy operation. + * @param {Ext.data.operation.Operation} operation The Operation to perform + * @method + */ + erase: Ext.emptyFn, + /** + * Performs a batch of {@link Ext.data.operation.Operation Operations}, in the order specified by {@link #batchOrder}. Used + * internally by {@link Ext.data.Store}'s {@link Ext.data.Store#sync sync} method. Example usage: + * + * myProxy.batch({ + * create : [myModel1, myModel2], + * update : [myModel3], + * destroy: [myModel4, myModel5] + * }); + * + * Where the myModel* above are {@link Ext.data.Model Model} instances - in this case 1 and 2 are new instances and + * have not been saved before, 3 has been saved previously but needs to be updated, and 4 and 5 have already been + * saved but should now be destroyed. + * + * Note that the previous version of this method took 2 arguments (operations and listeners). While this is still + * supported for now, the current signature is now a single `options` argument that can contain both operations and + * listeners, in addition to other options. The multi-argument signature will likely be deprecated in a future release. + * + * @param {Object} options Object containing one or more properties supported by the batch method: + * + * @param {Object} options.operations Object containing the Model instances to act upon, keyed by action name + * + * @param {Object} [options.listeners] Event listeners object passed straight through to the Batch - + * see {@link Ext.data.Batch} for details + * + * @param {Ext.data.Batch/Object} [options.batch] A {@link Ext.data.Batch} object (or batch config to apply + * to the created batch). If unspecified a default batch will be auto-created. + * + * @param {Function} [options.callback] The function to be called upon completion of processing the batch. + * The callback is called regardless of success or failure and is passed the following parameters: + * @param {Ext.data.Batch} options.callback.batch The {@link Ext.data.Batch batch} that was processed, + * containing all operations in their current state after processing + * @param {Object} options.callback.options The options argument that was originally passed into batch + * + * @param {Function} [options.success] The function to be called upon successful completion of the batch. The + * success function is called only if no exceptions were reported in any operations. If one or more exceptions + * occurred then the `failure` function will be called instead. The success function is called + * with the following parameters: + * @param {Ext.data.Batch} options.success.batch The {@link Ext.data.Batch batch} that was processed, + * containing all operations in their current state after processing + * @param {Object} options.success.options The options argument that was originally passed into batch + * + * @param {Function} [options.failure] The function to be called upon unsuccessful completion of the batch. The + * failure function is called when one or more operations returns an exception during processing (even if some + * operations were also successful). In this case you can check the batch's {@link Ext.data.Batch#exceptions + * exceptions} array to see exactly which operations had exceptions. The failure function is called with the + * following parameters: + * @param {Ext.data.Batch} options.failure.batch The {@link Ext.data.Batch batch} that was processed, + * containing all operations in their current state after processing + * @param {Object} options.failure.options The options argument that was originally passed into batch + * + * @param {Object} [options.scope] The scope in which to execute any callbacks (i.e. the `this` object inside + * the callback, success and/or failure functions). Defaults to the proxy. + * + * @param {Object} [listeners] (deprecated) If `options` is the `operations`, this + * parameter is the listeners. Instead of passing these two arguments, the proper form + * is to pass them as: + * + * batch({ + * operations: ... + * listeners: ... + * }); + * + * @return {Ext.data.Batch} The newly created Batch + */ + batch: function(options, listeners) { + var me = this, + useBatch = me.getBatchActions(), + batch, records, actions, aLen, action, a, r, rLen, record; + if (options.operations === undefined) { + // the old-style (operations, listeners) signature was called + // so convert to the single options argument syntax + options = { + operations: options, + listeners: listeners + }; + } + if (options.batch) { + if (Ext.isDefined(options.batch.runOperation)) { + batch = Ext.applyIf(options.batch, { + proxy: me, + listeners: {} + }); + } + } else { + options.batch = { + proxy: me, + listeners: options.listeners || {} + }; + } + if (!batch) { + batch = new Ext.data.Batch(options.batch); + } + // Use single so that the listener gets removed upon completion. + batch.on('complete', Ext.bind(me.onBatchComplete, me, [ + options + ], 0), null, { + single: true, + priority: 1000 + }); + actions = me.getBatchOrder().split(','); + aLen = actions.length; + for (a = 0; a < aLen; a++) { + action = actions[a]; + records = options.operations[action]; + if (records) { + if (useBatch) { + batch.add(me.createOperation(action, { + records: records, + // Relay any additional params through to the Operation (and Request). + params: options.params + })); + } else { + rLen = records.length; + for (r = 0; r < rLen; r++) { + record = records[r]; + batch.add(me.createOperation(action, { + records: [ + record + ], + // Relay any additional params through to the Operation (and Request). + params: options.params + })); + } + } + } + } + batch.start(); + return batch; + }, + /** + * @private + * The internal callback that the proxy uses to call any specified user callbacks after completion of a batch + */ + onBatchComplete: function(batchOptions, batch) { + var scope = batchOptions.scope || this; + if (batch.hasException()) { + if (Ext.isFunction(batchOptions.failure)) { + Ext.callback(batchOptions.failure, scope, [ + batch, + batchOptions + ]); + } + } else if (Ext.isFunction(batchOptions.success)) { + Ext.callback(batchOptions.success, scope, [ + batch, + batchOptions + ]); + } + if (Ext.isFunction(batchOptions.callback)) { + Ext.callback(batchOptions.callback, scope, [ + batch, + batchOptions + ]); + } + }, + createOperation: function(action, config) { + var operation = Ext.createByAlias('data.operation.' + action, config); + operation.setProxy(this); + this.pendingOperations[operation._internalId] = operation; + return operation; + }, + completeOperation: function(operation) { + delete this.pendingOperations[operation._internalId]; + }, + clone: function() { + return new this.self(this.getInitialConfig()); + }, + destroy: function() { + var ops = this.pendingOperations, + opId, op; + for (opId in ops) { + op = ops[opId]; + if (op && op.isRunning()) { + op.abort(); + } + } + this.pendingOperations = null; + this.callParent(); + } +}); + +/** + * Base class for any client-side storage. Used as a superclass for {@link Ext.data.proxy.Memory Memory} and + * {@link Ext.data.proxy.WebStorage Web Storage} proxies. Do not use directly, use one of the subclasses instead. + * @private + */ +Ext.define('Ext.data.proxy.Client', { + extend: 'Ext.data.proxy.Proxy', + alternateClassName: 'Ext.data.ClientProxy', + /** + * @property {Boolean} isSynchronous + * `true` in this class to identify that requests made on this proxy are + * performed synchronously + */ + isSynchronous: true, + /** + * Abstract function that must be implemented by each ClientProxy subclass. This should purge all record data + * from the client side storage, as well as removing any supporting data (such as lists of record IDs) + */ + clear: function() { + Ext.raise("The Ext.data.proxy.Client subclass that you are using has not defined a 'clear' function. See src/data/ClientProxy.js for details."); + } +}); + +/** + * In-memory proxy. This proxy simply uses a local variable for data storage/retrieval, so its contents are lost on + * every page refresh. + * + * Usually this Proxy isn't used directly, serving instead as a helper to a {@link Ext.data.Store Store} where a reader + * is required to load data. For example, say we have a Store for a User model and have some inline data we want to + * load, but this data isn't in quite the right format: we can use a MemoryProxy with a JsonReader to read it into our + * Store: + * + * //this is the model we will be using in the store + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'id', type: 'int'}, + * {name: 'name', type: 'string'}, + * {name: 'phone', type: 'string', mapping: 'phoneNumber'} + * ] + * }); + * + * //this data does not line up to our model fields - the phone field is called phoneNumber + * var data = { + * users: [ + * { + * id: 1, + * name: 'Ed Spencer', + * phoneNumber: '555 1234' + * }, + * { + * id: 2, + * name: 'Abe Elias', + * phoneNumber: '666 1234' + * } + * ] + * }; + * + * //note how we set the 'root' in the reader to match the data structure above + * var store = Ext.create('Ext.data.Store', { + * autoLoad: true, + * model: 'User', + * data : data, + * proxy: { + * type: 'memory', + * reader: { + * type: 'json', + * rootProperty: 'users' + * } + * } + * }); + */ +Ext.define('Ext.data.proxy.Memory', { + extend: 'Ext.data.proxy.Client', + alias: 'proxy.memory', + alternateClassName: 'Ext.data.MemoryProxy', + isMemoryProxy: true, + config: { + /** + * @cfg {Boolean} [enablePaging=false] + * Configure as `true` to enable this MemoryProxy to honour a read operation's `start` and `limit` options. + * + * When `true`, read operations will be able to read *pages* of records from the data object. + */ + enablePaging: null, + /** + * @cfg {Object} data + * Optional data to pass to configured Reader. + */ + data: { + $value: null, + // Because of destructive association reading, we always need to clone incoming data + // to protect externally owned data objects from mutation + merge: function(newValue, currentValue, target, mixinClass) { + return newValue ? Ext.clone(newValue) : newValue; + } + }, + /** + * @cfg {Boolean} [clearOnRead=false] + * By default MemoryProxy data is persistent, and subsequent reads will read the + * same data. If this is not required, configure the proxy using `clearOnRead: true`. + */ + clearOnRead: null + }, + /** + * @private + * Fake processing function to commit the records, set the current operation + * to successful and call the callback if provided. This function is shared + * by the create, update and destroy methods to perform the bare minimum + * processing required for the proxy to register a result from the action. + */ + finishOperation: function(operation) { + var recs = operation.getRecords(), + len = recs.length, + i; + for (i = 0; i < len; i++) { + // Because Memory proxy is synchronous, the commit must call store#afterErase + recs[i].dropped = !!operation.isDestroyOperation; + recs[i].commit(); + } + operation.setSuccessful(true); + }, + /** + * Currently this is a hard-coded method that simply commits any records and sets the operation to successful, + * then calls the callback function, if provided. It is essentially mocking a server call in memory, but since + * there is no real back end in this case there's not much else to do. This method can be easily overridden to + * implement more complex logic if needed. + * @param {Ext.data.operation.Operation} operation The Operation to perform + * @method + */ + create: function(operation) { + this.finishOperation(operation); + }, + /** + * Currently this is a hard-coded method that simply commits any records and sets the operation to successful, + * then calls the callback function, if provided. It is essentially mocking a server call in memory, but since + * there is no real back end in this case there's not much else to do. This method can be easily overridden to + * implement more complex logic if needed. + * @param {Ext.data.operation.Operation} operation The Operation to perform + * @method + */ + update: function(operation) { + this.finishOperation(operation); + }, + /** + * Currently this is a hard-coded method that simply commits any records and sets the operation to successful, + * then calls the callback function, if provided. It is essentially mocking a server call in memory, but since + * there is no real back end in this case there's not much else to do. This method can be easily overridden to + * implement more complex logic if needed. + * @param {Ext.data.operation.Operation} operation The Operation to perform + * @method + */ + erase: function(operation) { + this.finishOperation(operation); + }, + /** + * Reads data from the configured {@link #data} object. Uses the Proxy's {@link #reader}, if present. + * @param {Ext.data.operation.Operation} operation The read Operation + */ + read: function(operation) { + var me = this, + reader = me.getReader(), + resultSet = reader.read(me.getData(), { + recordCreator: reader.defaultRecordCreatorFromServer + }), + records = resultSet.getRecords(), + sorters = operation.getSorters(), + grouper = operation.getGrouper(), + filters = operation.getFilters(), + start = operation.getStart(), + limit = operation.getLimit(), + meta; + // Apply filters, sorters, and start/limit options + if (operation.process(resultSet, null, null, false) !== false) { + // If we are configured to read the data one time only, clear our data + if (operation.success && me.getClearOnRead()) { + this.setData(null); + } + // Filter the resulting array of records + if (filters && filters.length) { + // Total will be updated by setting records + resultSet.setRecords(records = Ext.Array.filter(records, Ext.util.Filter.createFilterFn(filters))); + resultSet.setTotal(records.length); + } + // Remotely, grouper just mean top priority sorters + if (grouper) { + // Must concat so as not to mutate passed sorters array which could be the items property of the sorters collection + sorters = sorters ? sorters.concat(grouper) : sorters; + } + // Sort by the specified grouper and sorters + if (sorters && sorters.length) { + resultSet.setRecords(records = Ext.Array.sort(records, Ext.util.Sortable.createComparator(sorters))); + } + // Reader reads the whole passed data object. + // If successful and we were given a start and limit, slice the result. + if (me.getEnablePaging() && start !== undefined && limit !== undefined) { + // Attempt to read past end of memory dataset - convert to failure + if (start >= resultSet.getTotal()) { + resultSet.setConfig({ + success: false, + records: [], + total: 0 + }); + } else // Range is valid, slice it up. + { + resultSet.setRecords(Ext.Array.slice(records, start, start + limit)); + } + } + operation.setCompleted(); + // If a JsonReader detected metadata, process it now. + // This will fire the 'metachange' event which the Store processes to fire its own 'metachange' + if (meta = resultSet.getMetadata()) { + me.onMetaChange(meta); + } + } + }, + clear: Ext.emptyFn +}); + +/** + * ProxyStore is a superclass of {@link Ext.data.Store} and {@link Ext.data.BufferedStore}. It's never used directly, + * but offers a set of methods used by both of those subclasses. + * + * We've left it here in the docs for reference purposes, but unless you need to make a whole new type of Store, what + * you're probably looking for is {@link Ext.data.Store}. If you're still interested, here's a brief description of what + * ProxyStore is and is not. + * + * ProxyStore provides the basic configuration for anything that can be considered a Store. It expects to be + * given a {@link Ext.data.Model Model} that represents the type of data in the Store. It also expects to be given a + * {@link Ext.data.proxy.Proxy Proxy} that handles the loading of data into the Store. + * + * ProxyStore provides a few helpful methods such as {@link #method-load} and {@link #sync}, which load and save data + * respectively, passing the requests through the configured {@link #proxy}. + * + * Built-in Store subclasses add extra behavior to each of these functions. Note also that each ProxyStore subclass + * has its own way of storing data - in {@link Ext.data.Store} the data is saved as a flat {@link Ext.util.Collection Collection}, + * whereas in {@link Ext.data.BufferedStore BufferedStore} we use a {@link Ext.data.PageMap} to maintain a client side cache of pages of records. + * + * The store provides filtering and sorting support. This sorting/filtering can happen on the client side + * or can be completed on the server. This is controlled by the {@link Ext.data.Store#remoteSort remoteSort} and + * {@link Ext.data.Store#remoteFilter remoteFilter} config options. For more information see the {@link #method-sort} and + * {@link Ext.data.Store#filter filter} methods. + */ +Ext.define('Ext.data.ProxyStore', { + extend: 'Ext.data.AbstractStore', + requires: [ + 'Ext.data.Model', + 'Ext.data.proxy.Proxy', + 'Ext.data.proxy.Memory', + 'Ext.data.operation.*' + ], + config: { + // @cmd-auto-dependency {aliasPrefix: "model.", mvc: true, blame: "all"} + /** + * @cfg {String/Ext.data.Model} model + * Name of the {@link Ext.data.Model Model} associated with this store. See + * {@link Ext.data.Model#entityName}. + * + * May also be the actual Model subclass. + * + * This config is required for the store to be able to read data unless you have + * defined the {@link #fields} config which will create an anonymous + * `Ext.data.Model`. + */ + model: undefined, + // @cmd-auto-dependency {aliasPrefix: "data.field."} + /** + * @cfg fields + * @inheritdoc Ext.data.Model#cfg-fields + * + * @localdoc **Note:** In general, this configuration option should only be used + * for simple stores like a two-field store of + * {@link Ext.form.field.ComboBox ComboBox}. For anything more complicated, such + * as specifying a particular id property or associations, a + * {@link Ext.data.Model Model} should be defined and specified for the + * {@link #model} config. + * + * @since 2.3.0 + */ + fields: null, + // @cmd-auto-dependency {aliasPrefix : "proxy."} + /** + * @cfg {String/Ext.data.proxy.Proxy/Object} proxy + * The Proxy to use for this Store. This can be either a string, a config object + * or a Proxy instance - see {@link #setProxy} for details. + * @since 1.1.0 + */ + proxy: undefined, + /** + * @cfg {Boolean/Object} autoLoad + * If data is not specified, and if autoLoad is true or an Object, this store's + * load method is automatically called after creation. If the value of autoLoad + * is an Object, this Object will be passed to the store's load method. + * + * It's important to note that {@link Ext.data.TreeStore Tree Stores} will + * load regardless of autoLoad's value if expand is set to true on the + * {@link Ext.data.TreeStore#root root node}. + * + * @since 2.3.0 + */ + autoLoad: undefined, + /** + * @cfg {Boolean} autoSync + * True to automatically sync the Store with its Proxy after every edit to one of + * its Records. Defaults to false. + */ + autoSync: false, + /** + * @cfg {String} batchUpdateMode + * Sets the updating behavior based on batch synchronization. 'operation' (the + * default) will update the Store's internal representation of the data after + * each operation of the batch has completed, 'complete' will wait until the + * entire batch has been completed before updating the Store's data. 'complete' + * is a good choice for local storage proxies, 'operation' is better for remote + * proxies, where there is a comparatively high latency. + */ + batchUpdateMode: 'operation', + /** + * @cfg {Boolean} sortOnLoad + * If true, any sorters attached to this Store will be run after loading data, + * before the datachanged event is fired. Defaults to true, ignored if + * {@link Ext.data.Store#remoteSort remoteSort} is true + */ + sortOnLoad: true, + /** + * @cfg {Boolean} trackRemoved + * This config controls whether removed records are remembered by this store for + * later saving to the server. + */ + trackRemoved: true, + /** + * @cfg {Boolean} asynchronousLoad + * This defaults to `true` when this store's {@link #cfg-proxy} is asynchronous, + * such as an {@link Ext.data.proxy.Ajax Ajax proxy}. + * + * When the proxy is synchronous, such as a {@link Ext.data.proxy.Memory} memory + * proxy, this defaults to `false`. + * + * *NOTE:* This does not cause synchronous Ajax requests if configured `false` + * when an Ajax proxy is used. It causes immediate issuing of an Ajax request + * when {@link #method-load} is called rather than issuing the request at the end + * of the current event handler run. + * + * What this means is that when using an Ajax proxy, calls to + * {@link #method-load} do not fire the request to the remote resource + * immediately, but schedule a request to be made. This is so that multiple + * requests are not fired when mutating a store's remote filters and sorters (as + * happens during state restoration). The request is made only once after all + * relevant store state is fully set. + * + * @since 6.0.1 + */ + asynchronousLoad: undefined + }, + onClassExtended: function(cls, data, hooks) { + var model = data.model, + onBeforeClassCreated; + if (typeof model === 'string') { + onBeforeClassCreated = hooks.onBeforeCreated; + hooks.onBeforeCreated = function() { + var me = this, + args = arguments; + Ext.require(model, function() { + onBeforeClassCreated.apply(me, args); + }); + }; + } + }, + /** + * @private + * @property {Boolean} implicitModel + * The class name of the model that this store uses if no explicit {@link #model} is + * given + */ + implicitModel: 'Ext.data.Model', + /** + * @property {Object} lastOptions + * Property to hold the last options from a {@link #method-load} method call. This + * object is used for the {@link #method-reload} to reuse the same options. Please + * see {@link #method-reload} for a simple example on how to use the lastOptions + * property. + */ + /** + * @property {Number} autoSyncSuspended + * A counter to track suspensions. + * @private + */ + autoSyncSuspended: 0, + /** + * @property {Ext.data.Model[]} removed + * Temporary cache in which removed model instances are kept until successfully + * synchronised with a Proxy, at which point this is cleared. + * + * This cache is maintained unless you set `trackRemoved` to `false`. + * + * @protected + * @readonly + */ + removed: null, + /** + * @event beforeload + * Fires before a request is made for a new data object. If the beforeload handler returns false the load + * action will be canceled. + * + * **Note:** If you are using a buffered store, you should use + * {@link Ext.data.Store#beforeprefetch beforeprefetch}. + * @param {Ext.data.Store} store This Store + * @param {Ext.data.operation.Operation} operation The Ext.data.operation.Operation object that will be passed to the Proxy to + * load the Store + * @since 1.1.0 + */ + /** + * @event load + * Fires whenever the store reads data from a remote data source. + * + * **Note:** If you are using a buffered store, you should use + * {@link Ext.data.Store#prefetch prefetch}. + * @param {Ext.data.Store} this + * @param {Ext.data.Model[]} records An array of records + * @param {Boolean} successful True if the operation was successful. + * @param {Ext.data.operation.Read} operation The + * {@link Ext.data.operation.Read Operation} object that was used in the data + * load call + * @since 1.1.0 + */ + /** + * @event write + * Fires whenever a successful write has been made via the configured {@link #proxy Proxy} + * @param {Ext.data.Store} store This Store + * @param {Ext.data.operation.Operation} operation The {@link Ext.data.operation.Operation Operation} object that was used in + * the write + * @since 3.4.0 + */ + /** + * @event beforesync + * Fired before a call to {@link #sync} is executed. Return false from any listener to cancel the sync + * @param {Object} options Hash of all records to be synchronized, broken down into create, update and destroy + */ + /** + * @event metachange + * Fires when this store's underlying reader (available via the proxy) provides new metadata. + * Metadata usually consists of new field definitions, but can include any configuration data + * required by an application, and can be processed as needed in the event handler. + * This event is currently only fired for JsonReaders. + * @param {Ext.data.Store} this + * @param {Object} meta The JSON metadata + * @since 1.1.0 + */ + constructor: function(config) { + var me = this; + var configModel = me.model; + me.callParent(arguments); + if (me.getAsynchronousLoad() === false) { + me.flushLoad(); + } + if (!me.getModel() && me.useModelWarning !== false && me.getStoreId() !== 'ext-empty-store') { + // There are a number of ways things could have gone wrong, try to give as much information as possible + var logMsg = [ + Ext.getClassName(me) || 'Store', + ' created with no model.' + ]; + if (typeof configModel === 'string') { + logMsg.push(" The name '", configModel, "'", ' does not correspond to a valid model.'); + } + Ext.log.warn(logMsg.join('')); + } + }, + /** + * @private + */ + doDestroy: function() { + var me = this, + proxy = me.getProxy(); + me.clearLoadTask(); + Ext.destroy(me.getData()); + me.data = null; + me.setProxy(null); + if (proxy.autoCreated) { + proxy.destroy(); + } + me.setModel(null); + me.callParent(); + }, + applyAsynchronousLoad: function(asynchronousLoad) { + // Default in an asynchronousLoad setting. + // It defaults to false if the proxy is synchronous, and true if the proxy is asynchronous. + if (asynchronousLoad == null) { + asynchronousLoad = !this.loadsSynchronously(); + } + return asynchronousLoad; + }, + updateAutoLoad: function(autoLoad) { + // Ensure the data collection is set up + this.getData(); + if (autoLoad) { + // Defer the load until idle, when the store (and probably the view) is fully constructed + this.load(Ext.isObject(autoLoad) ? autoLoad : undefined); + } + }, + /** + * Returns the total number of {@link Ext.data.Model Model} instances that the {@link Ext.data.proxy.Proxy Proxy} + * indicates exist. This will usually differ from {@link #getCount} when using paging - getCount returns the + * number of records loaded into the Store at the moment, getTotalCount returns the number of records that + * could be loaded into the Store if the Store contained all data + * @return {Number} The total number of Model instances available via the Proxy. 0 returned if + * no value has been set via the reader. + */ + getTotalCount: function() { + return this.totalCount || 0; + }, + applyFields: function(fields) { + if (fields) { + this.createImplicitModel(fields); + } + }, + applyModel: function(model) { + if (model) { + model = Ext.data.schema.Schema.lookupEntity(model); + } else if (!this.destroying) { + // If no model, ensure that the fields config is converted to a model. + this.getFields(); + model = this.getModel() || this.createImplicitModel(); + } + return model; + }, + applyProxy: function(proxy) { + var model = this.getModel(); + if (proxy !== null) { + if (proxy) { + if (proxy.isProxy) { + proxy.setModel(model); + } else { + if (Ext.isString(proxy)) { + proxy = { + type: proxy, + model: model + }; + } else if (!proxy.model) { + proxy = Ext.apply({ + model: model + }, proxy); + } + proxy = Ext.createByAlias('proxy.' + proxy.type, proxy); + proxy.autoCreated = true; + } + } else if (model) { + proxy = model.getProxy(); + this.useModelProxy = true; + } + if (!proxy) { + proxy = Ext.createByAlias('proxy.memory'); + proxy.autoCreated = true; + } + } + return proxy; + }, + applyState: function(state) { + var me = this; + me.callParent([ + state + ]); + // This is called during construction. Sorters and filters might have changed + // which require a reload. + // If autoLoad is true, it might have loaded synchronously from a memory proxy, so needs to reload. + // If it is already loaded, we definitely need to reload to apply the state. + if (me.getAutoLoad() || me.isLoaded()) { + me.load(); + } + }, + updateProxy: function(proxy, oldProxy) { + this.proxyListeners = Ext.destroy(this.proxyListeners); + }, + updateTrackRemoved: function(track) { + this.cleanRemoved(); + this.removed = track ? [] : null; + }, + /** + * @private + */ + onMetaChange: function(proxy, meta) { + this.fireEvent('metachange', this, meta); + }, + //saves any phantom records + create: function(data, options) { + var me = this, + Model = me.getModel(), + instance = new Model(data), + operation; + options = Ext.apply({}, options); + if (!options.records) { + options.records = [ + instance + ]; + } + options.internalScope = me; + options.internalCallback = me.onProxyWrite; + operation = me.createOperation('create', options); + return operation.execute(); + }, + read: function() { + return this.load.apply(this, arguments); + }, + update: function(options) { + var me = this, + operation; + options = Ext.apply({}, options); + if (!options.records) { + options.records = me.getUpdatedRecords(); + } + options.internalScope = me; + options.internalCallback = me.onProxyWrite; + operation = me.createOperation('update', options); + return operation.execute(); + }, + /** + * @private + * Callback for any write Operation over the Proxy. Updates the Store's MixedCollection to reflect + * the updates provided by the Proxy + */ + onProxyWrite: function(operation) { + var me = this, + success = operation.wasSuccessful(), + records = operation.getRecords(); + switch (operation.getAction()) { + case 'create': + me.onCreateRecords(records, operation, success); + break; + case 'update': + me.onUpdateRecords(records, operation, success); + break; + case 'destroy': + me.onDestroyRecords(records, operation, success); + break; + } + if (success) { + me.fireEvent('write', me, operation); + me.fireEvent('datachanged', me); + } + }, + // may be implemented by store subclasses + onCreateRecords: Ext.emptyFn, + // may be implemented by store subclasses + onUpdateRecords: Ext.emptyFn, + /** + * Removes any records when a write is returned from the server. + * @private + * @param {Ext.data.Model[]} records The array of removed records + * @param {Ext.data.operation.Operation} operation The operation that just completed + * @param {Boolean} success True if the operation was successful + */ + onDestroyRecords: function(records, operation, success) { + if (success) { + this.cleanRemoved(); + } + }, + // tells the attached proxy to destroy the given records + // @since 3.4.0 + erase: function(options) { + var me = this, + operation; + options = Ext.apply({}, options); + if (!options.records) { + options.records = me.getRemovedRecords(); + } + options.internalScope = me; + options.internalCallback = me.onProxyWrite; + operation = me.createOperation('destroy', options); + return operation.execute(); + }, + /** + * @private + * Attached as the 'operationcomplete' event listener to a proxy's Batch object. By default just calls through + * to onProxyWrite. + */ + onBatchOperationComplete: function(batch, operation) { + return this.onProxyWrite(operation); + }, + /** + * @private + * Attached as the 'complete' event listener to a proxy's Batch object. Iterates over the batch operations + * and updates the Store's internal data MixedCollection. + */ + onBatchComplete: function(batch, operation) { + var me = this, + operations = batch.operations, + length = operations.length, + i; + if (me.batchUpdateMode !== 'operation') { + me.suspendEvents(); + for (i = 0; i < length; i++) { + me.onProxyWrite(operations[i]); + } + me.resumeEvents(); + } + me.isSyncing = false; + batch.destroy(); + me.fireEvent('datachanged', me); + }, + /** + * @private + */ + onBatchException: function(batch, operation) {}, + // //decide what to do... could continue with the next operation + // batch.start(); + // + // //or retry the last operation + // batch.retry(); + /** + * @private + * Filter function for new records. + */ + filterNew: function(item) { + // only want phantom records that are valid + return item.phantom && item.isValid(); + }, + /** + * Returns all `{@link Ext.data.Model#property-phantom phantom}` records in this store. + * @return {Ext.data.Model[]} A possibly empty array of `phantom` records. + */ + getNewRecords: function() { + return []; + }, + /** + * Returns all valid, non-phantom Model instances that have been updated in the Store but not yet synchronized with the Proxy. + * @return {Ext.data.Model[]} The updated Model instances + */ + getUpdatedRecords: function() { + return []; + }, + /** + * Gets all {@link Ext.data.Model records} added or updated since the last commit. Note that the order of records + * returned is not deterministic and does not indicate the order in which records were modified. Note also that + * removed records are not included (use {@link #getRemovedRecords} for that). + * @return {Ext.data.Model[]} The added and updated Model instances + */ + getModifiedRecords: function() { + return [].concat(this.getNewRecords(), this.getUpdatedRecords()); + }, + /** + * @private + * Filter function for updated records. + */ + filterUpdated: function(item) { + // only want dirty records, not phantoms that are valid + return item.dirty && !item.phantom && item.isValid(); + }, + /** + * Returns any records that have been removed from the store but not yet destroyed on the proxy. + * @return {Ext.data.Model[]} The removed Model instances. Note that this is a *copy* of the store's + * array, so may be mutated. + */ + getRemovedRecords: function() { + var removed = this.getRawRemovedRecords(); + return removed ? Ext.Array.clone(removed) : []; + }, + /** + * Synchronizes the store with its {@link #proxy}. This asks the proxy to batch together any new, updated + * and deleted records in the store, updating the store's internal representation of the records + * as each operation completes. + * + * @param {Object} [options] Object containing one or more properties supported by the sync method (these get + * passed along to the underlying proxy's {@link Ext.data.Proxy#batch batch} method): + * + * @param {Ext.data.Batch/Object} [options.batch] A {@link Ext.data.Batch} object (or batch config to apply + * to the created batch). If unspecified a default batch will be auto-created as needed. + * + * @param {Function} [options.callback] The function to be called upon completion of the sync. + * The callback is called regardless of success or failure and is passed the following parameters: + * @param {Ext.data.Batch} options.callback.batch The {@link Ext.data.Batch batch} that was processed, + * containing all operations in their current state after processing + * @param {Object} options.callback.options The options argument that was originally passed into sync + * + * @param {Function} [options.success] The function to be called upon successful completion of the sync. The + * success function is called only if no exceptions were reported in any operations. If one or more exceptions + * occurred then the failure function will be called instead. The success function is called + * with the following parameters: + * @param {Ext.data.Batch} options.success.batch The {@link Ext.data.Batch batch} that was processed, + * containing all operations in their current state after processing + * @param {Object} options.success.options The options argument that was originally passed into sync + * + * @param {Function} [options.failure] The function to be called upon unsuccessful completion of the sync. The + * failure function is called when one or more operations returns an exception during processing (even if some + * operations were also successful). In this case you can check the batch's {@link Ext.data.Batch#exceptions + * exceptions} array to see exactly which operations had exceptions. The failure function is called with the + * following parameters: + * @param {Ext.data.Batch} options.failure.batch The {@link Ext.data.Batch} that was processed, containing all + * operations in their current state after processing + * @param {Object} options.failure.options The options argument that was originally passed into sync + * + * @param {Object} [options.params] Additional params to send during the sync Operation(s). + * + * @param {Object} [options.scope] The scope in which to execute any callbacks (i.e. the `this` object inside + * the callback, success and/or failure functions). Defaults to the store's proxy. + * + * @return {Ext.data.Store} this + */ + sync: function(options) { + var me = this, + operations = {}, + toCreate = me.getNewRecords(), + toUpdate = me.getUpdatedRecords(), + toDestroy = me.getRemovedRecords(), + needsSync = false; + if (me.isSyncing) { + Ext.log.warn('Sync called while a sync operation is in progress. Consider configuring autoSync as false.'); + } + me.needsSync = false; + if (toCreate.length > 0) { + operations.create = toCreate; + needsSync = true; + } + if (toUpdate.length > 0) { + operations.update = toUpdate; + needsSync = true; + } + if (toDestroy.length > 0) { + operations.destroy = toDestroy; + needsSync = true; + } + if (needsSync && me.fireEvent('beforesync', operations) !== false) { + me.isSyncing = true; + options = options || {}; + me.proxy.batch(Ext.apply(options, { + operations: operations, + listeners: me.getBatchListeners() + })); + } + return me; + }, + /** + * @private + * Returns an object which is passed in as the listeners argument to proxy.batch inside this.sync. + * This is broken out into a separate function to allow for customisation of the listeners + * @return {Object} The listeners object + */ + getBatchListeners: function() { + var me = this, + listeners = { + scope: me, + exception: me.onBatchException, + complete: me.onBatchComplete + }; + if (me.batchUpdateMode === 'operation') { + listeners.operationcomplete = me.onBatchOperationComplete; + } + return listeners; + }, + /** + * Saves all pending changes via the configured {@link #proxy}. Use {@link #sync} instead. + * @deprecated 4.0.0 Will be removed in the next major version + */ + save: function() { + return this.sync.apply(this, arguments); + }, + /** + * Marks this store as needing a load. When the current executing event handler exits, + * this store will send a request to load using its configured {@link #proxy}. + * + * Upon return of the data from whatever data source the proxy connected to, the retrieved + * {@link Ext.data.Model records} will be loaded into this store, and the optional callback will be called. + * Example usage: + * + * store.load({ + * scope: this, + * callback: function(records, operation, success) { + * // the operation object + * // contains all of the details of the load operation + * console.log(records); + * } + * }); + * + * If the callback scope does not need to be set, a function can simply be passed: + * + * store.load(function(records, operation, success) { + * console.log('loaded records'); + * }); + * + * @param {Object} [options] This is passed into the {@link Ext.data.operation.Operation Operation} + * object that is created and then sent to the proxy's {@link Ext.data.proxy.Proxy#read} function. + * In addition to the options listed below, this object may contain properties to configure the + * {@link Ext.data.operation.Operation Operation}. + * @param {Function} [options.callback] A function which is called when the response arrives. + * @param {Ext.data.Model[]} options.callback.records Array of records. + * @param {Ext.data.operation.Operation} options.callback.operation The Operation itself. + * @param {Boolean} options.callback.success `true` when operation completed successfully. + * @param {Boolean} [options.addRecords=false] Specify as `true` to *add* the incoming records rather than the + * default which is to have the incoming records *replace* the existing store contents. + * + * @return {Ext.data.Store} this + * @since 1.1.0 + */ + load: function(options) { + var me = this; + // Legacy option. Specifying a function was allowed. + if (typeof options === 'function') { + options = { + callback: options + }; + } else { + // We may mutate the options object in setLoadOptions. + options = options ? Ext.Object.chain(options) : {}; + } + me.pendingLoadOptions = options; + // If we are configured to load asynchronously (the default for async proxies) + // then schedule a flush, unless one is already scheduled. + if (me.getAsynchronousLoad()) { + if (!me.loadTimer) { + me.loadTimer = Ext.asap(me.flushLoad, me); + } + } else // If we are configured to load synchronously (the default for sync proxies) + // then flush the load now. + { + me.flushLoad(); + } + return me; + }, + /** + * Called when the event handler which called the {@link #method-load} method exits. + */ + flushLoad: function() { + var me = this, + options = me.pendingLoadOptions, + operation; + if (me.destroying || me.destroyed) { + return; + } + // If it gets called programatically before the timer fired, the listener will need cancelling. + me.clearLoadTask(); + if (!options) { + return; + } + me.setLoadOptions(options); + if (me.getRemoteSort() && options.sorters) { + me.fireEvent('beforesort', me, options.sorters); + } + operation = Ext.apply({ + internalScope: me, + internalCallback: me.onProxyLoad, + scope: me + }, options); + me.lastOptions = operation; + operation = me.createOperation('read', operation); + if (me.fireEvent('beforeload', me, operation) !== false) { + me.onBeforeLoad(operation); + me.loading = true; + // Internal event, fired after the flag is set, we need + // to fire this beforeload is too early + if (me.hasListeners.beginload) { + me.fireEvent('beginload', me, operation); + } + operation.execute(); + } + }, + /** + * Reloads the store using the last options passed to the {@link #method-load} method. You can use the reload method to reload the + * store using the parameters from the last load() call. For example: + * + * store.load({ + * params : { + * userid : 22216 + * } + * }); + * + * //... + * + * store.reload(); + * + * The initial {@link #method-load} execution will pass the `userid` parameter in the request. The {@link #reload} execution + * will also send the same `userid` parameter in its request as it will reuse the `params` object from the last {@link #method-load} call. + * + * You can override a param by passing in the config object with the `params` object: + * + * store.load({ + * params : { + * userid : 22216, + * foo : 'bar' + * } + * }); + * + * //... + * + * store.reload({ + * params : { + * userid : 1234 + * } + * }); + * + * The initial {@link #method-load} execution sends the `userid` and `foo` parameters but in the {@link #reload} it only sends + * the `userid` paramter because you are overriding the `params` config not just overriding the one param. To only change a single param + * but keep other params, you will have to get the last params from the {@link #lastOptions} property: + * + * var lastOptions = store.lastOptions, + * lastParams = Ext.clone(lastOptions.params); // make a copy of the last params so we don't affect future reload() calls + * + * lastParams.userid = 1234; + * + * store.reload({ + * params : lastParams + * }); + * + * This will now send the `userid` parameter as `1234` and the `foo` param as `'bar'`. + * + * @param {Object} [options] A config object which contains options which may override the options passed to the previous load call. See the + * {@link #method-load} method for valid configs. + */ + reload: function(options) { + return this.load(Ext.apply({}, options, this.lastOptions)); + }, + onEndUpdate: function() { + var me = this; + if (me.needsSync && me.autoSync && !me.autoSyncSuspended) { + me.sync(); + } + }, + /** + * @private + * A model instance should call this method on the Store it has been {@link Ext.data.Model#join joined} to.. + * @param {Ext.data.Model} record The model instance that was edited + * @since 3.4.0 + */ + afterReject: function(record) { + var me = this; + // Must pass the 5th param (modifiedFieldNames) as null, otherwise the + // event firing machinery appends the listeners "options" object to the arg list + // which may get used as the modified fields array by a handler. + // This array is used for selective grid cell updating by Grid View. + // Null will be treated as though all cells need updating. + if (me.contains(record)) { + me.onUpdate(record, Ext.data.Model.REJECT, null); + me.fireEvent('update', me, record, Ext.data.Model.REJECT, null); + me.fireEvent('datachanged', me); + } + }, + /** + * A model instance should call this method on the Store it has been + * {@link Ext.data.Model#join joined} to. + * @param {Ext.data.Model} record The model instance that was edited. + * @param {String[]} [modifiedFieldNames] (private) + * @since 3.4.0 + * @private + */ + afterCommit: function(record, modifiedFieldNames) { + var me = this; + if (!modifiedFieldNames) { + modifiedFieldNames = null; + } + if (me.contains(record)) { + me.onUpdate(record, Ext.data.Model.COMMIT, modifiedFieldNames); + me.fireEvent('update', me, record, Ext.data.Model.COMMIT, modifiedFieldNames); + me.fireEvent('datachanged', me); + } + }, + afterErase: function(record) { + this.onErase(record); + }, + onErase: Ext.emptyFn, + onUpdate: Ext.emptyFn, + /** + * Returns true if the store has a pending load task. + * @return {Boolean} `true` if the store has a pending load task. + * @private + */ + hasPendingLoad: function() { + return !!this.pendingLoadOptions || this.isLoading(); + }, + /** + * Returns true if the Store is currently performing a load operation + * @return {Boolean} `true` if the Store is currently loading + */ + isLoading: function() { + return !!this.loading; + }, + /** + * Returns `true` if the Store has been loaded. + * @return {Boolean} `true` if the Store has been loaded. + */ + isLoaded: function() { + return this.loadCount > 0; + }, + /** + * Suspends automatically syncing the Store with its Proxy. Only applicable if {@link #autoSync} is `true` + */ + suspendAutoSync: function() { + ++this.autoSyncSuspended; + }, + /** + * Resumes automatically syncing the Store with its Proxy. Only applicable if {@link #autoSync} is `true` + * @param {Boolean} syncNow Pass `true` to synchronize now. Only synchronizes with the Proxy if the suspension + * count has gone to zero (We are not under a higher level of suspension) + * + */ + resumeAutoSync: function(syncNow) { + var me = this; + if (!me.autoSyncSuspended) { + Ext.log.warn('Mismatched call to resumeAutoSync - auto synchronization is currently not suspended.'); + } + if (me.autoSyncSuspended && !--me.autoSyncSuspended) { + if (syncNow) { + me.sync(); + } + } + }, + /** + * Removes all records from the store. This method does a "fast remove", + * individual remove events are not called. The {@link #clear} event is + * fired upon completion. + * @method + * @since 1.1.0 + */ + removeAll: Ext.emptyFn, + // individual store subclasses should implement a "fast" remove + // and fire a clear event afterwards + // to be implemented by subclasses + clearData: Ext.emptyFn, + privates: { + /** + * @private + * Returns the array of records which have been removed since the last time this store was synced. + * + * This is used internally, when purging removed records after a successful sync. + * This is overridden by TreeStore because TreeStore accumulates deleted records on removal + * of child nodes from their parent, *not* on removal of records from its collection. The collection + * has records added on expand, and removed on collapse. + */ + getRawRemovedRecords: function() { + return this.removed; + }, + onExtraParamsChanged: function() {}, + clearLoadTask: function() { + this.pendingLoadOptions = this.loadTimer = Ext.unasap(this.loadTimer); + }, + cleanRemoved: function() { + // Must use class-specific getRawRemovedRecords. + // Regular Stores add to the "removed" property on remove. + // TreeStores are having records removed all the time; node collapse removes. + // TreeStores add to the "removedNodes" property onNodeRemove + var removed = this.getRawRemovedRecords(), + len, i; + if (removed) { + for (i = 0 , len = removed.length; i < len; ++i) { + removed[i].unjoin(this); + } + removed.length = 0; + } + }, + createOperation: function(type, options) { + var me = this, + proxy = me.getProxy(), + listeners; + if (!me.proxyListeners) { + listeners = { + scope: me, + destroyable: true, + beginprocessresponse: me.beginUpdate, + endprocessresponse: me.endUpdate + }; + if (!me.disableMetaChangeEvent) { + listeners.metachange = me.onMetaChange; + } + me.proxyListeners = proxy.on(listeners); + } + return proxy.createOperation(type, options); + }, + createImplicitModel: function(fields) { + var me = this, + modelCfg = { + extend: me.implicitModel, + statics: { + defaultProxy: 'memory' + } + }, + proxy, model; + if (fields) { + modelCfg.fields = fields; + } + model = Ext.define(null, modelCfg); + me.setModel(model); + proxy = me.getProxy(); + if (proxy) { + model.setProxy(proxy); + } else { + me.setProxy(model.getProxy()); + } + }, + loadsSynchronously: function() { + return this.getProxy().isSynchronous; + }, + onBeforeLoad: Ext.privateFn, + removeFromRemoved: function(record) { + // Must use class-specific getRawRemovedRecords. + // Regular Stores add to the "removed" property on remove. + // TreeStores are having records removed all the time; node collapse removes. + // TreeStores add to the "removedNodes" property onNodeRemove + var removed = this.getRawRemovedRecords(); + if (removed) { + Ext.Array.remove(removed, record); + record.unjoin(this); + } + }, + setLoadOptions: function(options) { + var me = this, + filters, sorters; + if (me.getRemoteFilter()) { + filters = me.getFilters(false); + if (filters && filters.getCount()) { + options.filters = filters.getRange(); + } + } + if (me.getRemoteSort()) { + sorters = me.getSorters(false); + if (sorters && sorters.getCount()) { + options.sorters = sorters.getRange(); + } + } + } + } +}); + +/** + * Encapsulates a grouped collection of records within a {@link Ext.util.Collection} + */ +Ext.define('Ext.util.Group', { + extend: 'Ext.util.Collection', + config: { + groupKey: null + }, + // Group collections must have a higher priority than normal collections. This ensures + // that their endupdate handlers for filters and sorters run prior to the endupdate + // handler of the store's main collection, and so when the user handles events such + // as sort/datachanged, the groups have already been sorted and filtered. + $endUpdatePriority: 2001, + manageSorters: false +}); + +/** + * Encapsulates a group of records. Can provide a + * {@link #getSummaryRecord} summary record. + * + * @since 6.5.0 + */ +Ext.define('Ext.data.Group', { + extend: 'Ext.util.Group', + store: null, + /** + * Returns the summary results for the group. + * @return {Ext.data.Model} + */ + getSummaryRecord: function() { + var me = this, + summaryRecord = me.summaryRecord, + store = me.store, + generation = store.getData().generation, + M, T; + if (!summaryRecord) { + M = store.getModel(); + T = M.getSummaryModel(); + me.summaryRecord = summaryRecord = new T(); + } + if (!summaryRecord.isRemote && summaryRecord.summaryGeneration !== generation) { + summaryRecord.calculateSummary(me.items); + summaryRecord.summaryGeneration = generation; + } + return summaryRecord; + } +}); + +/** + * A mixin that provides common store methods for Ext.data.Store & Ext.data.ChainedStore. + * @private + */ +Ext.define('Ext.data.LocalStore', { + extend: 'Ext.Mixin', + requires: [ + 'Ext.data.Group' + ], + mixinConfig: { + id: 'localstore' + }, + config: { + extraKeys: null + }, + applyExtraKeys: function(extraKeys) { + var indexName, + data = this.getData(); + // Add the extra keys to the data collection + data.setExtraKeys(extraKeys); + // Pluck the extra keys out so that we can keep them by index name + extraKeys = data.getExtraKeys(); + for (indexName in extraKeys) { + this[indexName] = extraKeys[indexName]; + } + }, + /** + * Adds Model instance to the Store. This method accepts either: + * + * - An array of Model instances or Model configuration objects. + * - Any number of Model instance or Model configuration object arguments. + * + * The new Model instances will be added at the end of the existing collection. + * + * Sample usage: + * + * myStore.add({some: 'data'}, {some: 'other data'}); + * + * Note that if this Store is sorted, the new Model instances will be inserted + * at the correct point in the Store to maintain the sort order. + * + * @param {Ext.data.Model[]/Ext.data.Model.../Object[]/Object...} record An array of + * records or configuration objects, or variable number of record or config arguments. + * @return {Ext.data.Model[]} The record instances that were added. + */ + add: function(record) { + return this.insert(this.getCount(), arguments.length === 1 ? record : arguments); + }, + constructDataCollection: function() { + var result = new Ext.util.Collection({ + rootProperty: 'data', + groupConfig: { + xclass: 'Ext.data.Group', + store: this + } + }); + // Add this store as an observer immediately so that we are informed of any + // synchronous autoLoad which may occur in this event. + result.addObserver(this); + return result; + }, + /** + * Converts a literal to a model, if it's not a model already + * @private + * @param {Ext.data.Model/Object} record The record to create + * @return {Ext.data.Model} + */ + createModel: function(record) { + var session = this.getSession(), + Model; + if (!record.isModel) { + Model = this.getModel(); + record = new Model(record, session); + } + return record; + }, + createFiltersCollection: function() { + return this.getData().getFilters(); + }, + createSortersCollection: function() { + var sorters = this.getData().getSorters(); + sorters.setSorterConfigure(this.addFieldTransform, this); + return sorters; + }, + /** + * Get the summary record for this store. See {@link Ext.data.Model#summary}. + * @return {Ext.data.Model} + * @since 6.5.0 + */ + getSummaryRecord: function() { + var me = this, + summaryRecord = me.summaryRecord, + data = me.getData(), + generation = data.generation, + T; + if (!summaryRecord) { + T = me.getModel().getSummaryModel(); + me.summaryRecord = summaryRecord = new T(); + } + if (!summaryRecord.isRemote && summaryRecord.summaryGeneration !== generation) { + summaryRecord.calculateSummary(data.items); + summaryRecord.summaryGeneration = generation; + } + return summaryRecord; + }, + onCollectionBeginUpdate: function() { + this.beginUpdate(); + }, + onCollectionEndUpdate: function() { + this.endUpdate(); + }, + // When the collection informs us that it has sorted, this LocalStore must react. + // AbstractStore#onSorterEndUpdate does the correct thing (fires a refresh) if remote sorting is false + onCollectionSort: function() { + this.onSorterEndUpdate(); + }, + // When the collection informs us that it has filtered, this LocalStore must react. + // AbstractStore#onFilterEndUpdate does the correct thing (fires a refresh) if remote sorting is false + onCollectionFilter: function() { + this.onFilterEndUpdate(); + }, + notifySorterChange: function() { + this.getData().onSorterChange(); + }, + forceLocalSort: function() { + var sorters = this.getSorters(); + // Sorter collection must inform all interested parties. + // We cannot just tell our data Collection to react - there + // may be GroupCollections hooked into the endUpdate call. + sorters.beginUpdate(); + sorters.endUpdate(); + }, + // Inherit docs + contains: function(record) { + return this.indexOf(record) > -1; + }, + /** + * Calls the specified function for each {@link Ext.data.Model record} in the store. + * + * When store is filtered, only loops over the filtered records. + * + * @param {Function} fn The function to call. The {@link Ext.data.Model Record} is passed as the first parameter. + * Returning `false` aborts and exits the iteration. + * @param {Object} [scope] The scope (`this` reference) in which the function is executed. + * Defaults to the current {@link Ext.data.Model record} in the iteration. + * @param {Object/Boolean} [includeOptions] An object which contains options which + * modify how the store is traversed. Or simply the `filtered` option. + * @param {Boolean} [includeOptions.filtered] Pass `true` to include filtered out + * nodes in the iteration. + */ + each: function(fn, scope, includeOptions) { + var data = this.getData(), + bypassFilters = includeOptions, + len, record, i; + if (typeof includeOptions === 'object') { + bypassFilters = includeOptions.filtered; + } + if (bypassFilters && data.filtered) { + data = data.getSource(); + } + data = data.items.slice(0); + // safe for re-entrant calls + len = data.length; + for (i = 0; i < len; ++i) { + record = data[i]; + if (fn.call(scope || record, record, i, len) === false) { + break; + } + } + }, + /** + * Collects unique values for a particular dataIndex from this store. + * + * Note that the `filtered` option can also be passed as a separate parameter for + * compatibility with previous versions. + * + * var store = Ext.create('Ext.data.Store', { + * fields: ['name'], + * data: [{ + * name: 'Larry' + * }, { + * name: 'Darryl' + * }, { + * name: 'Darryl' + * }] + * }); + * + * store.collect('name'); + * // returns ["Larry", "Darryl"] + * + * @param {String} property The property to collect + * @param {Object} [includeOptions] An object which contains options which modify how + * the store is traversed. For compatibility, this argument may be the `allowNull` + * value itself. If so, the next argument is the `filtered` value. + * @param {Boolean} [includeOptions.allowNull] Pass true to allow null, undefined or + * empty string values. + * @param {Boolean} [includeOptions.filtered] Pass `true` to collect from all records, + * even ones which are filtered. + * @param {Boolean} [filtered] This argument only applies when the legacy call form + * is used and `includeOptions` is actually the `allowNull` value. + * + * @return {Object[]} An array of the unique values + */ + collect: function(property, includeOptions, filtered) { + var me = this, + allowNull = includeOptions, + data = me.getData(); + if (typeof includeOptions === 'object') { + filtered = includeOptions.filtered; + allowNull = includeOptions.allowNull; + } + if (filtered && data.filtered) { + data = data.getSource(); + } + return data.collect(property, 'data', allowNull); + }, + /** + * Get the Record with the specified id. + * + * This method is not affected by filtering, lookup will be performed from all records + * inside the store, filtered or not. + * + * @param {Mixed} id The id of the Record to find. + * @return {Ext.data.Model} The Record with the passed id. Returns null if not found. + */ + getById: function(id) { + var data = this.getData(); + if (data.filtered) { + data = data.getSource(); + } + return data.get(id) || null; + }, + /** + * @private + * Get the Record with the specified internalId. + * + * This method is not affected by filtering, lookup will be performed from all records + * inside the store, filtered or not. + * + * @param {Mixed} internalId The id of the Record to find. + * @return {Ext.data.Model} The Record with the passed internalId. Returns null if not found. + */ + getByInternalId: function(internalId) { + var data = this.getData(), + keyCfg; + if (data.filtered) { + if (!data.$hasExtraKeys) { + keyCfg = this.makeInternalKeyCfg(); + data.setExtraKeys(keyCfg); + data.$hasExtraKeys = true; + } + data = data.getSource(); + } + if (!data.$hasExtraKeys) { + data.setExtraKeys(keyCfg || this.makeInternalKeyCfg()); + data.$hasExtraKeys = true; + } + return data.byInternalId.get(internalId) || null; + }, + /** + * Returns the complete unfiltered collection. + * @private + */ + getDataSource: function() { + var data = this.getData(); + return data.getSource() || data; + }, + /** + * Get the index of the record within the store. + * + * When store is filtered, records outside of filter will not be found. + * + * @param {Ext.data.Model} record The Ext.data.Model object to find. + * @return {Number} The index of the passed Record. Returns -1 if not found. + */ + indexOf: function(record) { + return this.getData().indexOf(record); + }, + /** + * Get the index within the store of the Record with the passed id. + * + * Like #indexOf, this method is affected by filtering. + * + * @param {String} id The id of the Record to find. + * @return {Number} The index of the Record. Returns -1 if not found. + */ + indexOfId: function(id) { + return this.indexOf(this.getById(id)); + }, + /** + * Inserts Model instances into the Store at the given index and fires the add event. + * See also {@link #method-add}. + * + * @param {Number} index The start index at which to insert the passed Records. + * @param {Ext.data.Model/Ext.data.Model[]/Object/Object[]} records An `Ext.data.Model` instance, the + * data needed to populate an instance or an array of either of these. + * + * @return {Ext.data.Model[]} records The added records + */ + insert: function(index, records) { + var me = this, + len, i; + if (records) { + if (!Ext.isIterable(records)) { + records = [ + records + ]; + } else { + records = Ext.Array.clone(records); + } + len = records.length; + } + if (!len) { + return []; + } + for (i = 0; i < len; ++i) { + records[i] = me.createModel(records[i]); + } + me.getData().insert(index, records); + return records; + }, + /** + * Query all the cached records in this Store using a filtering function. The specified function + * will be called with each record in this Store. If the function returns `true` the record is + * included in the results. + * + * This method is not affected by filtering, it will always search *all* records in the store + * regardless of filtering. + * + * @param {Function} fn The function to be called. It will be passed the following parameters: + * @param {Ext.data.Model} fn.record The record to test for filtering. Access field values + * using {@link Ext.data.Model#get}. + * @param {Object} fn.id The ID of the Record passed. + * @param {Object} [scope] The scope (this reference) in which the function is executed + * Defaults to this Store. + * @return {Ext.util.Collection} The matched records + */ + queryBy: function(fn, scope) { + var data = this.getData(); + return (data.getSource() || data).createFiltered(fn, scope); + }, + /** + * Query all the cached records in this Store by name/value pair. + * The parameters will be used to generated a filter function that is given + * to the queryBy method. + * + * This method complements queryBy by generating the query function automatically. + * + * This method is not affected by filtering, it will always search *all* records in the store + * regardless of filtering. + * + * @param {String} property The property to create the filter function for + * @param {String/RegExp} value The string/regex to compare the property value to + * @param {Boolean} [anyMatch=false] True to match any part of the string, not just the + * beginning. + * @param {Boolean} [caseSensitive=false] `true` to create a case-sensitive regex. + * @param {Boolean} [exactMatch=false] True to force exact match (^ and $ characters + * added to the regex). Ignored if `anyMatch` is `true`. + * @return {Ext.util.Collection} The matched records + */ + query: function(property, value, anyMatch, caseSensitive, exactMatch) { + var data = this.getData(); + return (data.getSource() || data).createFiltered(property, value, anyMatch, caseSensitive, exactMatch); + }, + /** + * Convenience function for getting the first model instance in the store. + * + * When store is filtered, will return first item within the filter. + * + * @param {Boolean} [grouped] True to perform the operation for each group + * in the store. The value returned will be an object literal with the key being the group + * name and the first record being the value. The grouped parameter is only honored if + * the store has a groupField. + * @return {Ext.data.Model/undefined} The first model instance in the store, or undefined + */ + first: function(grouped) { + return this.getData().first(grouped) || null; + }, + /** + * Convenience function for getting the last model instance in the store. + * + * When store is filtered, will return last item within the filter. + * + * @param {Boolean} [grouped] True to perform the operation for each group + * in the store. The value returned will be an object literal with the key being the group + * name and the last record being the value. The grouped parameter is only honored if + * the store has a groupField. + * @return {Ext.data.Model/undefined} The last model instance in the store, or undefined + */ + last: function(grouped) { + return this.getData().last(grouped) || null; + }, + /** + * Sums the value of `field` for each {@link Ext.data.Model record} in store + * and returns the result. + * + * When store is filtered, only sums items within the filter. + * + * @param {String} field A field in each record + * @param {Boolean} [grouped] True to perform the operation for each group + * in the store. The value returned will be an object literal with the key being the group + * name and the sum for that group being the value. The grouped parameter is only honored if + * the store has a groupField. + * @return {Number} The sum + */ + sum: function(field, grouped) { + var data = this.getData(); + return (grouped && this.isGrouped()) ? data.sumByGroup(field) : data.sum(field); + }, + /** + * Gets the count of items in the store. + * + * When store is filtered, only items within the filter are counted. + * + * @param {Boolean} [grouped] True to perform the operation for each group + * in the store. The value returned will be an object literal with the key being the group + * name and the count for each group being the value. The grouped parameter is only honored if + * the store has a groupField. + * @return {Number} the count + */ + count: function(grouped) { + var data = this.getData(); + return (grouped && this.isGrouped()) ? data.countByGroup() : data.count(); + }, + /** + * Gets the minimum value in the store. + * + * When store is filtered, only items within the filter are aggregated. + * + * @param {String} field The field in each record + * @param {Boolean} [grouped] True to perform the operation for each group + * in the store. The value returned will be an object literal with the key being the group + * name and the minimum in the group being the value. The grouped parameter is only honored if + * the store has a groupField. + * @return {Object} The minimum value, if no items exist, undefined. + */ + min: function(field, grouped) { + var data = this.getData(); + return (grouped && this.isGrouped()) ? data.minByGroup(field) : data.min(field); + }, + /** + * Gets the maximum value in the store. + * + * When store is filtered, only items within the filter are aggregated. + * + * @param {String} field The field in each record + * @param {Boolean} [grouped] True to perform the operation for each group + * in the store. The value returned will be an object literal with the key being the group + * name and the maximum in the group being the value. The grouped parameter is only honored if + * the store has a groupField. + * @return {Object} The maximum value, if no items exist, undefined. + */ + max: function(field, grouped) { + var data = this.getData(); + return (grouped && this.isGrouped()) ? data.maxByGroup(field) : data.max(field); + }, + /** + * Gets the average value in the store. + * + * When store is filtered, only items within the filter are aggregated. + * + * @param {String} field The field in each record + * @param {Boolean} [grouped] True to perform the operation for each group + * in the store. The value returned will be an object literal with the key being the group + * name and the group average being the value. The grouped parameter is only honored if + * the store has a groupField. + * @return {Object} The average value, if no items exist, 0. + */ + average: function(field, grouped) { + var data = this.getData(); + return (grouped && this.isGrouped()) ? data.averageByGroup(field) : data.average(field); + }, + /** + * Runs the aggregate function for all the records in the store. + * + * When store is filtered, only items within the filter are aggregated. + * + * @param {Function} fn The function to execute. The function is called with a single parameter, + * an array of records for that group. + * @param {Object} [scope] The scope to execute the function in. Defaults to the store. + * @param {Boolean} [grouped] True to perform the operation for each group + * in the store. The value returned will be an object literal with the key being the group + * name and the group average being the value. The grouped parameter is only honored if + * the store has a groupField. + * @param {String} field The field to get the value from + * @return {Object} An object literal with the group names and their appropriate values. + */ + aggregate: function(fn, scope, grouped, field) { + var me = this, + groups, len, out, group, i; + if (grouped && me.isGrouped()) { + groups = me.getGroups().items; + len = groups.length; + out = {}; + for (i = 0; i < len; ++i) { + group = groups[i]; + out[group.getGroupKey()] = me.getAggregate(fn, scope || me, group.items, field); + } + return out; + } else { + return me.getAggregate(fn, scope, me.getData().items, field); + } + }, + getAggregate: function(fn, scope, records, field) { + var values = [], + len = records.length, + i; + //TODO EXTJSIV-12307 - not the right way to call fn + for (i = 0; i < len; ++i) { + values[i] = records[i].get(field); + } + return fn.call(scope || this, records, values); + }, + addObserver: function(observer) { + var observers = this.observers; + if (!observers) { + this.observers = observers = new Ext.util.Collection(); + } + observers.add(observer); + }, + removeObserver: function(observer) { + var observers = this.observers; + if (observers) { + observers.remove(observer); + } + }, + callObservers: function(action, args) { + var observers = this.observers, + len, items, i, methodName, item; + if (observers) { + items = observers.items; + if (args) { + args.unshift(this); + } else { + args = [ + this + ]; + } + for (i = 0 , len = items.length; i < len; ++i) { + item = items[i]; + methodName = 'onSource' + action; + if (item[methodName]) { + item[methodName].apply(item, args); + } + } + } + }, + /** + * Query all the cached records in this Store using a filtering function. The specified function + * will be called with each record in this Store. If the function returns `true` the record is + * included in the results. + * + * This method is not affected by filtering, it will always search *all* records in the store + * regardless of filtering. + * + * @param {Function} fn The function to be called. It will be passed the following parameters: + * @param {Ext.data.Model} fn.record The record to test for filtering. + * @param {Object} [scope] The scope (this reference) in which the function is executed + * Defaults to this Store. + * @return {Ext.data.Model[]} The matched records. + * + * @private + */ + queryRecordsBy: function(fn, scope) { + var data = this.getData(), + matches = [], + len, i, record; + data = (data.getSource() || data).items; + scope = scope || this; + for (i = 0 , len = data.length; i < len; ++i) { + record = data[i]; + if (fn.call(scope, record) === true) { + matches.push(record); + } + } + return matches; + }, + /** + * Query all the cached records in this Store by field. + * + * This method is not affected by filtering, it will always search *all* records in the store + * regardless of filtering. + * + * @param {String} field The field from each record to use. + * @param {Object} value The value to match. + * @return {Ext.data.Model[]} The matched records. + * + * @private + */ + queryRecords: function(field, value) { + var data = this.getData(), + matches = [], + len, i, record; + data = (data.getSource() || data).items; + for (i = 0 , len = data.length; i < len; ++i) { + record = data[i]; + if (record.get(field) === value) { + matches.push(record); + } + } + return matches; + }, + privates: { + isLast: function(record) { + return record === this.last(); + }, + makeInternalKeyCfg: function() { + return { + byInternalId: { + property: 'internalId', + rootProperty: '' + } + }; + } + } +}); + +/** + * ServerProxy is a superclass of {@link Ext.data.proxy.JsonP JsonPProxy} and {@link Ext.data.proxy.Ajax AjaxProxy}, and + * would not usually be used directly. + * @protected + */ +Ext.define('Ext.data.proxy.Server', { + extend: 'Ext.data.proxy.Proxy', + alias: 'proxy.server', + alternateClassName: 'Ext.data.ServerProxy', + uses: [ + 'Ext.data.Request' + ], + isRemote: true, + config: { + /** + * @cfg {String} url + * The URL from which to request the data object. + */ + url: '', + /** + * @cfg {String} [pageParam="page"] + * The name of the 'page' parameter to send in a request. Defaults to 'page'. Set this to `''` if you don't + * want to send a page parameter. + */ + pageParam: 'page', + /** + * @cfg {String} [startParam="start"] + * The name of the 'start' parameter to send in a request. Defaults to 'start'. Set this to `''` if you don't + * want to send a start parameter. + */ + startParam: 'start', + /** + * @cfg {String} [limitParam="limit"] + * The name of the 'limit' parameter to send in a request. Defaults to 'limit'. Set this to `''` if you don't + * want to send a limit parameter. + */ + limitParam: 'limit', + /** + * @cfg {String} [groupParam="group"] + * The name of the 'group' parameter to send in a request. Defaults to 'group'. Set this to `''` if you don't + * want to send a group parameter. + */ + groupParam: 'group', + /** + * @cfg {String} [groupDirectionParam="groupDir"] + * The name of the direction parameter to send in a request. **This is only used when simpleGroupMode is set to + * true.** + * If this is set to the same value as the {@link #groupParam}, then the group property name *and* direction + * of each grouper is passed as a single, space separated parameter, looking like a database `group by` specification. + * + * So if there are multiple groupers, the single group parameter will look like this: + * + * ?group=name%20ASC&group=age%20DESC + */ + groupDirectionParam: 'groupDir', + /** + * @cfg {String} [sortParam="sort"] + * The name of the 'sort' parameter to send in a request. Defaults to 'sort'. Set this to `''` if you don't + * want to send a sort parameter. + */ + sortParam: 'sort', + /** + * @cfg {String} [filterParam="filter"] + * The name of the 'filter' parameter to send in a request. Defaults to 'filter'. Set this to `''` if you don't + * want to send a filter parameter. + */ + filterParam: 'filter', + /** + * @cfg {String} [directionParam="dir"] + * The name of the direction parameter to send in a request. **This is only used when simpleSortMode is set to + * true.** + * + * If this is set to the same value as the {@link #sortParam}, then the sort property name *and* direction + * of each sorter is passed as a single, space separated parameter, looking like a database `order by` specification. + * + * So if there are multiple sorters, the single sort parameter will look like this: + * + * ?sort=name%20ASC&sort=age%20DESC + */ + directionParam: 'dir', + /** + * @cfg {String} [idParam="id"] + * The name of the parameter which carries the id of the entity being operated upon. + */ + idParam: 'id', + /** + * @cfg {Boolean} [simpleSortMode=false] + * Enabling simpleSortMode in conjunction with remoteSort will send the sorted field names in the + * parameter named by {@link #sortParam}, and the directions for each sorted field in a parameter named by {@link #directionParam}. + * + * In the simplest case, with one Sorter, this will result in HTTP parameters like this: + * + * ?sort=name&dir=ASC + * + * If there are multiple sorters, the parameters will be encoded like this: + * + * ?sort=name&sort=age&dir=ASC&dir=DESC + */ + simpleSortMode: false, + /** + * @cfg {Boolean} [simpleGroupMode=false] + * Enabling simpleGroupMode in conjunction with remoteGroup will only send one group property and a direction when a + * remote group is requested. The {@link #groupDirectionParam} and {@link #groupParam} will be sent with the property name and either 'ASC' + * or 'DESC'. + */ + simpleGroupMode: false, + /** + * @cfg {Boolean} [noCache=true] + * Disable caching by adding a unique parameter name to the request. Set to false to allow caching. Defaults to true. + */ + noCache: true, + /** + * @cfg {String} [cacheString="_dc"] + * The name of the cache param added to the url when using noCache. Defaults to "_dc". + */ + cacheString: "_dc", + /** + * @cfg {Number} timeout + * The number of milliseconds to wait for a response. Defaults to 30000 milliseconds (30 seconds). + */ + timeout: 30000, + /** + * @cfg {Object} api + * Specific urls to call on CRUD action methods "create", "read", "update" and "destroy". Defaults to: + * + * api: { + * create : undefined, + * read : undefined, + * update : undefined, + * destroy : undefined + * } + * + * The url is built based upon the action being executed [create|read|update|destroy] using the commensurate + * {@link #api} property, or if undefined default to the configured + * {@link Ext.data.Store}.{@link Ext.data.proxy.Server#url url}. + * + * For example: + * + * api: { + * create : '/controller/new', + * read : '/controller/load', + * update : '/controller/update', + * destroy : '/controller/destroy_action' + * } + * + * If the specific URL for a given CRUD action is undefined, the CRUD action request will be directed to the + * configured {@link Ext.data.proxy.Server#url url}. + */ + api: { + create: undefined, + read: undefined, + update: undefined, + destroy: undefined + }, + /** + * @cfg {Object} extraParams + * Extra parameters that will be included on every request. Individual requests with params of the same name + * will override these params when they are in conflict. + */ + extraParams: {} + }, + primitiveRe: /string|number|boolean/, + /** + * @event exception + * Fires when the server returns an exception. This event may also be listened + * to in the event that a request has timed out or has been aborted. + * @param {Ext.data.proxy.Proxy} this + * @param {Ext.data.Response} response The response that was received + * @param {Ext.data.operation.Operation} operation The operation that triggered the request + */ + //in a ServerProxy all four CRUD operations are executed in the same manner, so we delegate to doRequest in each case + create: function() { + return this.doRequest.apply(this, arguments); + }, + read: function() { + return this.doRequest.apply(this, arguments); + }, + update: function() { + return this.doRequest.apply(this, arguments); + }, + erase: function() { + return this.doRequest.apply(this, arguments); + }, + /** + * Sets a value in the underlying {@link #extraParams}. + * @param {String} name The key for the new value + * @param {Object} value The value + */ + setExtraParam: function(name, value) { + var extraParams = this.getExtraParams(); + extraParams[name] = value; + this.fireEvent('extraparamschanged', extraParams); + }, + updateExtraParams: function(newExtraParams, oldExtraParams) { + this.fireEvent('extraparamschanged', newExtraParams); + }, + /** + * Creates an {@link Ext.data.Request Request} object from {@link Ext.data.operation.Operation Operation}. + * + * This gets called from doRequest methods in subclasses of Server proxy. + * + * @param {Ext.data.operation.Operation} operation The operation to execute + * @return {Ext.data.Request} The request object + */ + buildRequest: function(operation) { + var me = this, + initialParams = Ext.apply({}, operation.getParams()), + // Clone params right now so that they can be mutated at any point further down the call stack + params = Ext.applyIf(initialParams, me.getExtraParams() || {}), + request, operationId, idParam; + //copy any sorters, filters etc into the params so they can be sent over the wire + Ext.applyIf(params, me.getParams(operation)); + // Set up the entity id parameter according to the configured name. + // This defaults to "id". But TreeStore has a "nodeParam" configuration which + // specifies the id parameter name of the node being loaded. + operationId = operation.getId(); + idParam = me.getIdParam(); + if (operationId !== undefined && params[idParam] === undefined) { + params[idParam] = operationId; + } + request = new Ext.data.Request({ + params: params, + action: operation.getAction(), + records: operation.getRecords(), + url: operation.getUrl(), + operation: operation, + // this is needed by JsonSimlet in order to properly construct responses for + // requests from this proxy + proxy: me + }); + request.setUrl(me.buildUrl(request)); + /* + * Save the request on the Operation. Operations don't usually care about Request and Response data, but in the + * ServerProxy and any of its subclasses we add both request and response as they may be useful for further processing + */ + operation.setRequest(request); + return request; + }, + /** + * Processes response, which may involve updating or committing records, each of which + * will inform the owning stores and their interested views. Finally, we may perform + * an additional layout if the data shape has changed. + * + * @protected + */ + processResponse: function(success, operation, request, response) { + var me = this, + exception, reader, resultSet, meta; + // Async callback could have landed at any time, including during and after + // destruction. We don't want to unravel the whole response chain in such case. + if (me.destroying || me.destroyed) { + return; + } + // Processing a response may involve updating or committing many records + // each of which will inform the owning stores, which will ultimately + // inform interested views which will most likely have to do a layout + // assuming that the data shape has changed. + // Bracketing the processing with this event gives owning stores the ability + // to fire their own beginupdate/endupdate events which can be used by interested + // views to suspend layouts. + me.fireEvent('beginprocessresponse', me, response, operation); + if (success === true) { + reader = me.getReader(); + if (response.status === 204) { + resultSet = reader.getNullResultSet(); + } else { + resultSet = reader.read(me.extractResponseData(response), { + // If we're doing an update, we want to construct the models ourselves. + recordCreator: operation.getRecordCreator() || reader.defaultRecordCreatorFromServer + }); + } + operation.process(resultSet, request, response); + exception = !operation.wasSuccessful(); + } else { + me.setException(operation, response); + exception = true; + } + // It is possible that exception callback destroyed the store and owning proxy, + // in which case we can't do nothing except punt. + if (me.destroyed) { + return; + } + if (exception) { + me.fireEvent('exception', me, response, operation); + } else // If a JsonReader detected metadata, process it now. + // This will fire the 'metachange' event which the Store processes to fire its own 'metachange' + { + meta = resultSet.getMetadata(); + if (meta) { + me.onMetaChange(meta); + } + } + // Ditto + if (me.destroyed) { + return; + } + me.afterRequest(request, success); + // Tell owning store processing has finished. + // It will fire its endupdate event which will cause interested views to + // resume layouts. + me.fireEvent('endprocessresponse', me, response, operation); + }, + /** + * Sets up an exception on the operation + * @private + * @param {Ext.data.operation.Operation} operation The operation + * @param {Object} response The response + */ + setException: function(operation, response) { + operation.setException({ + status: response.status, + statusText: response.statusText, + response: response + }); + }, + /** + * @method + * Template method to allow subclasses to specify how to get the response for the reader. + * @template + * @private + * @param {Object} response The server response + * @return {Object} The response data to be used by the reader + */ + extractResponseData: Ext.identityFn, + /** + * Encode any values being sent to the server. Can be overridden in subclasses. + * @protected + * @param {Array} value An array of sorters/filters. + * @return {Object} The encoded value + */ + applyEncoding: function(value) { + return Ext.encode(value); + }, + /** + * Encodes the array of {@link Ext.util.Sorter} objects into a string to be sent in the request url. By default, + * this simply JSON-encodes the sorter data + * @param {Ext.util.Sorter[]} sorters The array of {@link Ext.util.Sorter Sorter} objects + * @param {Boolean} [preventArray=false] Prevents the items from being output as an array. + * @return {String} The encoded sorters + */ + encodeSorters: function(sorters, preventArray) { + var out = [], + length = sorters.length, + i; + for (i = 0; i < length; i++) { + out[i] = sorters[i].serialize(); + } + return this.applyEncoding(preventArray ? out[0] : out); + }, + /** + * Encodes the array of {@link Ext.util.Filter} objects into a string to be sent in the request url. By default, + * this simply JSON-encodes the filter data + * @param {Ext.util.Filter[]} filters The array of {@link Ext.util.Filter Filter} objects + * @return {String} The encoded filters + */ + encodeFilters: function(filters) { + var out = [], + length = filters.length, + needsEncoding, i, filter, encodedFilter; + for (i = 0; i < length; i++) { + filter = filters[i]; + // Filters with a custom filterFn cannot be serialized. But since #getFilterFn() + // always returns a filterFn, we need to check if it's been generated by default. + // If so, we know that the filter cannot have a custom filterFn defined, and it + // is therefore okay to serialize. + filter.getFilterFn(); + if (filter.generatedFilterFn) { + encodedFilter = filter.serialize(); + needsEncoding |= !this.primitiveRe.test(typeof encodedFilter); + out.push(encodedFilter); + } + } + // If any Filters return Objects encapsulating their full state, then the parameters + // needs JSON encoding. + return needsEncoding ? this.applyEncoding(out) : out; + }, + /** + * @private + * Copy any sorters, filters etc into the params so they can be sent over the wire + */ + getParams: function(operation) { + if (!operation.isReadOperation) { + return {}; + } + var me = this, + params = {}, + grouper = operation.getGrouper(), + sorters = operation.getSorters(), + filters = operation.getFilters(), + page = operation.getPage(), + start = operation.getStart(), + limit = operation.getLimit(), + simpleSortMode = me.getSimpleSortMode(), + simpleGroupMode = me.getSimpleGroupMode(), + pageParam = me.getPageParam(), + startParam = me.getStartParam(), + limitParam = me.getLimitParam(), + groupParam = me.getGroupParam(), + groupDirectionParam = me.getGroupDirectionParam(), + sortParam = me.getSortParam(), + filterParam = me.getFilterParam(), + directionParam = me.getDirectionParam(), + hasGroups, index; + if (pageParam && page) { + params[pageParam] = page; + } + if (startParam && (start || start === 0)) { + params[startParam] = start; + } + if (limitParam && limit) { + params[limitParam] = limit; + } + hasGroups = groupParam && grouper; + if (hasGroups) { + // Grouper is a subclass of sorter, so we can just use the sorter method + if (simpleGroupMode) { + params[groupParam] = grouper.getProperty(); + // Allow for direction to be encoded into the same parameter + if (groupDirectionParam === groupParam) { + params[groupParam] += ' ' + grouper.getDirection(); + } else { + params[groupDirectionParam] = grouper.getDirection(); + } + } else { + params[groupParam] = me.encodeSorters([ + grouper + ], true); + } + } + if (sortParam && sorters && sorters.length > 0) { + if (simpleSortMode) { + // Group will be included in sorters, so skip sorter 0 if groups + for (index = (sorters.length > 1 && hasGroups) ? 1 : 0; index < sorters.length; index++) { + // Allow for direction to be encoded into the same parameter + if (directionParam === sortParam) { + params[sortParam] = Ext.Array.push(params[sortParam] || [], sorters[index].getProperty() + ' ' + sorters[index].getDirection()); + } else { + params[sortParam] = Ext.Array.push(params[sortParam] || [], sorters[index].getProperty()); + params[directionParam] = Ext.Array.push(params[directionParam] || [], sorters[index].getDirection()); + } + } + } else { + params[sortParam] = me.encodeSorters(sorters); + } + } + if (filterParam && filters && filters.length > 0) { + params[filterParam] = me.encodeFilters(filters); + } + return params; + }, + /** + * Generates a url based on a given Ext.data.Request object. By default, ServerProxy's buildUrl will add the + * cache-buster param to the end of the url. Subclasses may need to perform additional modifications to the url. + * @param {Ext.data.Request} request The request object + * @return {String} The url + */ + buildUrl: function(request) { + var me = this, + url = me.getUrl(request); + if (!url) { + Ext.raise("You are using a ServerProxy but have not supplied it with a url."); + } + if (me.getNoCache()) { + url = Ext.urlAppend(url, Ext.String.format("{0}={1}", me.getCacheString(), Ext.Date.now())); + } + return url; + }, + /** + * Get the url for the request taking into account the order of priority, + * - The request + * - The api + * - The url + * @private + * @param {Ext.data.Request} request The request + * @return {String} The url + */ + getUrl: function(request) { + var url; + if (request) { + url = request.getUrl() || this.getApi()[request.getAction()]; + } + return url ? url : this.callParent(); + }, + /** + * In ServerProxy subclasses, the {@link #method-create}, {@link #method-read}, {@link #method-update} and + * {@link #method-erase} methods all pass through to doRequest. Each ServerProxy subclass must implement the + * doRequest method - see {@link Ext.data.proxy.JsonP} and {@link Ext.data.proxy.Ajax} for examples. This method + * carries the same signature as each of the methods that delegate to it. + * + * @param {Ext.data.operation.Operation} operation The Ext.data.operation.Operation object + * @param {Function} callback The callback function to call when the Operation has completed + * @param {Object} scope The scope in which to execute the callback + */ + doRequest: function(operation, callback, scope) { + Ext.raise("The doRequest function has not been implemented on your Ext.data.proxy.Server subclass. See src/data/ServerProxy.js for details"); + }, + /** + * Optional callback function which can be used to clean up after a request has been completed. + * @param {Ext.data.Request} request The Request object + * @param {Boolean} success True if the request was successful + * @protected + * @template + * @method + */ + afterRequest: Ext.emptyFn, + destroy: function() { + var me = this; + me.destroying = true; + // Don't force Reader and Writer creation if they weren't yet instantiated + me.reader = me.writer = Ext.destroy(me.reader, me.writer); + me.callParent(); + me.destroying = false; + me.destroyed = true; + } +}); + +/** + * AjaxProxy is one of the most widely-used ways of getting data into your application. It uses AJAX requests to load + * data from the server, usually to be placed into a {@link Ext.data.Store Store}. Let's take a look at a typical setup. + * Here we're going to set up a Store that has an AjaxProxy. To prepare, we'll also set up a {@link Ext.data.Model + * Model}: + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: ['id', 'name', 'email'] + * }); + * + * //The Store contains the AjaxProxy as an inline configuration + * var store = Ext.create('Ext.data.Store', { + * model: 'User', + * proxy: { + * type: 'ajax', + * url : 'users.json' + * } + * }); + * + * store.load(); + * + * Our example is going to load user data into a Store, so we start off by defining a {@link Ext.data.Model Model} with + * the fields that we expect the server to return. Next we set up the Store itself, along with a + * {@link Ext.data.Store#proxy proxy} configuration. This configuration was automatically turned into an + * Ext.data.proxy.Ajax instance, with the url we specified being passed into AjaxProxy's constructor. + * It's as if we'd done this: + * + * new Ext.data.proxy.Ajax({ + * url: 'users.json', + * model: 'User', + * reader: 'json' + * }); + * + * A couple of extra configurations appeared here - {@link #model} and {@link #reader}. These are set by default when we + * create the proxy via the Store - the Store already knows about the Model, and Proxy's default {@link + * Ext.data.reader.Reader Reader} is {@link Ext.data.reader.Json JsonReader}. + * + * Now when we call store.load(), the AjaxProxy springs into action, making a request to the url we configured + * ('users.json' in this case). As we're performing a read, it sends a GET request to that url (see + * {@link #actionMethods} to customize this - by default any kind of read will be sent as a GET request and any kind of write + * will be sent as a POST request). + * + * # Limitations + * + * AjaxProxy cannot be used to retrieve data from other domains. If your application is running on http://domainA.com it + * cannot load data from http://domainB.com because browsers have a built-in security policy that prohibits domains + * talking to each other via AJAX. + * + * If you need to read data from another domain and can't set up a proxy server (some software that runs on your own + * domain's web server and transparently forwards requests to http://domainB.com, making it look like they actually came + * from http://domainA.com), you can use {@link Ext.data.proxy.JsonP} and a technique known as JSON-P (JSON with + * Padding), which can help you get around the problem so long as the server on http://domainB.com is set up to support + * JSON-P responses. See {@link Ext.data.proxy.JsonP JsonPProxy}'s introduction docs for more details. + * + * # Readers and Writers + * + * AjaxProxy can be configured to use any type of {@link Ext.data.reader.Reader Reader} to decode the server's response. + * If no Reader is supplied, AjaxProxy will default to using a {@link Ext.data.reader.Json JsonReader}. Reader + * configuration can be passed in as a simple object, which the Proxy automatically turns into a {@link + * Ext.data.reader.Reader Reader} instance: + * + * var proxy = new Ext.data.proxy.Ajax({ + * model: 'User', + * reader: { + * type: 'xml', + * rootProperty: 'users' + * } + * }); + * + * proxy.getReader(); //returns an XmlReader instance based on the config we supplied + * + * # Url generation + * + * AjaxProxy automatically inserts any sorting, filtering, paging and grouping options into the url it generates for + * each request. These are controlled with the following configuration options: + * + * - {@link #pageParam} - controls how the page number is sent to the server (see also {@link #startParam} and {@link #limitParam}) + * - {@link #sortParam} - controls how sort information is sent to the server + * - {@link #groupParam} - controls how grouping information is sent to the server + * - {@link #filterParam} - controls how filter information is sent to the server + * + * Each request sent by AjaxProxy is described by an {@link Ext.data.operation.Operation Operation}. To see how we can customize + * the generated urls, let's say we're loading the Proxy with the following Operation: + * + * var proxy = new Ext.data.proxy.Ajax({ + * url: '/users' + * }); + * + * var operation = proxy.createOperation('read', { + * page : 2 + * }); + * + * Now we'll issue the request for this Operation by calling {@link #read}: + * + * proxy.read(operation); //GET /users?page=2 + * + * Easy enough - the Proxy just copied the page property from the Operation. We can customize how this page data is sent + * to the server: + * + * var proxy = new Ext.data.proxy.Ajax({ + * url: '/users', + * pageParam: 'pageNumber' + * }); + * + * proxy.read(operation); //GET /users?pageNumber=2 + * + * Alternatively, our Operation could have been configured to send start and limit parameters instead of page: + * + * var proxy = new Ext.data.proxy.Ajax({ + * url: '/users' + * }); + * + * var operation = proxy.createOperation('read', { + * start : 50, + * limit : 25 + * }); + * + * proxy.read(operation); //GET /users?start=50&limit;=25 + * + * Again we can customize this url: + * + * var proxy = new Ext.data.proxy.Ajax({ + * url: '/users', + * startParam: 'startIndex', + * limitParam: 'limitIndex' + * }); + * + * proxy.read(operation); //GET /users?startIndex=50&limitIndex;=25 + * + * AjaxProxy will also send sort and filter information to the server. Let's take a look at how this looks with a more + * expressive Operation object: + * + * var operation = proxy.createOperation('read', { + * sorters: [ + * new Ext.util.Sorter({ + * property : 'name', + * direction: 'ASC' + * }), + * new Ext.util.Sorter({ + * property : 'age', + * direction: 'DESC' + * }) + * ], + * filters: [ + * new Ext.util.Filter({ + * property: 'eyeColor', + * value : 'brown' + * }) + * ] + * }); + * + * This is the type of object that is generated internally when loading a {@link Ext.data.Store Store} with sorters and + * filters defined. By default the AjaxProxy will JSON encode the sorters and filters, resulting in something like this + * (note that the url is escaped before sending the request, but is left unescaped here for clarity): + * + * var proxy = new Ext.data.proxy.Ajax({ + * url: '/users' + * }); + * + * proxy.read(operation); //GET /users?sort=[{"property":"name","direction":"ASC"},{"property":"age","direction":"DESC"}]&filter;=[{"property":"eyeColor","value":"brown"}] + * + * We can again customize how this is created by supplying a few configuration options. Let's say our server is set up + * to receive sorting information is a format like "sortBy=name#ASC,age#DESC". We can configure AjaxProxy to provide + * that format like this: + * + * var proxy = new Ext.data.proxy.Ajax({ + * url: '/users', + * sortParam: 'sortBy', + * filterParam: 'filterBy', + * + * //our custom implementation of sorter encoding - turns our sorters into "name#ASC,age#DESC" + * encodeSorters: function(sorters) { + * var length = sorters.length, + * sortStrs = [], + * sorter, i; + * + * for (i = 0; i < length; i++) { + * sorter = sorters[i]; + * + * sortStrs[i] = sorter.property + '#' + sorter.direction + * } + * + * return sortStrs.join(","); + * } + * }); + * + * proxy.read(operation); //GET /users?sortBy=name#ASC,age#DESC&filterBy;=[{"property":"eyeColor","value":"brown"}] + * + * We can also provide a custom {@link #encodeFilters} function to encode our filters. + * + * # Debugging your Ajax Proxy + * + * If the data is not being loaded into the store as expected, it could be due to a mismatch between the the way that the {@link #reader} + * is configured, and the shape of the incoming data. + * + * To debug from the point that your data arrives back from the network, set a breakpoint inside the callback function + * created in the `createRequestCallback` method of the Ajax Proxy class, and follow the data to where the {@link #reader} attempts + * to consume it. + * + * @constructor + * Note that if this HttpProxy is being used by a {@link Ext.data.Store Store}, then the Store's call to + * {@link Ext.data.Store#method-load load} will override any specified callback and params options. In this case, use the + * {@link Ext.data.Store Store}'s events to modify parameters, or react to loading events. + * + * @param {Object} config (optional) Config object. + * If an options parameter is passed, the singleton {@link Ext.Ajax} object will be used to make the request. + */ +Ext.define('Ext.data.proxy.Ajax', { + requires: [ + 'Ext.Ajax' + ], + extend: 'Ext.data.proxy.Server', + alias: 'proxy.ajax', + alternateClassName: [ + 'Ext.data.HttpProxy', + 'Ext.data.AjaxProxy' + ], + isAjaxProxy: true, + // Keep a default copy of the action methods here. Ideally could just null + // out actionMethods and just check if it exists & has a property, otherwise + // fallback to the default. But at the moment it's defined as a public property, + // so we need to be able to maintain the ability to modify/access it. + defaultActionMethods: { + create: 'POST', + read: 'GET', + update: 'POST', + destroy: 'POST' + }, + config: { + /** + * @cfg {Boolean} binary + * True to request binary data from the server. This feature requires + * the use of a binary reader such as {@link Ext.data.amf.Reader AMF Reader} + */ + binary: false, + /** + * @cfg {Object} [headers] + * Any headers to add to the Ajax request. + * + * example: + * + * proxy: { + * headers: {'Content-Type': "text/plain" } + * ... + * } + */ + headers: undefined, + /** + * @cfg {Boolean} paramsAsJson + * Set to `true` to have any request parameters sent as {@link Ext.data.Connection#method-request jsonData} + * where they can be parsed from the raw request. By default, parameters are sent via the + * {@link Ext.data.Connection#method-request params} property. **Note**: This setting does not apply when the + * request is sent as a 'GET' request. See {@link #cfg!actionMethods} for controlling the HTTP verb + * that is used when sending requests. + */ + paramsAsJson: false, + /** + * @cfg {Boolean} withCredentials + * This configuration is sometimes necessary when using cross-origin resource sharing. + * @accessor + */ + withCredentials: false, + /** + * @cfg {Boolean} useDefaultXhrHeader + * Set this to false to not send the default Xhr header (X-Requested-With) with every request. + * This should be set to false when making CORS (cross-domain) requests. + * @accessor + */ + useDefaultXhrHeader: true, + /** + * @cfg {String} username + * Most oData feeds require basic HTTP authentication. This configuration allows + * you to specify the username. + * @accessor + */ + username: null, + /** + * @cfg {String} password + * Most oData feeds require basic HTTP authentication. This configuration allows + * you to specify the password. + * @accessor + */ + password: null, + /** + * @cfg {Object} actionMethods + * Mapping of action name to HTTP request method. In the basic AjaxProxy these are set to 'GET' for 'read' actions + * and 'POST' for 'create', 'update' and 'destroy' actions. The {@link Ext.data.proxy.Rest} maps these to the + * correct RESTful methods. + */ + actionMethods: { + create: 'POST', + read: 'GET', + update: 'POST', + destroy: 'POST' + } + }, + doRequest: function(operation) { + var me = this, + writer = me.getWriter(), + request = me.buildRequest(operation), + method = me.getMethod(request), + jsonData, params; + if (writer && operation.allowWrite()) { + request = writer.write(request); + } + request.setConfig({ + binary: me.getBinary(), + headers: me.getHeaders(), + timeout: me.getTimeout(), + scope: me, + callback: me.createRequestCallback(request, operation), + method: method, + useDefaultXhrHeader: me.getUseDefaultXhrHeader(), + disableCaching: false + }); + // explicitly set it to false, ServerProxy handles caching + if (method.toUpperCase() !== 'GET' && me.getParamsAsJson()) { + params = request.getParams(); + if (params) { + jsonData = request.getJsonData(); + if (jsonData) { + jsonData = Ext.Object.merge({}, jsonData, params); + } else { + jsonData = params; + } + request.setJsonData(jsonData); + request.setParams(undefined); + } + } + if (me.getWithCredentials()) { + request.setWithCredentials(true); + request.setUsername(me.getUsername()); + request.setPassword(me.getPassword()); + } + return me.sendRequest(request); + }, + /** + * Fires a request + * @param {Ext.data.Request} request The request + * @return {Ext.data.Request} The request + * @private + */ + sendRequest: function(request) { + request.setRawRequest(Ext.Ajax.request(request.getCurrentConfig())); + this.lastRequest = request; + return request; + }, + /** + * Aborts a running request. + * @param {Ext.data.Request} [request] The request to abort. If not passed, the most recent active + * request will be aborted. + */ + abort: function(request) { + request = request || this.lastRequest; + if (request) { + Ext.Ajax.abort(request.getRawRequest()); + } + }, + /** + * Returns the HTTP method name for a given request. By default this returns based on a lookup on + * {@link #cfg!actionMethods}. + * @param {Ext.data.Request} request The request object + * @return {String} The HTTP method to use (should be one of 'GET', 'POST', 'PUT' or 'DELETE') + */ + getMethod: function(request) { + var actions = this.getActionMethods(), + action = request.getAction(), + method; + if (actions) { + method = actions[action]; + } + return method || this.defaultActionMethods[action]; + }, + /** + * @private + * TODO: This is currently identical to the JsonPProxy version except for the return function's signature. There is a lot + * of code duplication inside the returned function so we need to find a way to DRY this up. + * @param {Ext.data.Request} request The Request object + * @param {Ext.data.operation.Operation} operation The Operation being executed + * @return {Function} The callback function + */ + createRequestCallback: function(request, operation) { + return function(options, success, response) { + var me = this; + if (request === me.lastRequest) { + me.lastRequest = null; + } + if (!me.destroying && !me.destroyed) { + me.processResponse(success, operation, request, response); + } + }; + }, + destroy: function() { + this.lastRequest = null; + this.callParent(); + } +}); + +/** + * The JSON Reader is used by a Proxy to read a server response that is sent back in JSON format. This usually + * happens as a result of loading a Store - for example we might create something like this: + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: ['id', 'name', 'email'] + * }); + * + * var store = Ext.create('Ext.data.Store', { + * model: 'User', + * proxy: { + * type: 'ajax', + * url : 'users.json', + * reader: { + * type: 'json' + * } + * } + * }); + * + * The example above creates a 'User' model. Models are explained in the {@link Ext.data.Model Model} docs if you're + * not already familiar with them. + * + * We created the simplest type of JSON Reader possible by simply telling our {@link Ext.data.Store Store}'s + * {@link Ext.data.proxy.Proxy Proxy} that we want a JSON Reader. The Store automatically passes the configured model to the + * Store, so it is as if we passed this instead: + * + * reader: { + * type : 'json', + * model: 'User' + * } + * + * The reader we set up is ready to read data from our server - at the moment it will accept a response like this: + * + * [ + * { + * "id": 1, + * "name": "Ed Spencer", + * "email": "ed@sencha.com" + * }, + * { + * "id": 2, + * "name": "Abe Elias", + * "email": "abe@sencha.com" + * } + * ] + * + * ## Reading other JSON formats + * + * If you already have your JSON format defined and it doesn't look quite like what we have above, you can usually + * pass JsonReader a couple of configuration options to make it parse your format. For example, we can use the + * {@link #cfg-rootProperty} configuration to parse data that comes back like this: + * + * { + * "users": [ + * { + * "id": 1, + * "name": "Ed Spencer", + * "email": "ed@sencha.com" + * }, + * { + * "id": 2, + * "name": "Abe Elias", + * "email": "abe@sencha.com" + * } + * ] + * } + * + * To parse this we just pass in a {@link #rootProperty} configuration that matches the 'users' above: + * + * reader: { + * type: 'json', + * rootProperty: 'users' + * } + * + * Sometimes the JSON structure is even more complicated. Document databases like CouchDB often provide metadata + * around each record inside a nested structure like this: + * + * { + * "total": 122, + * "offset": 0, + * "users": [ + * { + * "id": "ed-spencer-1", + * "value": 1, + * "user": { + * "id": 1, + * "name": "Ed Spencer", + * "email": "ed@sencha.com" + * } + * } + * ] + * } + * + * In the case above the record data is nested an additional level inside the "users" array as each "user" item has + * additional metadata surrounding it ('id' and 'value' in this case). To parse data out of each "user" item in the + * JSON above we need to specify the {@link #record} configuration like this: + * + * reader: { + * type : 'json', + * rootProperty : 'users', + * record: 'user' + * } + * + * ## Response MetaData + * + * The server can return metadata in its response, in addition to the record data, that describe attributes + * of the data set itself or are used to reconfigure the Reader. To pass metadata in the response you simply + * add a `metaData` attribute to the root of the response data. The metaData attribute can contain anything, + * but supports a specific set of properties that are handled by the Reader if they are present: + * + * - {@link #rootProperty}: the property name of the root response node containing the record data + * - {@link #totalProperty}: property name for the total number of records in the data + * - {@link #successProperty}: property name for the success status of the response + * - {@link #messageProperty}: property name for an optional response message + * - {@link Ext.data.Model#cfg-fields fields}: Config used to reconfigure the Model's fields before converting the + * response data into records + * + * An initial Reader configuration containing all of these properties might look like this ("fields" would be + * included in the Model definition, not shown): + * + * reader: { + * type : 'json', + * rootProperty : 'root', + * totalProperty : 'total', + * successProperty: 'success', + * messageProperty: 'message' + * } + * + * If you were to pass a response object containing attributes different from those initially defined above, you could + * use the `metaData` attribute to reconfigure the Reader on the fly. For example: + * + * { + * "count": 1, + * "ok": true, + * "msg": "Users found", + * "users": [{ + * "userId": 123, + * "name": "Ed Spencer", + * "email": "ed@sencha.com" + * }], + * "metaData": { + * "rootProperty": "users", + * "totalProperty": 'count', + * "successProperty": 'ok', + * "messageProperty": 'msg' + * } + * } + * + * You can also place any other arbitrary data you need into the `metaData` attribute which will be ignored by the Reader, + * but will be accessible via the Reader's {@link #metaData} property (which is also passed to listeners via the Proxy's + * {@link Ext.data.proxy.Proxy#metachange metachange} event (also relayed by the store). Application code can then + * process the passed metadata in any way it chooses. + * + * A simple example for how this can be used would be customizing the fields for a Model that is bound to a grid. By passing + * the `fields` property the Model will be automatically updated by the Reader internally, but that change will not be + * reflected automatically in the grid unless you also update the column configuration. You could do this manually, or you + * could simply pass a standard grid {@link Ext.panel.Table#columns column} config object as part of the `metaData` attribute + * and then pass that along to the grid. Here's a very simple example for how that could be accomplished: + * + * // response format: + * { + * ... + * "metaData": { + * "fields": [ + * { "name": "userId", "type": "int" }, + * { "name": "name", "type": "string" }, + * { "name": "birthday", "type": "date", "dateFormat": "Y-j-m" }, + * ], + * "columns": [ + * { "text": "User ID", "dataIndex": "userId", "width": 40 }, + * { "text": "User Name", "dataIndex": "name", "flex": 1 }, + * { "text": "Birthday", "dataIndex": "birthday", "flex": 1, "format": 'Y-j-m', "xtype": "datecolumn" } + * ] + * } + * } + * + * The Reader will automatically read the meta fields config and rebuild the Model based on the new fields, but to handle + * the new column configuration you would need to handle the metadata within the application code. This is done simply enough + * by handling the metachange event on either the store or the proxy, e.g.: + * + * var store = Ext.create('Ext.data.Store', { + * ... + * listeners: { + * 'metachange': function(store, meta) { + * myGrid.reconfigure(store, meta.columns); + * } + * } + * }); + * + */ +Ext.define('Ext.data.reader.Json', { + extend: 'Ext.data.reader.Reader', + requires: [ + 'Ext.JSON' + ], + alternateClassName: 'Ext.data.JsonReader', + alias: 'reader.json', + config: { + /** + * @cfg {String} record The optional location within the JSON response that the record data itself can be found at. + * See the JsonReader intro docs for more details. This is not often needed. + */ + record: null, + /** + * @cfg {String} [metaProperty] + * Name of the property from which to retrieve the `metaData` attribute. See {@link #metaData}. + */ + metaProperty: 'metaData', + /** + * @cfg {Boolean} useSimpleAccessors True to ensure that field names/mappings are treated as literals when + * reading values. + * + * For example, by default, using the mapping "foo.bar.baz" will try and read a property foo from the root, then a property bar + * from foo, then a property baz from bar. Setting the simple accessors to true will read the property with the name + * "foo.bar.baz" direct from the root object. + */ + useSimpleAccessors: false, + /** + * @cfg {Boolean} preserveRawData + * The reader will keep a copy of the most recent request in the {@link #rawData} property. For performance reasons, + * the data object for each record is used directly as the model data. This means that these objects may be modified and + * thus modify the raw data. To ensure the objects are copied, set this option to `true`. NB: This only applies to items + * that are read as part of the data array, any other metadata will not be modified: + * + * { + * "someOtherData": 1, // Won't be modified + * "root": [{}, {}, {}] // The objects here will be modified + * } + */ + preserveRawData: false + }, + updateRootProperty: function() { + this.forceBuildExtractors(); + }, + updateMetaProperty: function() { + this.forceBuildExtractors(); + }, + /** + * @method readRecords + * Reads a JSON object and returns a ResultSet. Uses the internal getTotal and getSuccess extractors to + * retrieve meta data from the response, and extractData to turn the JSON data into model instances. + * @param {Object} data The raw JSON data + * @param {Object} [readOptions] See {@link #read} for details. + * @return {Ext.data.ResultSet} A ResultSet containing model instances and meta data about the results + */ + getResponseData: function(response) { + var error; + try { + return Ext.decode(response.responseText); + } catch (ex) { + error = this.createReadError(ex.message); + Ext.Logger.warn('Unable to parse the JSON returned by the server'); + this.fireEvent('exception', this, response, error); + return error; + } + }, + buildExtractors: function(force) { + var me = this, + emptyFn = Ext.emptyFn, + prop; + // Will only return true if we need to build + if (me.callParent([ + force + ])) { + me.getRoot = me.setupExtractor(me.getRootProperty(), Ext.identityFn); + me.getGroupRoot = me.setupExtractor(me.getGroupRootProperty(), emptyFn); + me.getSummaryRoot = me.setupExtractor(me.getSummaryRootProperty(), emptyFn); + me.getMeta = me.setupExtractor(me.getMetaProperty(), emptyFn); + } + }, + /** + * @private + * We're just preparing the data for the superclass by pulling out the record objects we want. If a {@link #record} + * was specified we have to pull those out of the larger JSON object, which is most of what this function is doing + * @param {Object} root The JSON root node + * @param {Object} [readOptions] See {@link #read} for details. + * @return {Ext.data.Model[]} The records + */ + extractData: function(root, readOptions) { + var recordName = this.getRecord(), + data = [], + length, i; + if (recordName) { + length = root.length; + if (!length && Ext.isObject(root)) { + length = 1; + root = [ + root + ]; + } + for (i = 0; i < length; i++) { + data[i] = root[i][recordName]; + } + } else { + data = root; + } + return this.callParent([ + data, + readOptions + ]); + }, + getModelData: function(raw) { + return this.getPreserveRawData() ? Ext.apply({}, raw) : raw; + }, + /** + * @private + * @method + * Returns an accessor function for the given property string. Gives support for properties such as the following: + * + * - 'someProperty' + * - 'some.property' + * - '["someProperty"]' + * - 'values[0]' + * + * This is used by {@link #buildExtractors} to create optimized extractor functions for properties that are looked + * up directly on the source object (e.g. {@link #successProperty}, {@link #messageProperty}, etc.). + */ + createAccessor: (function() { + var re = /[\[\.]/; + return function(expr) { + var simple = this.getUseSimpleAccessors(), + operatorIndex, result, current, parts, part, inExpr, isDot, isLeft, isRight, special, c, i, bracketed, len; + if (!(expr || expr === 0)) { + return; + } + if (typeof expr === 'function') { + return expr; + } + if (!simple) { + operatorIndex = String(expr).search(re); + } + if (simple === true || operatorIndex < 0) { + result = function(raw) { + return raw[expr]; + }; + } else { + // The purpose of this part is to generate a "safe" accessor for any complex + // json expression. For example 'foo.bar.baz' will get transformed: + // raw.foo && raw.foo.bar && raw.foo.bar.baz + current = 'raw'; + parts = []; + part = ''; + inExpr = 0; + len = expr.length; + // The <= is intentional here. We handle the last character + // being undefined so that we can append any final values at + // the end + for (i = 0; i <= len; ++i) { + c = expr[i]; + isDot = c === '.'; + isLeft = c === '['; + isRight = c === ']'; + special = isDot || isLeft || isRight || !c; + // If either: + // a) Not a special char + // b) We're nested more than 1 deep, no single char can bring us out + // c) We are in an expr & it's not an ending brace + // Then just push the character on + if (!special || inExpr > 1 || (inExpr && !isRight)) { + part += c; + } else if (special) { + bracketed = false; + if (isLeft) { + ++inExpr; + } else if (isRight) { + --inExpr; + bracketed = true; + } + if (part) { + if (bracketed) { + part = '[' + part + ']'; + } else { + part = '.' + part; + } + current += part; + // Concatting the empty string to the start fixes a very odd intermittent bug with IE9/10. + // On some occasions, without it, it will end up generating + // raw.foo.bar.baz && raw.foo.bar.baz && raw.foo.bar.baz + // At this point, not really sure why forcibly casting it to a string makes a difference + parts.push('' + current); + part = ''; + } + } + } + result = parts.join(' && '); + result = Ext.functionFactory('raw', 'return ' + result); + } + return result; + }; + }()), + /** + * @private + * @method + * Returns an accessor function for the passed Field. Gives support for properties such as the following: + * + * - 'someProperty' + * - 'some.property' + * - '["someProperty"]' + * - 'values[0]' + * + * This is used by {@link #buildExtractors} to create optimized extractor expressions when converting raw + * data into model instances. This method is used at the field level to dynamically map values to model fields. + */ + createFieldAccessor: function(field) { + // Need to capture me for the extractor + var me = this, + mapping = field.mapping, + hasMap = mapping || mapping === 0, + map = hasMap ? mapping : field.name; + if (hasMap) { + if (typeof map === 'function') { + return function(raw, self) { + return field.mapping(raw, self); + }; + } else { + return me.createAccessor(map); + } + } + }, + getAccessorKey: function(prop) { + var simple = this.getUseSimpleAccessors() ? 'simple' : ''; + return this.callParent([ + simple + prop + ]); + }, + privates: { + copyFrom: function(reader) { + this.callParent([ + reader + ]); + this.getRoot = reader.getRoot; + }, + setupExtractor: function(prop, defaultFn) { + return prop ? this.getAccessor(prop) : defaultFn; + } + } +}); + +/** + * This class is used to write {@link Ext.data.Model} data to the server in a JSON format. + * The {@link #allowSingle} configuration can be set to false to force the records to always + * be encoded in an array, even if there is only a single record being sent. + */ +Ext.define('Ext.data.writer.Json', { + extend: 'Ext.data.writer.Writer', + alternateClassName: 'Ext.data.JsonWriter', + alias: 'writer.json', + config: { + /** + * @cfg {String} rootProperty The HTTP parameter name by which JSON encoded records will be passed to the server if the + * {@link #encode} option is `true`. + */ + rootProperty: undefined, + /** + * @cfg {Boolean} [encode=false] Configure `true` to send record data (all record fields if {@link #writeAllFields} is `true`) + * as a JSON encoded HTTP parameter named by the {@link #rootProperty} configuration. + * + * The encode option should only be set to true when a {@link #rootProperty} is defined, because the values will be + * sent as part of the request parameters as opposed to a raw post. The root will be the name of the parameter + * sent to the server. + */ + encode: false, + /** + * @cfg {Boolean} [allowSingle=true] Configure with `false` to ensure that records are always wrapped in an array, even if there is only + * one record being sent. When there is more than one record, they will always be encoded into an array. + */ + allowSingle: true, + /** + * @cfg {Boolean} [expandData=false] By default, when dot-delimited field {@link #nameProperty mappings} are + * used (e.g. `name: 'myProperty', mapping: 'my.nested.property'`) the writer will simply output a flat data + * object containing the mapping string literal as the property name (e.g. `{ 'my.nested.property': 'foo' }`). + * + * Mappings are used to map incoming nested JSON to flat Ext models. In many case, the data output by the + * writer should preferrably match the original nested data format. Setting this config to `true` will ensure + * that the output will instead look like `{ my: { nested: { property: 'foo' }}}`. The output is generated + * by {@link #getExpandedData}, which can optionally be overridden to apply more customized logic. + */ + expandData: false + }, + constructor: function(config) { + if (config && config.hasOwnProperty('root')) { + config = Ext.apply({}, config); + config.rootProperty = config.root; + delete config.root; + Ext.log.warn('Ext.data.writer.Json: Using the deprecated "root" configuration. Use "rootProperty" instead.'); + } + this.callParent([ + config + ]); + }, + /** + * @protected + * The Reader classes support dot-delimited data mappings for extracting nested raw data into fields, so the + * writer must support converting the flat {@link Ext.data.Model} structure back into the original nested data + * format. Using the same mappings when available, the Writer will simply split each delimiter into a nested + * object in the output, which should exactly match the input format. For example, record data like this: + * + * my.nested.property: 'foo', + * my.nested.another: 'bar', + * my.somethingElse: 123 + * + * should write out as... + * + * my: { + * nested: { + * property: 'foo', + * another: 'bar + * }, + * somethingElse: 123 + * } + * + * This behavior is governed by the {@link #expandData} config. By default, this option is `false` for + * compatibility reasons, and will output a flat structure matching the flat record format. Setting this config + * to `true` will enable the expanded mapping behavior as shown here. This method could also be overridden + * to provide an even more customized output data structure. + */ + getExpandedData: function(data) { + var dataLength = data.length, + i = 0, + item, prop, nameParts, j, tempObj, + toObject = function(name, value) { + var o = {}; + o[name] = value; + return o; + }; + for (; i < dataLength; i++) { + item = data[i]; + for (prop in item) { + if (item.hasOwnProperty(prop)) { + // e.g. my.nested.property: 'foo' + nameParts = prop.split('.'); + j = nameParts.length - 1; + if (j > 0) { + // Initially this will be the value 'foo'. + // Equivalent to rec['my.nested.property'] + tempObj = item[prop]; + for (; j > 0; j--) { + // Starting with the value above, we loop inside out, assigning the + // current object as the value for the parent name. Work all + // the way up until only the root name is left to assign. + tempObj = toObject(nameParts[j], tempObj); + } + // At this point we'll have all child properties rolled up into a single + // object like `{ nested: { property: 'foo' }}`. Now add the root name + // (e.g. 'my') to the record data if needed (do not overwrite existing): + item[nameParts[0]] = item[nameParts[0]] || {}; + // Since there could be duplicate names at any level of the nesting be sure + // to merge rather than assign when setting the object as the value: + Ext.Object.merge(item[nameParts[0]], tempObj); + // Finally delete the original mapped property from the record + delete item[prop]; + } + } + } + } + return data; + }, + writeRecords: function(request, data) { + var me = this, + root = me.getRootProperty(), + json, single, transform; + if (me.getExpandData()) { + data = me.getExpandedData(data); + } + if (me.getAllowSingle() && data.length === 1) { + // convert to single object format + data = data[0]; + single = true; + } + transform = this.getTransform(); + if (transform) { + data = transform(data, request); + } + if (me.getEncode()) { + if (root) { + // sending as a param, need to encode + request.setParam(root, Ext.encode(data)); + } else { + Ext.raise('Must specify a root when using encode'); + } + } else if (single || (data && data.length)) { + // send as jsonData + json = request.getJsonData() || {}; + if (root) { + json[root] = data; + } else { + json = data; + } + request.setJsonData(json); + } + return request; + } +}); + +/** + * This class provides a flexible means to control the + * `{@link Ext.util.Collection#cfg!sorters sorters}` of a + * `{@link Ext.util.Collection Collection}`. Instances of this class are created + * automatically when sorters are added to added to Collections. + * + * This collection can be directly manipulated by application code to gain full + * control over the sorters of the owner collection. Be aware that some components + * create sorters internally (such as grids) so be careful in such cases to not disturb + * these additional sorters. + * + * Items in this collection are `Ext.util.Sorter` instances and can be managed + * individually by their `id`. This is the recommended way to manage application + * filters while preserving sorter applied from other sources. + * + * Bulk changes to this collection should be wrapped in + * `{@link Ext.util.Collection#method!beginUpdate beginUpdate}` and + * `{@link Ext.util.Collection#method!endUpdate endUpdate}` (as with any collection). + * During these bulk updates all reactions to sorter changes will be suspended. + */ +Ext.define('Ext.util.SorterCollection', { + extend: 'Ext.util.Collection', + requires: [ + 'Ext.util.Sorter' + ], + isSorterCollection: true, + /** + * @property {Ext.util.Sortable} sortable + * The owning sortable instance. The sortable's configuration governs this + * collection. + * @private + * @readonly + */ + $sortable: null, + /** + * @property sortFn + * This is the cached sorting function which is a generated function that calls all the + * configured sorters in the correct order. + * @readonly + */ + sortFn: null, + config: { + /** + * @cfg {Function} applySorterOptionsFn + * A template method that can be used to apply options to a sorter during creation + * @private + */ + sorterOptionsFn: null, + /** + * @cfg {Object} applySorterOptionsScope + * The scope to execute the {@link #applySorterOptionsFn} + * @private + */ + sorterOptionsScope: null + }, + constructor: function(config) { + var me = this; + me.sortFn = Ext.util.Sorter.createComparator(me); + me.callParent([ + config + ]); + me.setDecoder(me.decodeSorter); + }, + addSort: function(property, direction, mode) { + var me = this, + count, index, limit, options, primary, sorter, sorters; + if (!property) { + // nothing specified so just trigger a sort... + me.beginUpdate(); + me.endUpdate(); + } else { + options = me.getOptions(); + if (property instanceof Array) { + sorters = property; + mode = direction; + direction = null; + } else if (Ext.isString(property)) { + if (!(sorter = me.get(property))) { + sorters = [ + { + property: property, + direction: direction || options.getDefaultSortDirection() + } + ]; + } else { + sorters = [ + sorter + ]; + } + } else if (Ext.isFunction(property)) { + sorters = [ + { + sorterFn: property, + direction: direction || options.getDefaultSortDirection() + } + ]; + } else { + if (!Ext.isObject(property)) { + Ext.raise('Invalid sort descriptor: ' + property); + } + sorters = [ + property + ]; + mode = direction; + direction = null; + } + if (mode && !me._sortModes[mode]) { + Ext.raise('Sort mode should be "multi", "append", "prepend" or "replace", not "' + mode + '"'); + } + mode = me._sortModes[mode || 'replace']; + primary = me.getAt(0); + count = me.length; + index = mode.append ? count : 0; + // We have multiple changes to make, so mark the sorters collection as updating + // before we start. + me.beginUpdate(); + // Leverage the decode logic wired to the collection to up-convert sorters to + // real instances. + me.splice(index, mode.replace ? count : 0, sorters); + if (mode.multi) { + count = me.length; + limit = options.getMultiSortLimit(); + if (count > limit) { + me.removeAt(limit, count); + } + } + // count will be truncated + if (sorter && direction) { + sorter.setDirection(direction); + } else if (index === 0 && primary && primary === me.getAt(0)) { + // If we just adjusted the sorters at the front and the primary sorter is + // still the primary sorter, toggle its direction: + primary.toggle(); + } + me.endUpdate(); + } + }, + clear: function() { + // The owning Collection needs to have its onSortersEndUpdate called on sorter clear so that + // it clears its sorted flag. + this.beginUpdate(); + this.callParent(); + this.endUpdate(this.items); + }, + /** + * Returns an up to date sort function. + * @return {Function} The sort function. + */ + getSortFn: function() { + return this.sortFn; + }, + /** + * Get the first matching sorter with a matching property. + * @param {String} prop The property name + * @return {Ext.util.Sorter} The sorter. `null` if not found. + * @private + */ + getByProperty: function(prop) { + var items = this.items, + len = items.length, + i, item; + for (i = 0; i < len; ++i) { + item = items[i]; + if (item.getProperty() === prop) { + return item; + } + } + return null; + }, + //------------------------------------------------------------------------- + // Private + _sortModes: { + append: { + append: 1 + }, + multi: { + multi: 1 + }, + prepend: { + prepend: 1 + }, + replace: { + replace: 1 + } + }, + decodeSorter: function(sorter, xclass) { + var me = this, + options = me.getOptions(), + root = options.getRootProperty(), + sorterOptionsFn = me.getSorterOptionsFn(), + currentSorter, sorterConfig, type; + if (sorter.isSorter) { + if (!sorter.getRoot()) { + sorter.setRoot(root); + } + } else { + sorterConfig = { + direction: options.getDefaultSortDirection(), + root: root + }; + type = typeof sorter; + // If we are dealing with a string we assume it is a property they want to sort on. + if (type === 'string') { + currentSorter = me.get(sorter); + if (currentSorter) { + return currentSorter; + } + sorterConfig.property = sorter; + } + // If it is a function, we assume its a sorting function. + else if (type === 'function') { + sorterConfig.sorterFn = sorter; + } else // If we are dealing with an object, we assume its a Sorter configuration. In + // this case we create an instance of Sorter passing this configuration. + { + // Finally we get to the point where it has to be invalid + if (!Ext.isObject(sorter)) { + Ext.raise('Invalid sorter specified: ' + sorter); + } + sorterConfig = Ext.apply(sorterConfig, sorter); + if (sorterConfig.fn) { + sorterConfig.sorterFn = sorterConfig.fn; + delete sorterConfig.fn; + } + } + // If a sorter config was created, make it an instance + sorter = Ext.create(xclass || Ext.util.Sorter, sorterConfig); + } + if (sorterOptionsFn) { + sorterOptionsFn.call(me.getSorterOptionsScope() || me, sorter); + } + return sorter; + }, + setSorterConfigure: function(fn, scope) { + this.setSorterOptionsFn(fn); + this.setSorterOptionsScope(scope); + }, + decodeRemoveItems: function(args, index) { + var me = this, + ret = (index === undefined) ? args : args[index]; + if (!ret || !ret.$cloned) { + if (args.length > index + 1 || !Ext.isIterable(ret)) { + ret = Ext.Array.slice(args, index); + } + var currentSorters = me.items, + ln = ret.length, + remove = [], + i, item, n, sorter, type; + for (i = 0; i < ln; i++) { + sorter = ret[i]; + if (sorter && sorter.isSorter) { + remove.push(sorter); + } else { + type = typeof sorter; + if (type === 'string') { + sorter = me.get(sorter); + if (sorter) { + remove.push(sorter); + } + } else if (type === 'function') { + for (n = currentSorters.length; n-- > 0; ) { + item = currentSorters[n]; + if (item.getSorterFn() === sorter) { + remove.push(item); + } + } + } else { + Ext.raise('Invalid sorter specification: ' + sorter); + } + } + } + ret = remove; + ret.$cloned = true; + } + return ret; + }, + getOptions: function() { + // Odd thing this. We need a Sortable to know how to manage our collection, but + // we may not have one. Of course as a Collection, we *are* one as well... just + // that is not really useful to sort the sorters themselves, but we do have the + // default options for Sortables baked in, so we'll do. + return this.$sortable || this; + } +}); + +/** + * This class provides a flexible means to control the + * `{@link Ext.util.Collection#cfg!filters filters}` of a + * `{@link Ext.util.Collection Collection}`. Instances of this class are created + * automatically when filters are added to added to Collections. + * + * This collection can be directly manipulated by application code to gain full + * control over the filters of the owner collection. Be aware that some components + * create filters internally (such as `Ext.form.field.ComboBox` and the + * `Ext.grid.filters.Filters` plugin) so be careful in such cases to not disturb + * these additional filters. + * + * Items in this collection are `Ext.util.Filter` instances and can be managed + * individually by their `id`. This is the recommended way to manage application + * filters while preserving filters applied from other sources. + * + * Bulk changes to this collection should be wrapped in + * `{@link Ext.util.Collection#method!beginUpdate beginUpdate}` and + * `{@link Ext.util.Collection#method!endUpdate endUpdate}` (as with any collection). + * During these bulk updates all reactions to filter changes will be suspended. + */ +Ext.define('Ext.util.FilterCollection', { + extend: 'Ext.util.Collection', + requires: [ + 'Ext.util.Filter' + ], + isFilterCollection: true, + /** + * @property {Ext.util.Collection} $filterable + * The owning filterable instance. The filterable's configuration governs this + * collection. + * @private + * @readonly + */ + $filterable: null, + /** + * @property filterFn + * This is the cached filter function. + * @readonly + */ + filterFn: null, + constructor: function(config) { + var me = this; + // Because this closure operates on the collection, we are able to use it for as + // long as we have the Collection instance. + me.filterFn = Ext.util.Filter.createFilterFn(me); + me.callParent([ + config + ]); + me.setDecoder(me.decodeFilter); + }, + /** + * This method will filter an array based on the currently configured `filters`. + * @param {Array} data The array you want to have filtered. + * @return {Array} The array you passed after it is filtered. + */ + filterData: function(data) { + return this.filtered ? Ext.Array.filter(data, this.filterFn) : data; + }, + /** + * Returns the filter function. + * @return {Function} The filter function. + */ + getFilterFn: function() { + return this.filterFn; + }, + isItemFiltered: function(item) { + return !this.filterFn(item); + }, + /** + * returns the number of *enabled* filters in this `FilterCollection` + * @returns {Number} + */ + getFilterCount: function() { + var filters = this.items, + len = filters.length, + i; + for (i = len - 1; i >= 0; i--) { + if (filters[i].getDisabled()) { + len--; + } + } + return len; + }, + //------------------------------------------------------------------------- + // Private + decodeFilter: function(filter) { + var options = this.getOptions(), + filterRoot = options.getRootProperty(), + filterConfig; + if (filter.isFilter) { + if (!filter.getRoot()) { + filter.setRoot(filterRoot); + } + } else { + filterConfig = { + root: filterRoot + }; + if (Ext.isFunction(filter)) { + filterConfig.filterFn = filter; + } else // If we are dealing with an object, we assume its a Filter configuration. In + // this case we create an instance of Ext.util.Filter passing the config. + { + // Finally we get to the point where it has to be invalid + if (!Ext.isObject(filter)) { + Ext.raise('Invalid filter specified: ' + filter); + } + filterConfig = Ext.apply(filterConfig, filter); + if (filterConfig.fn) { + filterConfig.filterFn = filterConfig.fn; + delete filterConfig.fn; + } + if (Ext.util.Filter.isInvalid(filterConfig)) { + return false; + } + } + filter = new Ext.util.Filter(filterConfig); + } + return filter; + }, + decodeRemoveItems: function(args, index) { + var me = this, + ret = (index === undefined) ? args : args[index]; + if (!ret.$cloned) { + if (args.length > index + 1 || !Ext.isIterable(ret)) { + ret = Ext.Array.slice(args, index); + } + var currentFilters = me.items, + ln = ret.length, + remove = [], + filter, i, isFunction, isProp, isString, item, match, n, type; + for (i = 0; i < ln; i++) { + filter = ret[i]; + if (filter && filter.isFilter) { + remove.push(filter); + } else { + type = typeof filter; + isFunction = type === 'function'; + isProp = filter.property !== undefined && filter.value !== undefined; + isString = type === 'string'; + if (!isFunction && !isProp && !isString) { + Ext.raise('Invalid filter specification: ' + filter); + } + for (n = currentFilters.length; n-- > 0; ) { + item = currentFilters[n]; + match = false; + if (isString) { + match = item.getProperty() === filter; + } else if (isFunction) { + match = item.getFilterFn() === filter; + } else if (isProp) { + match = item.getProperty() === filter.property && item.getValue() === filter.value; + } + if (match) { + remove.push(item); + } + } + } + } + ret = remove; + ret.$cloned = true; + } + return ret; + }, + getOptions: function() { + // Odd thing this. We need a Filterable to know how to manage our collection, but + // we may not have one. Of course as a Collection, we *are* one as well... just + // that is not really useful to filter the filters themselves, but we do have the + // default options for Filterable baked in, so we'll do. + return this.$filterable || this; + } +}); + +/** + * @private + * A collection containing the result of applying grouping to the records in the store. + */ +Ext.define('Ext.util.GroupCollection', { + extend: 'Ext.util.Collection', + requires: [ + 'Ext.util.Group', + // Since Collection uses sub-collections of various derived types we step up to + // list all the requirements of Collection. The idea being that instead of a + // "requires" of Ext.util.Collection (which cannot pull everything) you instead + // do a "requires" of Ext.util.GroupCollection and it will. + 'Ext.util.SorterCollection', + 'Ext.util.FilterCollection' + ], + isGroupCollection: true, + config: { + grouper: null, + groupConfig: null, + itemRoot: null + }, + observerPriority: -100, + emptyGroupRetainTime: 300000, + // Private timer to hang on to emptied groups. Milliseconds. + constructor: function(config) { + this.emptyGroups = {}; + this.callParent([ + config + ]); + this.on('remove', 'onGroupRemove', this); + }, + /** + * Returns the `Ext.util.Group` associated with the given record. + * + * @param {Object} item The item for which the group is desired. + * @return {Ext.util.Group} + * @since 6.5.0 + */ + getItemGroup: function(item) { + var key = this.getGrouper().getGroupString(item); + return this.get(key); + }, + //------------------------------------------------------------------------- + // Calls from the source Collection: + onCollectionAdd: function(source, details) { + if (!this.isConfiguring) { + this.addItemsToGroups(source, details.items, details.at); + } + }, + onCollectionBeforeItemChange: function(source, details) { + this.changeDetails = details; + }, + onCollectionBeginUpdate: function() { + this.beginUpdate(); + }, + onCollectionEndUpdate: function() { + this.endUpdate(); + }, + onCollectionItemChange: function(source, details) { + // Check if the change to the item caused the item to move. If it did, the group + // ordering will be handled by virtue of being removed/added to the collection. + // If not, check whether we're in the correct group and fix up if not. + if (!details.indexChanged) { + this.syncItemGrouping(source, details); + } + this.changeDetails = null; + }, + onCollectionRefresh: function(source) { + if (source.generation) { + var me = this, + itemGroupKeys = me.itemGroupKeys = {}, + groupData = me.createEntries(source, source.items), + entries = groupData.entries, + groupKey, i, len, entry, j; + // The magic of Collection will automatically update the group with its new members. + for (i = 0 , len = entries.length; i < len; ++i) { + entry = entries[i]; + // Will add or replace + entry.group.splice(0, 1.0E99, entry.items); + // Add item key -> group mapping for every entry + for (j = 0; j < entry.items.length; j++) { + itemGroupKeys[source.getKey(entry.items[j])] = entry.group; + } + } + // Remove groups to which we have not added items. + entries = null; + for (groupKey in me.map) { + if (!(groupKey in groupData.groups)) { + (entries || (entries = [])).push(me.map[groupKey]); + } + } + if (entries) { + me.remove(entries); + } + // autoSort is disabled when adding new groups because + // it relies on there being at least one record in the group + me.sortItems(); + } + }, + onCollectionRemove: function(source, details) { + var me = this, + changeDetails = me.changeDetails, + itemGroupKeys = me.itemGroupKeys || (me.itemGroupKeys = {}), + entries, entry, group, i, n, j, removeGroups, item; + if (source.getCount()) { + if (changeDetails) { + // The item has changed, so the group key may be different, need + // to look it up + item = changeDetails.item || changeDetails.items[0]; + entries = me.createEntries(source, [ + item + ]).entries; + entries[0].group = itemGroupKeys['oldKey' in details ? details.oldKey : source.getKey(item)]; + } else { + entries = me.createEntries(source, details.items).entries; + } + for (i = 0 , n = entries.length; i < n; ++i) { + group = (entry = entries[i]).group; + if (group) { + group.remove(entry.items); + } + // Delete any item key -> group mapping + for (j = 0; j < entry.items.length; j++) { + delete itemGroupKeys[source.getKey(entry.items[j])]; + } + if (group && !group.length) { + (removeGroups || (removeGroups = [])).push(group); + } + } + } else // Straight cleardown + { + me.itemGroupKeys = {}; + removeGroups = me.items; + for (i = 0 , n = removeGroups.length; i < n; ++i) { + removeGroups[i].clear(); + } + } + if (removeGroups) { + me.remove(removeGroups); + } + }, + // If the SorterCollection instance is not changing, the Group will react to + // changes inside the SorterCollection, but if the instance changes we need + // to sync the Group to the new SorterCollection. + onCollectionSort: function(source) { + // sorting the collection effectively sorts the items in each group... + var me = this, + sorters = source.getSorters(false), + items, length, i, group; + if (sorters) { + items = me.items; + length = me.length; + for (i = 0; i < length; ++i) { + group = items[i]; + if (group.getSorters() !== sorters) { + group.setSorters(sorters); + } + } + } + }, + onCollectionUpdateKey: function(source, details) { + if (!details.indexChanged) { + details.oldIndex = source.indexOf(details.item); + this.syncItemGrouping(source, details); + } + }, + //------------------------------------------------------------------------- + // Private + addItemsToGroups: function(source, items, at, oldIndex) { + var me = this, + itemGroupKeys = me.itemGroupKeys || (me.itemGroupKeys = {}), + entries = me.createEntries(source, items).entries, + index = -1, + sourceStartIndex, entry, i, len, j, group, firstIndex, item; + for (i = 0 , len = entries.length; i < len; ++i) { + entry = entries[i]; + group = entry.group; + // A single item moved - from onCollectionItemChange + if (oldIndex || oldIndex === 0) { + item = items[0]; + if (group.getCount() > 0 && source.getSorters().getCount() === 0) { + // We have items in the group & it's not sorted, so find the + // correct position in the group to insert. + firstIndex = source.indexOf(group.items[0]); + if (oldIndex < firstIndex) { + index = 0; + } else { + index = oldIndex - firstIndex; + } + } + if (index === -1) { + group.add(item); + } else { + group.insert(index, item); + } + } else { + if (me.length > 1 && at) { + sourceStartIndex = source.indexOf(entries[0].group.getAt(0)); + at = Math.max(at - sourceStartIndex, 0); + } + entry.group.insert(at != null ? at : group.items.length, entry.items); + // Add item key -> group mapping + for (j = 0; j < entry.items.length; j++) { + itemGroupKeys[source.getKey(entry.items[j])] = entry.group; + } + } + } + // autoSort is disabled when adding new groups because + // it relies on there being at least one record in the group + me.sortItems(); + }, + createEntries: function(source, items) { + // Separate the items out into arrays by group + var me = this, + groups = {}, + entries = [], + grouper = me.getGrouper(), + entry, group, groupKey, i, item, len; + for (i = 0 , len = items.length; i < len; ++i) { + groupKey = grouper.getGroupString(item = items[i]); + if (!(entry = groups[groupKey])) { + group = me.getGroup(source, groupKey); + entries.push(groups[groupKey] = entry = { + group: group, + items: [] + }); + } + // Collect items to add/remove for each group + // which has items in the array + entry.items.push(item); + } + return { + groups: groups, + entries: entries + }; + }, + syncItemGrouping: function(source, details) { + var me = this, + itemGroupKeys = me.itemGroupKeys || (me.itemGroupKeys = {}), + item = details.item, + oldKey, itemKey, oldGroup, group; + itemKey = source.getKey(item); + oldKey = 'oldKey' in details ? details.oldKey : itemKey; + // The group the item was in before the change took place. + oldGroup = itemGroupKeys[oldKey]; + // Look up/create the group into which the item now must be added. + group = me.getGroup(source, me.getGrouper().getGroupString(item)); + details.group = group; + details.oldGroup = oldGroup; + // The change did not cause a change in group + if (!(details.groupChanged = group !== oldGroup)) { + // Inform group about change + oldGroup.itemChanged(item, details.modified, details.oldKey, details); + } else { + // Remove from its old group if there was one. + if (oldGroup) { + // Ensure Geoup knows about any unknown key changes, or item will not be removed. + oldGroup.updateKey(item, oldKey, itemKey); + oldGroup.remove(item); + // Queue newly empy group for destruction. + if (!oldGroup.length) { + me.remove(oldGroup); + } + } + // Add to new group + me.addItemsToGroups(source, [ + item + ], null, details.oldIndex); + } + // Keep item key -> group mapping up to date + delete itemGroupKeys[oldKey]; + itemGroupKeys[itemKey] = group; + }, + getGroup: function(source, key) { + var me = this, + group = me.get(key), + autoSort = me.getAutoSort(); + if (group) { + group.setSorters(source.getSorters()); + } else { + group = me.emptyGroups[key] || Ext.create(Ext.apply({ + xclass: 'Ext.util.Group', + groupKey: key, + rootProperty: me.getItemRoot(), + sorters: source.getSorters() + }, me.getGroupConfig())); + group.ejectTime = null; + me.setAutoSort(false); + me.add(group); + me.setAutoSort(autoSort); + } + return group; + }, + getKey: function(item) { + return item.getGroupKey(); + }, + createSortFn: function() { + var me = this, + grouper = me.getGrouper(), + sorterFn = me.getSorters().getSortFn(); + if (!grouper) { + return sorterFn; + } + return function(lhs, rhs) { + // The grouper has come from the collection, so we pass the items in + // the group for comparison because the grouper is also used to + // sort the data in the collection + return grouper.sort(lhs.items[0], rhs.items[0]) || sorterFn(lhs, rhs); + }; + }, + updateGrouper: function(grouper) { + var me = this; + me.grouped = !!(grouper && me.$groupable.getAutoGroup()); + me.onSorterChange(); + me.onEndUpdateSorters(me.getSorters()); + }, + destroy: function() { + var me = this; + me.$groupable = null; + // Ensure group objects get destroyed, they may have + // added listeners to the main collection sorters. + me.destroyGroups(me.items); + Ext.undefer(me.checkRemoveQueueTimer); + me.callParent(); + }, + privates: { + destroyGroups: function(groups) { + var len = groups.length, + i; + for (i = 0; i < len; ++i) { + groups[i].destroy(); + } + }, + onGroupRemove: function(collection, info) { + var me = this, + groups = info.items, + emptyGroups = me.emptyGroups, + len, group, i; + groups = Ext.Array.from(groups); + for (i = 0 , len = groups.length; i < len; i++) { + group = groups[i]; + group.setSorters(null); + emptyGroups[group.getGroupKey()] = group; + group.ejectTime = Ext.now(); + } + // Removed empty groups are reclaimable by getGroup for emptyGroupRetainTime milliseconds + me.checkRemoveQueue(); + }, + checkRemoveQueue: function() { + var me = this, + emptyGroups = me.emptyGroups, + groupKey, group, reschedule; + for (groupKey in emptyGroups) { + group = emptyGroups[groupKey]; + // If the group's retain time has expired, destroy it. + if (!group.getCount() && Ext.now() - group.ejectTime > me.emptyGroupRetainTime) { + Ext.destroy(group); + delete emptyGroups[groupKey]; + } else { + reschedule = true; + } + } + // Still some to remove in the future. Check back in emptyGroupRetainTime + if (reschedule) { + Ext.undefer(me.checkRemoveQueueTimer); + me.checkRemoveQueueTimer = Ext.defer(me.checkRemoveQueue, me.emptyGroupRetainTime, me); + } + } + } +}); + +/** + * The Store class encapsulates a client side cache of {@link Ext.data.Model Model} objects. Stores load data via a + * {@link Ext.data.proxy.Proxy Proxy}, and also provide functions for {@link #method-sort sorting}, {@link #filter filtering} + * and querying the {@link Ext.data.Model model} instances contained within it. + * + * Creating a Store is easy - we just tell it the Model and the Proxy to use for loading and saving its data: + * + * // Set up a model to use in our Store + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: [ + * {name: 'firstName', type: 'string'}, + * {name: 'lastName', type: 'string'}, + * {name: 'age', type: 'int'}, + * {name: 'eyeColor', type: 'string'} + * ] + * }); + * + * var myStore = Ext.create('Ext.data.Store', { + * model: 'User', + * proxy: { + * type: 'ajax', + * url: '/users.json', + * reader: { + * type: 'json', + * rootProperty: 'users' + * } + * }, + * autoLoad: true + * }); + * + * In the example above we configured an AJAX proxy to load data from the url '/users.json'. We told our Proxy to use a + * {@link Ext.data.reader.Json JsonReader} to parse the response from the server into Model object - {@link + * Ext.data.reader.Json see the docs on JsonReader} for details. + * + * ## Inline data + * + * Stores can also load data inline. Internally, Store converts each of the objects we pass in as {@link #cfg-data} into + * Model instances: + * + * Ext.create('Ext.data.Store', { + * model: 'User', + * data : [ + * {firstName: 'Peter', lastName: 'Venkman'}, + * {firstName: 'Egon', lastName: 'Spengler'}, + * {firstName: 'Ray', lastName: 'Stantz'}, + * {firstName: 'Winston', lastName: 'Zeddemore'} + * ] + * }); + * + * Loading inline data using the method above is great if the data is in the correct format already (e.g. it doesn't + * need to be processed by a {@link Ext.data.reader.Reader reader}). If your inline data requires processing to decode + * the data structure, use a {@link Ext.data.proxy.Memory MemoryProxy} instead (see the {@link Ext.data.proxy.Memory + * MemoryProxy} docs for an example). + * + * Additional data can also be loaded locally using {@link #method-add}. + * + * ## Dynamic Loading + * + * Stores can be dynamically updated by calling the {@link #method-load} method: + * + * store.load({ + * params: { + * group: 3, + * type: 'user' + * }, + * callback: function(records, operation, success) { + * // do something after the load finishes + * }, + * scope: this + * }); + * + * Here a bunch of arbitrary parameters is passed along with the load request and a callback function is set + * up to do something after the loading is over. + * + * ## Loading Nested Data + * + * Applications often need to load sets of associated data - for example a CRM system might load a User and her Orders. + * Instead of issuing an AJAX request for the User and a series of additional AJAX requests for each Order, we can load + * a nested dataset and allow the Reader to automatically populate the associated models. Below is a brief example, see + * the {@link Ext.data.reader.Reader} intro docs for a full explanation: + * + * var store = Ext.create('Ext.data.Store', { + * autoLoad: true, + * model: "User", + * proxy: { + * type: 'ajax', + * url: 'users.json', + * reader: { + * type: 'json', + * rootProperty: 'users' + * } + * } + * }); + * + * Which would consume a response like this: + * + * { + * "users": [{ + * "id": 1, + * "name": "Peter", + * "orders": [{ + * "id": 10, + * "total": 10.76, + * "status": "invoiced" + * },{ + * "id": 11, + * "total": 13.45, + * "status": "shipped" + * }] + * }] + * } + * + * See the {@link Ext.data.reader.Reader} intro docs for a full explanation. + * + * ## Filtering and Sorting + * + * Stores can be sorted and filtered - in both cases either remotely or locally. The {@link #cfg-sorters} and + * {@link #cfg-filters} are held inside {@link Ext.util.Collection Collection} instances to make them easy to manage. + * Usually it is sufficient to either just specify sorters and filters in the Store configuration or call {@link #method-sort} + * or {@link #filter}: + * + * var store = Ext.create('Ext.data.Store', { + * model: 'User', + * sorters: [{ + * property: 'age', + * direction: 'DESC' + * }, { + * property: 'firstName', + * direction: 'ASC' + * }], + * + * filters: [{ + * property: 'firstName', + * value: /Peter/ + * }] + * }); + * + * The new Store will keep the configured sorters and filters in the Collection instances mentioned above. By + * default, sorting and filtering are both performed locally by the Store - see {@link #remoteSort} and + * {@link #remoteFilter} to allow the server to perform these operations instead. + * + * Filtering and sorting after the Store has been instantiated is also easy. Calling {@link #filter} adds another filter + * to the Store and automatically filters the dataset (calling {@link #filter} with no arguments simply re-applies all + * existing filters). + * + * store.filter('eyeColor', 'Brown'); + * + * Change the sorting at any time by calling {@link #method-sort}: + * + * store.sort('height', 'ASC'); + * + * Note that all existing sorters will be removed in favor of the new sorter data (if {@link #method-sort} is called with no + * arguments, the existing sorters are just reapplied instead of being removed). To keep existing sorters and add new + * ones, just add them to the Collection: + * + * store.sorters.add(new Ext.util.Sorter({ + * property : 'shoeSize', + * direction: 'ASC' + * })); + * + * store.sort(); + * + * ## Registering with StoreManager + * + * Any Store that is instantiated with a {@link #storeId} will automatically be registered with the {@link + * Ext.data.StoreManager StoreManager}. This makes it easy to reuse the same store in multiple views: + * + * //this store can be used several times + * Ext.create('Ext.data.Store', { + * model: 'User', + * storeId: 'usersStore' + * }); + * + * new Ext.List({ + * store: 'usersStore', + * //other config goes here + * }); + * + * new Ext.view.View({ + * store: 'usersStore', + * //other config goes here + * }); + * + * ## Further Reading + * + * Stores are backed up by an ecosystem of classes that enables their operation. To gain a full understanding of these + * pieces and how they fit together, see: + * + * - {@link Ext.data.proxy.Proxy Proxy} - overview of what Proxies are and how they are used + * - {@link Ext.data.Model Model} - the core class in the data package + * - {@link Ext.data.reader.Reader Reader} - used by any subclass of {@link Ext.data.proxy.Server ServerProxy} to read a response + */ +Ext.define('Ext.data.Store', { + extend: 'Ext.data.ProxyStore', + alias: 'store.store', + mixins: [ + 'Ext.data.LocalStore' + ], + // Required classes must be loaded before the definition callback runs + // The class definition callback creates a dummy Store which requires that + // all the classes below have been loaded. + requires: [ + 'Ext.data.Model', + 'Ext.data.proxy.Ajax', + 'Ext.data.reader.Json', + 'Ext.data.writer.Json', + // This ensures that we have Ext.util.Collection and all of its requirements. + 'Ext.util.GroupCollection', + 'Ext.util.DelayedTask' + ], + uses: [ + 'Ext.data.StoreManager', + 'Ext.util.Grouper' + ], + config: { + /** + * @cfg {Object[]/Ext.data.Model[]} data + * Array of Model instances or data objects to load locally. See "Inline data" + * above for details. + */ + data: undefined, + // undefined so the applier is always called + /** + * @cfg {Boolean} [clearRemovedOnLoad=true] + * `true` to clear anything in the {@link #removed} record collection when the store loads. + */ + clearRemovedOnLoad: true, + /** + * @cfg {Boolean} [clearOnPageLoad=true] + * True to empty the store when loading another page via {@link #loadPage}, + * {@link #nextPage} or {@link #previousPage}. Setting to false keeps existing records, allowing + * large data sets to be loaded one page at a time but rendered all together. + */ + clearOnPageLoad: true, + /** + * @cfg {Ext.data.Model} [associatedEntity] + * The owner of this store if the store is used as part of an association. + * + * @private + */ + associatedEntity: null, + /** + * @cfg {Ext.data.schema.Role} [role] + * The role for the {@link #associatedEntity}. + * + * @private + */ + role: null, + /** + * @cfg {Ext.data.Session} session + * The session for this store. By specifying a session, it ensures any records that are + * added to this store are also included in the session. This store does not become a member + * of the session itself. + * + * @since 5.0.0 + */ + session: null + }, + /** + * @property {Ext.util.Collection} data + * The `data` property is a `Collection` which holds this store's local cache of records. + * @private + * @readonly + */ + /** + * @private + * Used as a parameter to loadRecords + */ + addRecordsOptions: { + addRecords: true + }, + /** + * @property {Number} loadCount + * The number of times records have been loaded into the store. This includes loads via + * {@link #loadData} & {@link #loadRecords}. + * @readonly + */ + loadCount: 0, + /** + * `true` once the store has loaded data from the server. + * @property {Boolean} complete + * + * @private + */ + complete: false, + moveMapCount: 0, + /** + * Creates the store. + * @param {Object} [config] Config object. + */ + constructor: function(config) { + var me = this, + data; + if (config) { + if (config.buffered) { + if (this.self !== Ext.data.Store) { + Ext.raise('buffered config not supported on derived Store classes. ' + 'Please derive from Ext.data.BufferedStore.'); + } + // Hide this from Cmd + return new Ext.data['BufferedStore'](config); + } + if (config.remoteGroup) { + Ext.log.warn('Ext.data.Store: remoteGroup has been removed. Use remoteSort instead.'); + } + } + /** + * @event beforeprefetch + * Fires before a prefetch occurs. Return `false` to cancel. + * @param {Ext.data.Store} this + * @param {Ext.data.operation.Operation} operation The associated operation. + */ + /** + * @event groupchange + * Fired whenever the grouping in the grid changes. + * @param {Ext.data.Store} store The store. + * @param {Ext.util.Grouper} grouper The grouper object. + */ + /** + * @event prefetch + * Fires whenever records have been prefetched. + * @param {Ext.data.Store} this + * @param {Ext.data.Model[]} records An array of records. + * @param {Boolean} successful `true` if the operation was successful. + * @param {Ext.data.operation.Operation} operation The associated operation. + */ + /** + * @event filterchange + * Fired whenever the filter set changes. + * @param {Ext.data.Store} store The store. + * @param {Ext.util.Filter[]} filters The array of Filter objects. + */ + me.callParent([ + config + ]); + // See applyData for the details. + data = me.inlineData; + if (data) { + delete me.inlineData; + me.loadInlineData(data); + } + }, + /** + * @method getData + * Returns the store's records. + * + * **Note:** If your store has been filtered, getData() will return a filtered + * collection. Use `getData().{@link Ext.util.Collection#getSource getSource()}` to + * fetch all unfiltered records. + * + * @return {Ext.util.Collection} An Ext.util.Collection of records + * (an empty Collection if no records are held by the store). + */ + /** + * @method setData + * Loads an array of data directly into the Store. + * + * setData() is ideal if your data's format is already in its appropriate format (e.g. it doesn't need to be + * processed by a reader). If your data's structure requires processing, use a + * {@link Ext.data.proxy.Memory MemoryProxy} or {@link #loadRawData}. + * + * Use {@link #loadData}, {@link #method-add}, or {@link #insert} if records need to be + * appended to the current recordset. + * + * @param {Ext.data.Model[]/Object[]} data Array of data to load. Any non-model instances will be cast + * into model instances first. + */ + applyData: function(data, dataCollection) { + // We bring up the Collection for records which forms the bottom of the config + // dependency graph. The appliers for "filters" and "sorters" depend on "data" + // and "remoteFilter" and "remoteSort" depend on both in their updaters. + var me = this; + // Ensure that the model class exits + me.getFields(); + me.getModel(); + // We might be configured with a Collection instance + if (data && data.isCollection) { + dataCollection = data; + } else { + if (!dataCollection) { + dataCollection = me.constructDataCollection(); + } + if (data) { + if (me.isInitializing) { + // When data is configured on the instance of a Store we must wait for + // all the things to initialize (sorters, filters, groupers) so that we + // can properly process that data. All of those appliers, however, depend + // on the dataCollection (us) to get booted up first so we must defer + // this back to after initConfig. In previous versions this was hacked + // at by the constructor via "config.data" but "data" can also be set on + // the Ext.define level so best to pick it up here and store aside to be + // finished in the constructor. + me.inlineData = data; + } else { + // If we are not constructing the Store than a setData call needs to be equivalent + // to the legacy loadData method with respect to events that fire, etc.. + me.loadData(data); + } + } + } + return dataCollection; + }, + loadInlineData: function(data) { + var me = this, + proxy = me.getProxy(); + if (proxy && proxy.isMemoryProxy) { + proxy.setData(data); + // Allow a memory proxy to trigger a load initially + me.suspendEvents(); + me.read(); + me.resumeEvents(); + } else { + // We make it silent because we don't want to fire a refresh event + me.removeAll(true); + // We don't want to fire addrecords event since we will be firing + // a refresh event later which will already take care of updating + // any views bound to this store + me.suspendEvents(); + me.loadData(data); + me.resumeEvents(); + } + }, + /** + * @method insert + * @inheritdoc Ext.data.LocalStore#insert + */ + onCollectionAdd: function(collection, info) { + this.loadCount = this.loadCount || 1; + this.onCollectionAddItems(collection, info.items, info); + }, + onCollectionFilterAdd: function(collection, items) { + this.onCollectionAddItems(collection, items); + }, + onCollectionAddItems: function(collection, records, info) { + var me = this, + len = records.length, + lastChunk = info ? !info.next : false, + // Must use class-specific removed property. + // Regular Stores add to the "removed" property on remove. + // TreeStores are having records removed all the time; node collapse removes. + // TreeStores add to the "removedNodes" property onNodeRemove + removed = me.removed, + ignoreAdd = me.ignoreCollectionAdd, + session = me.getSession(), + replaced = info && info.replaced, + i, sync, record, replacedItems; + // Collection add changes the items reference of the collection, and that array + // object if directly referenced by Ranges. The ranges have to refresh themselves + // upon add. + if (me.activeRanges) { + me.syncActiveRanges(); + } + for (i = 0; i < len; ++i) { + record = records[i]; + if (session) { + session.adopt(record); + } + // If ignoring, we don't want to do anything other than pull + // the added records into the session + if (!ignoreAdd) { + record.join(me); + if (removed && removed.length) { + Ext.Array.remove(removed, record); + } + sync = sync || record.phantom || record.dirty; + } + } + if (ignoreAdd) { + return; + } + if (replaced) { + replacedItems = []; + do { + Ext.Array.push(replacedItems, replaced.items); + replaced = replaced.next; + } while (replaced); + me.setMoving(replacedItems, true); + } + if (info) { + // If this is a replacement operation, there will have been a + // previous call to onCollectionRemove which will have fired no + // events in anticipation of a final refresh event. + // Here is where we inform interested parties of all the changes. + if (info.replaced) { + if (lastChunk) { + me.fireEvent('datachanged', me); + me.fireEvent('refresh', me); + } + } else { + me.fireEvent('add', me, records, info.at); + // If there is a next property, that means there is another range that needs + // to be removed after this. Wait until everything is gone before firing datachanged + // since it should be a bulk operation + if (lastChunk) { + me.fireEvent('datachanged', me); + } + } + } + if (replacedItems) { + me.setMoving(replacedItems, false); + } + // Addition means a sync is needed. + me.needsSync = me.needsSync || sync; + }, + onCollectionBeforeItemChange: function(collection, info) { + var record = info.item, + modifiedFieldNames = info.modified || null, + type = info.meta; + // This is currently intended to be private + this.fireEvent('beforeupdate', this, record, type, modifiedFieldNames, info); + }, + // If our source collection informs us that a filtered out item has changed, we must still fire the events... + onCollectionFilteredItemChange: function() { + this.onCollectionItemChange.apply(this, arguments); + }, + onCollectionItemChange: function(collection, info) { + var me = this, + record = info.item, + modifiedFieldNames = info.modified || null, + type = info.meta; + if (me.fireChangeEvent(record)) { + // Inform any interested parties that a record has been mutated. + // This will be invoked on TreeStores in which the invoking record + // is an descendant of a collapsed node, and so *will not be contained by this store + me.onUpdate(record, type, modifiedFieldNames, info); + me.fireEvent('update', me, record, type, modifiedFieldNames, info); + me.fireEvent('datachanged', me); + } + }, + afterChange: function(record, modifiedFieldNames, type) { + this.getData().itemChanged(record, modifiedFieldNames || null, undefined, type); + }, + afterCommit: function(record, modifiedFieldNames) { + this.afterChange(record, modifiedFieldNames, Ext.data.Model.COMMIT); + }, + afterEdit: function(record, modifiedFieldNames) { + this.needsSync = this.needsSync || record.dirty; + this.afterChange(record, modifiedFieldNames, Ext.data.Model.EDIT); + }, + afterReject: function(record) { + this.afterChange(record, null, Ext.data.Model.REJECT); + }, + afterDrop: function(record) { + this.getData().remove(record); + }, + afterErase: function(record) { + this.removeFromRemoved(record); + }, + /** + * @method add + * @inheritdoc Ext.data.LocalStore#add + */ + /** + * (Local sort only) Inserts the passed Record into the Store at the index where it + * should go based on the current sort information. + * + * @param {Ext.data.Record} record + */ + addSorted: function(record) { + var me = this, + remote = me.getRemoteSort(), + data = me.getData(), + index; + if (remote) { + data.setSorters(me.getSorters()); + } + index = data.findInsertionIndex(record); + if (remote) { + data.setSorters(null); + } + return me.insert(index, record); + }, + /** + * Removes the specified record(s) from the Store, firing the {@link #event-remove} + * event for the removed records. + * + * After all records have been removed a single `datachanged` is fired. + * + * @param {Ext.data.Model/Ext.data.Model[]/Number/Number[]} records Model instance or + * array of instances to remove or an array of indices from which to remove records. + * @param isMove (private) + * @param silent (private) + */ + remove: function(records, isMove, silent) { + var me = this, + data = me.getDataSource(), + len, i, toRemove, record; + if (records) { + if (records.isModel) { + if (data.indexOf(records) > -1) { + toRemove = [ + records + ]; + len = 1; + } else { + len = 0; + } + } else { + toRemove = []; + for (i = 0 , len = records.length; i < len; ++i) { + record = records[i]; + if (record && record.isEntity) { + if (!data.contains(record)) { + + continue; + } + } else if (!(record = data.getAt(record))) { + // an index + + continue; + } + toRemove.push(record); + } + len = toRemove.length; + } + } + if (!len) { + return []; + } + me.removeIsMove = isMove === true; + me.removeIsSilent = silent; + data.remove(toRemove); + me.removeIsSilent = false; + return toRemove; + }, + onCollectionRemove: function(collection, info) { + var me = this, + // Must use class-specific removed property. + // Regular Stores add to the "removed" property on remove. + // TreeStores are having records removed all the time; node collapse removes. + // TreeStores add to the "removedNodes" property onNodeRemove + removed = me.removed, + records = info.items, + len = records.length, + index = info.at, + replacement = info.replacement, + isMove = me.removeIsMove || (replacement && Ext.Array.equals(records, replacement.items)), + silent = me.removeIsSilent, + lastChunk = !info.next, + data = me.getDataSource(), + i, record; + if (me.ignoreCollectionRemove) { + return; + } + if (replacement) { + me.setMoving(replacement.items, true); + } + for (i = len - 1; i >= 0; i--) { + record = records[i]; + // If the data contains the record, that means the record is filtered out, so + // it's not being removed, nor should it be unjoined + if (!data.contains(record)) { + // Don't push interally moving, or phantom (client side only), + // erasing (informing server through its own proxy) records + if (removed && !isMove && !record.phantom && !record.erasing) { + // Store the index the record was removed from so that rejectChanges can re-insert at the correct place. + // The record's index property won't do, as that is the index in the overall dataset when Store is buffered. + record.removedFrom = index + i; + removed.push(record); + // Removal of a non-phantom record which is NOT erasing (informing the server through its own proxy) + // requires that the store be synced at some point. + me.needsSync = true; + } else { + // Only unjoin if we're not being pushed into the removed collection. We still + // have an interest in that record otherwise. + record.unjoin(me); + } + } + } + if (!silent) { + // If this removal is just the first part of a replacement operation, + // do not fire the events now. + // + // onCollectionAddItems will fire a refresh event, and convert multiple + // remove and add operations to an atomic refresh event. + // This will provide a better UI update. + // Also, focus can only be preserved around one operation, so + // editing a field which is the sorted field could result in + // incorrect focus.. + if (!replacement || !replacement.items.length) { + me.fireEvent('remove', me, records, index, isMove); + // If there is a next property, that means there is another range that needs + // to be removed after this. Wait until everything is gone before firing datachanged + // since it should be a bulk operation + if (lastChunk) { + me.fireEvent('datachanged', me); + } + } + } + if (replacement) { + me.setMoving(replacement.items, false); + } + }, + onFilterEndUpdate: function() { + var me = this; + if (me.destroying || me.destroyed) { + return; + } + // Filtering changes the items reference of the collection, and that array + // object if directly referenced by Ranges. The ranges have to refresh themselves + // upon add. + if (me.activeRanges) { + me.syncActiveRanges(); + } + me.callParent(arguments); + me.callObservers('Filter'); + }, + /** + * Removes the model instance(s) at the given index + * @param {Number} index The record index + * @param {Number} [count=1] The number of records to delete + */ + removeAt: function(index, count) { + var data = this.getData(); + // Sanity check input. + index = Math.max(index, 0); + if (index < data.length) { + if (arguments.length === 1) { + count = 1; + } else if (!count) { + return; + } + data.removeAt(index, count); + } + }, + /** + * Removes all unfiltered items from the store. Filtered records will not be removed. + * Individual record `{@link #event-remove}` events are not fired by this method. + * + * @param {Boolean} [silent=false] Pass `true` to prevent the `{@link #event-clear}` event from being fired. + * @return {Ext.data.Model[]} The removed records. + */ + removeAll: function(silent) { + var me = this, + data = me.getData(), + records = data.getRange(); + // We want to remove and mute any events here + if (data.length) { + // Explicit true here, we never want to fire remove events + me.removeIsSilent = true; + me.callObservers('BeforeRemoveAll'); + data.removeAll(); + me.removeIsSilent = false; + if (!silent) { + me.fireEvent('clear', me, records); + me.fireEvent('datachanged', me); + } + me.callObservers('AfterRemoveAll', [ + !!silent + ]); + } + return records; + }, + /** + * Make a set of records be current in the store. This means that unneeded records + * will be removed and new records will be added. + * @param {Ext.data.Model[]} records The records to be current in the store. + * + * @private + */ + setRecords: function(records) { + var count = this.getCount(); + ++this.loadCount; + if (count) { + this.getData().splice(0, count, records); + } else { + this.add(records); + } + }, + /** + * This method is basically the same as the JavaScript Array splice method. + * + * Negative indexes are interpreted starting at the end of the collection. That is, + * a value of -1 indicates the last item, or equivalent to `length - 1`. + * + * @param {Number} index The index at which to add or remove items. + * @param {Number/Object[]} toRemove The number of items to remove or an array of the + * items to remove. + * @param {Object[]} [toAdd] The items to insert at the given `index`. + * @private + */ + splice: function(index, toRemove, toAdd) { + return this.getData().splice(index, toRemove, toAdd); + }, + /** + * @protected + * Called internally when a Proxy has completed a load request + */ + onProxyLoad: function(operation) { + var me = this, + resultSet = operation.getResultSet(), + records = operation.getRecords(), + successful = operation.wasSuccessful(); + if (me.destroyed) { + return; + } + if (resultSet) { + me.totalCount = resultSet.getTotal(); + } + if (successful) { + records = me.processAssociation(records); + me.loadRecords(records, operation.getAddRecords() ? { + addRecords: true + } : undefined); + me.attachSummaryRecord(resultSet); + } else { + me.loading = false; + } + if (me.hasListeners.load) { + me.fireEvent('load', me, records, successful, operation); + } + me.callObservers('AfterLoad', [ + records, + successful, + operation + ]); + }, + onProxyWrite: function(operation) { + if (operation.wasSuccessful()) { + this.attachSummaryRecord(operation.getResultSet()); + } + this.callParent([ + operation + ]); + }, + // private + filterDataSource: function(fn) { + var source = this.getDataSource(), + items = source.items, + len = items.length, + ret = [], + i; + for (i = 0; i < len; i++) { + if (fn.call(source, items[i])) { + ret.push(items[i]); + } + } + return ret; + }, + getNewRecords: function() { + return this.filterDataSource(this.filterNew); + }, + getRejectRecords: function() { + return this.filterDataSource(this.filterRejects); + }, + getUpdatedRecords: function() { + return this.filterDataSource(this.filterUpdated); + }, + /** + * Loads an array of data straight into the Store. + * + * Using this method is great if the data is in the correct format already (e.g. it doesn't need to be + * processed by a reader). If your data requires processing to decode the data structure, use a + * {@link Ext.data.proxy.Memory MemoryProxy} or {@link #loadRawData}. + * + * @param {Ext.data.Model[]/Object[]} data Array of data to load. Any non-model instances will be cast + * into model instances first. + * @param {Boolean} [append=false] `true` to add the records to the existing records in the store, `false` + * to remove the old ones first. + */ + loadData: function(data, append) { + var me = this, + length = data.length, + newData = [], + i; + //make sure each data element is an Ext.data.Model instance + for (i = 0; i < length; i++) { + newData.push(me.createModel(data[i])); + } + newData = me.processAssociation(newData); + me.loadRecords(newData, append ? me.addRecordsOptions : undefined); + }, + /** + * Loads data via the bound Proxy's reader + * + * Use this method if you are attempting to load data and want to utilize the configured data reader. + * + * As of 4.2, this method will no longer fire the {@link #event-load} event. + * + * @param {Object[]} data The full JSON object you'd like to load into the Data store. + * @param {Boolean} [append=false] `true` to add the records to the existing records in the store, `false` + * to remove the old ones first. + * + * @return {Boolean} `true` if the reader processed the records correctly. See {@link Ext.data.reader.Reader#successProperty}. + * If the reader did not process the records, nothing will be added. + */ + loadRawData: function(data, append) { + var me = this, + session = me.getSession(), + result = me.getProxy().getReader().read(data, session ? { + recordCreator: session.recordCreator + } : undefined), + records = result.getRecords(), + success = result.getSuccess(); + if (success) { + me.totalCount = result.getTotal(); + me.loadRecords(records, append ? me.addRecordsOptions : undefined); + } + return success; + }, + /** + * Loads an array of {@link Ext.data.Model model} instances into the store, fires the datachanged event. This should only usually + * be called internally when loading from the {@link Ext.data.proxy.Proxy Proxy}, when adding records manually use {@link #method-add} instead + * @param {Ext.data.Model[]} records The array of records to load + * @param {Object} options + * @param {Boolean} [options.addRecords=false] Pass `true` to add these records to the existing records, `false` to remove the Store's existing records first. + */ + loadRecords: function(records, options) { + var me = this, + length = records.length, + data = me.getData(), + addRecords, i, skipSort; + if (options) { + addRecords = options.addRecords; + } + if (!me.getRemoteSort() && !me.getSortOnLoad()) { + skipSort = true; + data.setAutoSort(false); + } + if (!addRecords) { + me.clearData(true); + } + // Clear the flag AFTER the stores collection has been cleared down so that + // observers of that collection know that it was due to a load, and a refresh is imminent. + me.loading = false; + me.ignoreCollectionAdd = true; + me.callObservers('BeforePopulate'); + data.add(records); + me.ignoreCollectionAdd = false; + if (skipSort) { + data.setAutoSort(true); + } + for (i = 0; i < length; i++) { + records[i].join(me); + } + if (!me.isEmptyStore) { + ++me.loadCount; + me.complete = true; + } + if (me.hasListeners.datachanged) { + me.fireEvent('datachanged', me); + } + if (me.hasListeners.refresh) { + me.fireEvent('refresh', me); + } + me.callObservers('AfterPopulate'); + }, + // PAGING METHODS + /** + * Loads a given 'page' of data by setting the start and limit values appropriately. Internally this just causes a normal + * load operation, passing in calculated 'start' and 'limit' params. + * @param {Number} page The number of the page to load. + * @param {Object} [options] See options for {@link #method-load}. + */ + loadPage: function(page, options) { + var me = this, + size = me.getPageSize(); + me.currentPage = page; + // Copy options into a new object so as not to mutate passed in objects + options = Ext.apply({ + page: page, + start: (page - 1) * size, + limit: size, + addRecords: !me.getClearOnPageLoad() + }, options); + me.read(options); + }, + /** + * Loads the next 'page' in the current data set + * @param {Object} options See options for {@link #method-load} + */ + nextPage: function(options) { + this.loadPage(this.currentPage + 1, options); + }, + /** + * Loads the previous 'page' in the current data set + * @param {Object} options See options for {@link #method-load} + */ + previousPage: function(options) { + this.loadPage(this.currentPage - 1, options); + }, + /** + * @private + */ + clearData: function(isLoad) { + var me = this, + removed = me.removed, + data = me.getDataSource(), + clearRemovedOnLoad = me.getClearRemovedOnLoad(), + needsUnjoinCheck = removed && isLoad && !clearRemovedOnLoad, + records, record, i, len; + // We only have to do the unjoining if not buffered. PageMap will unjoin its records when it clears itself. + // There is a potential for a race condition in stores configured with autoDestroy: true; + // if loading was initiated but didn't complete by the time the store is destroyed, + // the data MC may not have been created yet so we have to check for its existence + // here and below. + if (data) { + records = data.items; + for (i = 0 , len = records.length; i < len; ++i) { + record = records[i]; + if (needsUnjoinCheck && Ext.Array.contains(removed, record)) { + + continue; + } + record.unjoin(me); + } + me.ignoreCollectionRemove = true; + me.callObservers('BeforeClear'); + data.removeAll(); + me.ignoreCollectionRemove = false; + me.callObservers('AfterClear'); + } + if (removed && (!isLoad || clearRemovedOnLoad)) { + removed.length = 0; + } + }, + onIdChanged: function(rec, oldId, newId) { + this.getData().updateKey(rec, oldId); + // This event is used internally + this.fireEvent('idchanged', this, rec, oldId, newId); + }, + /** + * Commits all Records with {@link #getModifiedRecords outstanding changes}. To handle updates for changes, + * subscribe to the Store's {@link #event-update update event}, and perform updating when the third parameter is + * Ext.data.Record.COMMIT. + */ + commitChanges: function() { + var me = this, + recs = me.getModifiedRecords(), + len = recs.length, + i = 0; + Ext.suspendLayouts(); + me.beginUpdate(); + for (; i < len; i++) { + recs[i].commit(); + } + me.cleanRemoved(); + me.endUpdate(); + Ext.resumeLayouts(true); + /** + * @private + * @event commit + * Fired when all changes were committed and the Store is clean. + * + * **Note** Used internally. + * + * @param {Ext.data.Store} store The Store object + */ + me.fireEvent('commit', me); + }, + filterNewOnly: function(item) { + return item.phantom === true; + }, + filterRejects: function(item) { + return item.phantom || item.dirty; + }, + /** + * {@link Ext.data.Model#reject Rejects} outstanding changes on all {@link #getModifiedRecords modified records} + * and re-insert any records that were removed locally. Any phantom records will be removed. + */ + rejectChanges: function() { + var me = this, + recs = me.getRejectRecords(), + len = recs.length, + i, rec, toRemove, sorted, data, currentAutoSort; + Ext.suspendLayouts(); + me.beginUpdate(); + for (i = 0; i < len; i++) { + rec = recs[i]; + if (rec.phantom) { + toRemove = toRemove || []; + toRemove.push(rec); + } else { + rec.reject(); + } + } + if (toRemove) { + me.remove(toRemove); + for (i = 0 , len = toRemove.length; i < len; ++i) { + toRemove[i].reject(); + } + } + // Restore removed records back to their original positions. + recs = me.getRawRemovedRecords(); + if (recs) { + len = recs.length; + sorted = !me.getRemoteSort() && me.isSorted(); + if (sorted) { + // Temporarily turn off sorting so .reject() doesn't attempt to sort the record. + // It would throw b/c the record isn't yet in its collection. + data = me.getData(); + currentAutoSort = data.getAutoSort(); + data.setAutoSort(false); + } + for (i = len - 1; i >= 0; i--) { + rec = recs[i]; + rec.reject(); + if (!sorted) { + me.insert(rec.removedFrom || 0, rec); + } + } + if (sorted) { + // Turn sorting back on so the collection is auto-sorted when added. + data.setAutoSort(currentAutoSort); + me.add(recs); + } + // Don't need to call cleanRemoved because we've re-added everything, don't + // need to unjoin the store + recs.length = 0; + } + me.endUpdate(); + Ext.resumeLayouts(true); + /** + * @private + * @event reject + * Fired when all changes were rejected and the Store is clean. + * + * **Note** Used internally. + * + * @param {Ext.data.Store} store The Store object + */ + me.fireEvent('reject', me); + }, + doDestroy: function() { + var me = this, + task = me.loadTask, + data = me.getData(), + source = data.getSource(); + // clearData ensures everything is unjoined + me.clearData(); + me.setSession(null); + me.observers = null; + if (task) { + task.cancel(); + me.loadTask = null; + } + if (source) { + source.destroy(); + } + me.callParent(); + }, + privates: { + commitOptions: { + commit: true + }, + attachSummaryRecord: function(resultSet) { + if (!resultSet) { + return; + } + var me = this, + summary = resultSet.getSummaryData(), + grouper = me.getGrouper(), + current = me.summaryRecord, + commitOptions = me.commitOptions, + groups, len, i, rec, group; + if (summary) { + if (current) { + current.set(summary.data, commitOptions); + } else { + me.summaryRecord = summary; + summary.isRemote = true; + } + } + if (grouper) { + summary = resultSet.getGroupData(); + if (summary) { + groups = me.getGroups(); + for (i = 0 , len = summary.length; i < len; ++i) { + rec = summary[i]; + group = groups.getItemGroup(rec); + if (group) { + current = group.summaryRecord; + if (current) { + current.set(rec.data, commitOptions); + } else { + group.summaryRecord = rec; + rec.isRemote = true; + } + } + } + } + } + }, + /** + * Similar to a load, however no records are added to the store. This is useful + * in allowing the developer to decide what to do with the new records. + * @param {Object} [options] See {@link #method-load load options}. + * + * @private + */ + fetch: function(options) { + options = Ext.apply({}, options); + this.setLoadOptions(options); + var operation = this.createOperation('read', options); + operation.execute(); + }, + fireChangeEvent: function(record) { + return this.getDataSource().contains(record); + }, + onBeforeLoad: function(operation) { + this.callObservers('BeforeLoad', [ + operation + ]); + }, + onRemoteFilterSet: function(filters, remoteFilter) { + if (filters) { + this.getData().setFilters(remoteFilter ? null : filters); + } + this.callParent([ + filters, + remoteFilter + ]); + }, + onRemoteSortSet: function(sorters, remoteSort) { + var data = this.getData(); + if (sorters) { + data.setSorters(remoteSort ? null : sorters); + } + data.setAutoGroup(!remoteSort); + this.callParent([ + sorters, + remoteSort + ]); + }, + /** + * Checks whether records are being moved within the store. This can be used in conjunction with the + * {@link #event-add} and {@link #event-remove} events to determine whether the records are being removed/added + * or just having the position changed. + * @param {Ext.data.Model[]/Ext.data.Model} [records] The record(s). + * @param {Object} [getMap] (private) + * @return {Number} The number of records being moved. `0` if no records are moving. If records are passed + * the number will refer to how many of the passed records are moving. + * + * @private + */ + isMoving: function(records, getMap) { + var map = this.moveMap, + moving = 0, + len, i; + if (map) { + if (records) { + if (Ext.isArray(records)) { + for (i = 0 , len = records.length; i < len; ++i) { + moving += map[records[i].id] ? 1 : 0; + } + } else if (map[records.id]) { + ++moving; + } + } else { + moving = getMap ? map : this.moveMapCount; + } + } + return moving; + }, + setLoadOptions: function(options) { + // Only add grouping options if grouping is remote + var me = this, + pageSize = me.getPageSize(), + session, grouper; + if (me.getRemoteSort() && !options.grouper) { + grouper = me.getGrouper(); + if (grouper) { + options.grouper = grouper; + } + } + if (pageSize || 'start' in options || 'limit' in options || 'page' in options) { + options.page = options.page != null ? options.page : me.currentPage; + options.start = (options.start !== undefined) ? options.start : (options.page - 1) * pageSize; + options.limit = options.limit != null ? options.limit : pageSize; + me.currentPage = options.page; + } + options.addRecords = options.addRecords || false; + if (!options.recordCreator) { + session = me.getSession(); + if (session) { + options.recordCreator = session.recordCreator; + } + } + me.callParent([ + options + ]); + }, + setMoving: function(records, isMoving) { + var me = this, + map = me.moveMap || (me.moveMap = {}), + len = records.length, + i, id; + for (i = 0; i < len; ++i) { + id = records[i].id; + if (isMoving) { + if (map[id]) { + ++map[id]; + } else { + map[id] = 1; + ++me.moveMapCount; + } + } else { + if (--map[id] === 0) { + delete map[id]; + --me.moveMapCount; + } + } + } + if (me.moveMapCount === 0) { + me.moveMap = null; + } + }, + processAssociation: function(records) { + var me = this, + associatedEntity = me.getAssociatedEntity(); + if (associatedEntity) { + records = me.getRole().processLoad(me, associatedEntity, records, me.getSession()); + } + return records; + } + } +}); +// Provides docs from the mixin +/** + * @method each + * @inheritdoc Ext.data.LocalStore#each + */ +/** + * @method collect + * @inheritdoc Ext.data.LocalStore#collect + */ +/** + * @method getById + * @inheritdoc Ext.data.LocalStore#getById + */ +/** + * @method getByInternalId + * @inheritdoc Ext.data.LocalStore#getByInternalId + */ +/** + * @method indexOf + * @inheritdoc Ext.data.LocalStore#indexOf + */ +/** + * @method indexOfId + * @inheritdoc Ext.data.LocalStore#indexOfId + */ +/** + * @method queryBy + * @inheritdoc Ext.data.LocalStore#queryBy + */ +/** + * @method query + * @inheritdoc Ext.data.LocalStore#query + */ +/** + * @method first + * @inheritdoc Ext.data.LocalStore#first + */ +/** + * @method last + * @inheritdoc Ext.data.LocalStore#last + */ +/** + * @method sum + * @inheritdoc Ext.data.LocalStore#sum + */ +/** + * @method count + * @inheritdoc Ext.data.LocalStore#count + */ +/** + * @method min + * @inheritdoc Ext.data.LocalStore#min + */ +/** + * @method max + * @inheritdoc Ext.data.LocalStore#max + */ +/** + * @method average + * @inheritdoc Ext.data.LocalStore#average + */ +/** + * @method aggregate + * @inheritdoc Ext.data.LocalStore#aggregate + */ + +/** + * Data reader class to create an Array of {@link Ext.data.Model} objects from an Array. + * Each element of that Array represents a row of data fields. The + * fields are pulled into a Record object using as a subscript, the `mapping` property + * of the field definition if it exists, or the field's ordinal position in the definition. + * + * ##Example code: + * + * Employee = Ext.define('Employee', { + * extend: 'Ext.data.Model', + * fields: [ + * 'id', + * {name: 'name', mapping: 1}, // "mapping" only needed if an "id" field is present which + * {name: 'occupation', mapping: 2} // precludes using the ordinal position as the index. + * ] + * }); + * + * var myReader = new Ext.data.reader.Array({ + * model: 'Employee' + * }, Employee); + * + * This would consume an Array like this: + * + * [ [1, 'Bill', 'Gardener'], [2, 'Ben', 'Horticulturalist'] ] + * + */ +Ext.define('Ext.data.reader.Array', { + extend: 'Ext.data.reader.Json', + alternateClassName: 'Ext.data.ArrayReader', + alias: 'reader.array', + // For Array Reader, methods in the base which use these properties must not see the defaults + config: { + /** + * @cfg totalProperty + * @inheritdoc + */ + totalProperty: undefined, + /** + * @cfg successProperty + * @inheritdoc + */ + successProperty: undefined + }, + /** + * @cfg {Boolean} preserveRawData + * @hide + */ + /** + * @method constructor + * @constructor + * Create a new ArrayReader + * @param {Object} meta Metadata configuration options. + */ + createFieldAccessor: function(field) { + // In the absence of a mapping property, use the original ordinal position + // at which the Model inserted the field into its collection. + var oldMap = field.mapping, + index = field.hasMapping() ? oldMap : field.ordinal, + result; + // Temporarily overwrite the mapping and use the superclass method. + field.mapping = index; + result = this.callParent(arguments); + field.mapping = oldMap; + return result; + }, + getModelData: function(raw) { + // Can't preserve raw data here + return {}; + } +}); + +/** + * Small helper class to make creating {@link Ext.data.Store}s from Array data easier. An ArrayStore will be + * automatically configured with a {@link Ext.data.reader.Array}. + * + * A store configuration would be something like: + * + * var store = Ext.create('Ext.data.ArrayStore', { + * // store configs + * storeId: 'myStore', + * // reader configs + * fields: [ + * 'company', + * {name: 'price', type: 'float'}, + * {name: 'change', type: 'float'}, + * {name: 'pctChange', type: 'float'}, + * {name: 'lastChange', type: 'date', dateFormat: 'n/j h:ia'} + * ] + * }); + * + * This store is configured to consume a returned object of the form: + * + * var myData = [ + * ['3m Co',71.72,0.02,0.03,'9/1 12:00am'], + * ['Alcoa Inc',29.01,0.42,1.47,'9/1 12:00am'], + * ['Boeing Co.',75.43,0.53,0.71,'9/1 12:00am'], + * ['Hewlett-Packard Co.',36.53,-0.03,-0.08,'9/1 12:00am'], + * ['Wal-Mart Stores, Inc.',45.45,0.73,1.63,'9/1 12:00am'] + * ]; + * + * An object literal of this form could also be used as the {@link #cfg-data} config option. + */ +Ext.define('Ext.data.ArrayStore', { + extend: 'Ext.data.Store', + alias: 'store.array', + alternateClassName: [ + 'Ext.data.SimpleStore' + ], + requires: [ + 'Ext.data.proxy.Memory', + 'Ext.data.reader.Array' + ], + config: { + proxy: { + type: 'memory', + reader: 'array' + } + }, + loadData: function(data, append) { + if (this.expandData) { + var r = [], + i = 0, + ln = data.length; + for (; i < ln; i++) { + r[r.length] = [ + data[i] + ]; + } + data = r; + } + this.callParent([ + data, + append + ]); + } +}); + +/** + * Contains a collection of all stores that are created that have an identifier. An identifier can be assigned by + * setting the {@link Ext.data.AbstractStore#storeId storeId} property. When a store is in the StoreManager, it can be + * referred to via it's identifier: + * + * Ext.create('Ext.data.Store', { + * model: 'SomeModel', + * storeId: 'myStore' + * }); + * + * var store = Ext.data.StoreManager.lookup('myStore'); + * + * Also note that the {@link #lookup} method is aliased to {@link Ext#getStore} for convenience. + * + * If a store is registered with the StoreManager, you can also refer to the store by it's identifier when registering + * it with any Component that consumes data from a store: + * + * Ext.create('Ext.data.Store', { + * model: 'SomeModel', + * storeId: 'myStore' + * }); + * + * Ext.create('Ext.view.View', { + * store: 'myStore', + * // other configuration here + * }); + * + */ +Ext.define('Ext.data.StoreManager', { + extend: 'Ext.util.MixedCollection', + alternateClassName: [ + 'Ext.StoreMgr', + 'Ext.data.StoreMgr', + 'Ext.StoreManager' + ], + singleton: true, + requires: [ + 'Ext.data.ArrayStore' + ], + /** + * @cfg {Object} listeners + * @private + */ + /** + * Registers one or more Stores with the StoreManager. You do not normally need to register stores manually. Any + * store initialized with a {@link Ext.data.Store#storeId} will be auto-registered. + * @param {Ext.data.Store...} stores Any number of Store instances + */ + register: function() { + for (var i = 0, + s; (s = arguments[i]); i++) { + this.add(s); + } + }, + /** + * Unregisters one or more Stores with the StoreManager + * @param {String/Object...} stores Any number of Store instances or ID-s + */ + unregister: function() { + for (var i = 0, + s; (s = arguments[i]); i++) { + this.remove(this.lookup(s)); + } + }, + /** + * Gets a registered Store by id + * @param {String/Object} store The id of the Store, or a Store instance, or a store configuration + * @param {String} [defaultType] The store type to create when used with store configuration and there + * is no type specified on the config. + * @return {Ext.data.Store} + */ + lookup: function(store, defaultType) { + // handle the case when we are given an array or an array of arrays. + if (Ext.isArray(store)) { + var first = store[0], + data = store, + arrays, fields, i, len; + if (Ext.isObject(first)) { + // store: [ { foo: 42, ... }, { foo: 427, ... }, ... ] + store = { + data: data + }; + } else { + arrays = Ext.isArray(first); + fields = [ + 'field1' + ]; + if (arrays) { + // store: [ [1,2], [3,4], ... ] + for (i = 2 , len = first.length; i <= len; ++i) { + fields.push('field' + i); + } + } else { + // store: [ 1,2,3, ... ] + data = []; + for (i = 0 , len = store.length; i < len; ++i) { + data.push([ + store[i] + ]); + } + } + return new Ext.data.ArrayStore({ + data: data, + fields: fields, + autoDestroy: true, + autoCreated: true, + expanded: !arrays + }); + } + } + if (Ext.isString(store)) { + // store id + return this.get(store); + } else { + // store instance or store config + return Ext.Factory.store(store, defaultType); + } + }, + // getKey implementation for MixedCollection + getKey: function(o) { + return o.storeId; + }, + addEmptyStore: function() { + // A dummy empty store with a fieldless Model defined in it. + // Just for binding to Views which are instantiated with no Store defined. + // They will be able to run and render fine, and be bound to a generated Store later. + var emptyStore = this.$emptyStore, + destoryable = { + destroy: Ext.emptyFn + }; + if (!emptyStore) { + emptyStore = this.$emptyStore = Ext.regStore('ext-empty-store', { + proxy: 'memory', + useModelWarning: false + }); + emptyStore.isEmptyStore = true; + emptyStore.on = emptyStore.addListener = function() { + return destoryable; + }; + emptyStore.un = emptyStore.removeListener = Ext.emptyFn; + emptyStore.add = emptyStore.remove = emptyStore.insert = emptyStore.destroy = emptyStore.loadData = function() { + Ext.raise('Cannot modify ext-empty-store'); + }; + } + this.add(emptyStore); + }, + clear: function() { + this.callParent(); + this.addEmptyStore(); + } +}, function() { + /** + * Creates a new store for the given id and config, then registers it with the {@link Ext.data.StoreManager Store Manager}. + * Sample usage: + * + * Ext.regStore('AllUsers', { + * model: 'User' + * }); + * + * // the store can now easily be used throughout the application + * new Ext.List({ + * store: 'AllUsers', + * ... other config + * }); + * + * @param {String/Object} id The id to set on the new store, or the `config` object + * that contains the `storeId` property. + * @param {Object} config The store config if the first parameter (`id`) is just the + * id. + * @member Ext + * @method regStore + */ + Ext.regStore = function(id, config) { + var store; + if (Ext.isObject(id)) { + config = id; + } else { + if (Ext.data.StoreManager.containsKey(id)) { + return Ext.data.StoreManager.lookup(id); + } + config.storeId = id; + } + if (config instanceof Ext.data.Store) { + store = config; + } else { + store = new Ext.data.Store(config); + } + Ext.data.StoreManager.register(store); + return store; + }; + /** + * @method getStore + * Shortcut to {@link Ext.data.StoreManager#lookup}. + * @member Ext + * @inheritdoc Ext.data.StoreManager#method-lookup + */ + Ext.getStore = function(name) { + return Ext.data.StoreManager.lookup(name); + }; + Ext.data.StoreManager.addEmptyStore(); +}); + +/** + * This class implements the data store event domain. All classes extending from + * {@link Ext.data.AbstractStore} are included in this domain. The selectors are simply + * store id, alias or the wildcard "*" to match any store. + * + * @private + */ +Ext.define('Ext.app.domain.Store', { + extend: 'Ext.app.EventDomain', + singleton: true, + requires: [ + 'Ext.data.AbstractStore' + ], + type: 'store', + prefix: 'store.', + idMatchRe: /^\#/, + constructor: function() { + var me = this; + me.callParent(); + me.monitor(Ext.data.AbstractStore); + }, + match: function(target, selector) { + var result = false, + alias = target.alias; + if (selector === '*') { + result = true; + } else if (this.idMatchRe.test(selector)) { + result = target.getStoreId() === selector.substring(1); + } else if (alias) { + result = Ext.Array.indexOf(alias, this.prefix + selector) > -1; + } + return result; + } +}); + +/** + * Controllers are the glue that binds an application together. That said, their main + * purpose is to listen for events (usually from views) and take some action. Here's how + * we might create a Controller to manage Users: + * + * Ext.define('MyApp.controller.Users', { + * extend: 'Ext.app.Controller', + * + * init: function() { + * console.log('Initialized Users! This happens before ' + + * 'the Application launch() function is called'); + * } + * }); + * + * The init function is a special method that is called when your application boots. It is + * called before the {@link Ext.app.Application Application}'s launch function is executed. + * This creates an area you can run code prior to Viewport creation. + * + * The controller's {@link #method-control} function + * makes it easy to listen to events on your view classes and take some action with a + * handler function. Let's update our Users controller to tell us when the panel is + * rendered: + * + * Ext.define('MyApp.controller.Users', { + * extend: 'Ext.app.Controller', + * + * control: { + * 'viewport > panel': { + * render: 'onPanelRendered' + * } + * } + * + * onPanelRendered: function() { + * console.log('The panel was rendered'); + * } + * }); + * + * The {@link Ext.app.BaseController#method-control control method} has now set up + * listeners on views in our application. The control method uses the ComponentQuery + * engine to quickly and easily get references to components on the page. If you are not + * familiar with ComponentQuery yet, be sure to check out the + * {@link Ext.ComponentQuery documentation}. In brief, it allows us to pass a + * CSS-like selector that will find every matching component on the page. + * + * In our init function above, we supplied 'viewport > panel', which translates to "find me + * every Panel that is a direct child of a Viewport". We then supplied an object that maps + * event names (just 'render' in this case) to handler functions. In short, whenever + * a component that matches our selector fires a 'render' event, our + * onPanelRendered function is called. + * + * ## Event domains + * + * In Ext JS 4.2, we introduced the concept of event domains. In terms of MVC, an event + * domain is one or more base classes that fire events to which a Controller wants to + * listen. Besides Component event domain that encompass {@link Ext.Component}-descended + * Views, Controllers now can listen to events from data Stores, Ext Direct Providers, + * other Controllers, and Ext.GlobalEvents. This feature provides a way to communicate + * between parts of the whole application without the need to bind controllers together + * tightly, and allows to develop and test application parts in isolation. + * + * See usage examples in {@link #method-listen} method documentation. + * + * ## Using refs + * + * One of the most useful parts of Controllers is the ref system. These use + * {@link Ext.ComponentQuery} to make it really easy to get references to Views on your + * page. Let's look at an example of this now: + * + * Ext.define('MyApp.controller.Users', { + * extend: 'Ext.app.Controller', + * + * refs: [{ + * ref: 'list', + * selector: 'grid' + * }], + * + * control: { + * 'button': { + * click: 'refreshGrid' + * } + * }, + * + * refreshGrid: function() { + * this.getList().store.load(); + * } + * }); + * + * This example assumes the existence of a {@link Ext.grid.Panel Grid} on the page, which + * contains a single button to refresh the Grid when clicked. In our refs array, we set up + * a reference to the grid. There are two parts to this - the 'selector', which is a + * {@link Ext.ComponentQuery ComponentQuery} selector which finds any grid on the page and + * assigns it to the reference 'list'. + * + * By giving the reference a name, we get a number of things for free. The first is the + * getList function that we use in the refreshGrid method above. This is generated + * automatically by the Controller based on the name of our ref, which was capitalized and + * prepended with get to go from 'list' to 'getList'. + * + * The way this works is that the first time getList is called by your code, the + * ComponentQuery selector is run and the first component that matches the selector + * ('grid' in this case) will be returned. All future calls to getList will use a cached + * reference to that grid. Usually it is advised to use a specific ComponentQuery selector + * that will only match a single View in your application (in the case above our selector + * will match any grid on the page). + * + * Bringing it all together, we configure control + * to listen to any click on a {@link Ext.button.Button button} and call our refreshGrid + * function (again, this will match any button on the page so we advise a more specific + * selector than just 'button', but have left it this way for simplicity). When the button + * is clicked we use out getList function to refresh the grid. + * + * You can create any number of refs and control any number of components this way, simply + * adding more functions to your Controller as you go. For an example of real-world usage + * of Controllers see the Feed Viewer example in the examples/app/feed-viewer folder in + * the SDK download. + * + * ## Generated getter methods + * + * Refs aren't the only thing that generate convenient getter methods. Controllers often + * have to deal with Models and Stores so the framework offers a couple of easy ways to + * get access to those too. Let's look at another example: + * + * Ext.define('MyApp.controller.Users', { + * extend: 'Ext.app.Controller', + * + * models: ['User'], + * stores: ['AllUsers', 'AdminUsers'], + * + * init: function() { + * var User, allUsers, ed; + * + * User = this.getUserModel(); + * allUsers = this.getAllUsersStore(); + * + * ed = new User({ name: 'Ed' }); + * allUsers.add(ed); + * } + * }); + * + * By specifying Models and Stores that the Controller cares about, it again dynamically + * loads them from the appropriate locations (app/model/User.js, app/store/AllUsers.js and + * app/store/AdminUsers.js in this case) and creates getter functions for them all. The + * example above will create a new User model instance and add it to the AllUsers Store. + * Of course, you could do anything in this function but in this case we just did + * something simple to demonstrate the functionality. + * + * ## Further Reading + * + * For more information about writing Ext JS 5 applications, please see the + * [Application Architecture](../../../application_architecture/application_architecture.html). + * Also see the {@link Ext.app.Application} documentation. + */ +Ext.define('Ext.app.Controller', { + extend: 'Ext.app.BaseController', + requires: [ + 'Ext.app.Util', + 'Ext.data.StoreManager', + 'Ext.ComponentManager', + 'Ext.app.domain.Component', + 'Ext.app.domain.Store' + ], + statics: { + strings: { + model: { + getter: 'getModel', + upper: 'Model' + }, + view: { + getter: 'getView', + upper: 'View' + }, + controller: { + getter: 'getController', + upper: 'Controller' + }, + store: { + getter: 'getStore', + upper: 'Store' + }, + profile: { + getter: 'getProfile', + upper: 'Profiles' + } + }, + controllerRegex: /^(.*)\.controller\./, + profileRegex: /^(.*)\.profile\./, + createGetter: function(baseGetter, name) { + return function() { + return this[baseGetter](name); + }; + }, + getGetterName: function(name, kindUpper) { + var fn = 'get', + parts = name.split('.'), + numParts = parts.length, + index; + // Handle namespaced class names. E.g. feed.Add becomes getFeedAddView etc. + for (index = 0; index < numParts; index++) { + fn += Ext.String.capitalize(parts[index]); + } + fn += kindUpper; + return fn; + }, + resolveNamespace: function(cls, data) { + var Controller = Ext.app.Controller, + namespaceRe = cls.prototype.isProfile ? Controller.profileRegex : Controller.controllerRegex, + className, namespace, match; + /* + * Namespace resolution is tricky business: we should know what namespace + * this Controller descendant belongs to, or model/store/view dependency + * resolution will be either ambiguous or plainly not possible. To avoid + * guessing games we try to look for a forward hint ($namespace) that + * Application class sets when its onClassExtended gets processed; if that + * fails we try to deduce namespace from class name. + * + * Note that for Ext.app.Application, Controller.onClassExtended gets executed + * *before* Application.onClassExtended so we have to delay namespace handling + * until after Application.onClassExtended kicks in, hence it is done in this hook. + */ + className = Ext.getClassName(cls); + namespace = data.$namespace || data.namespace || Ext.app.getNamespace(className) || ((match = namespaceRe.exec(className)) && match[1]); + if (!namespace) { + Ext.log.warn("Missing namespace for " + className + ", please define it " + "in namespaces property of your Application class."); + } + return namespace; + }, + /** + * This method is called like so: + * + * Ext.app.Controller.processDependencies(proto, requiresArray, 'MyApp', 'model', [ + * 'User', + * 'Item', + * 'Foo@Common.model', + * 'Bar.Baz@Common.model' + * ]); + * + * Required dependencies are added to requiresArray. + * + * @private + */ + processDependencies: function(cls, requires, namespace, kind, names, profileName) { + if (!names || !names.length) { + return; + } + var me = this, + strings = me.strings[kind], + o, absoluteName, shortName, name, j, subLn, getterName, getter; + if (!Ext.isArray(names)) { + names = [ + names + ]; + } + for (j = 0 , subLn = names.length; j < subLn; j++) { + name = names[j]; + o = me.getFullName(name, kind, namespace, profileName); + // Update the name in the array to be the absolute name + names[j] = absoluteName = o.absoluteName; + shortName = o.shortName; + requires.push(absoluteName); + getterName = me.getGetterName(shortName, strings.upper); + if (!cls[getterName]) { + cls[getterName] = getter = me.createGetter(strings.getter, name); + } else if (getterName === 'getMainView') { + Ext.log.warn('Cannot have a view named \'Main\' - getter conflicts with mainView config.'); + } + // Application class will init the controller getters + if (getter && kind !== 'controller') { + // This marker allows the constructor to easily/cheaply identify the + // generated getter methods since they all need to be called to get + // things initialized. We use a property name that deliberately does + // not work with dot-access to reduce any chance of collision. + getter['Ext.app.getter'] = true; + } + } + }, + getFullName: function(name, kind, namespace, profileName) { + var shortName = name, + sep, absoluteName; + if ((sep = name.indexOf('@')) > 0) { + // The unambiguous syntax is Model@Name.space (or "space.Model@Name") + // which contains both the short name ("Model" or "space.Model") and + // the full name (Name.space.Model). + // + shortName = name.substring(0, sep); + // "Model" + absoluteName = name.substring(sep + 1) + '.' + shortName; + } + // ex: "Name.space.Model" + // Deciding if a class name must be qualified: + // + // 1 - if the name doesn't contain a dot, we must qualify it + // + // 2 - the name may be a qualified name of a known class, but: + // + // 2.1 - in runtime, the loader may not know the class - specially in + // production - so we must check the class manager + // + // 2.2 - in build time, the class manager may not know the class, but + // the loader does, so we check the second one (the loader check + // assures it's really a class, and not a namespace, so we can + // have 'Books.controller.Books', and requesting a controller + // called Books will not be underqualified) + // + else if (name.indexOf('.') > 0 && (Ext.ClassManager.isCreated(name) || this.hasRegisteredPrefix(name))) { + absoluteName = name; + shortName = name.replace(namespace + '.' + kind + '.', ''); + } else { + if (!namespace) { + Ext.log.warn("Cannot find namespace for " + kind + " " + name + ", " + "assuming it is fully qualified class name"); + } + if (namespace) { + absoluteName = namespace + '.' + kind + '.' + (profileName ? profileName + '.' + name : name); + shortName = name; + } else { + absoluteName = name; + } + } + return { + absoluteName: absoluteName, + shortName: shortName + }; + }, + hasRegisteredPrefix: function(className) { + var inventory = Ext.ClassManager, + prefix = inventory.getPrefix(className); + // It's a class if className is not equal to any known namespace + return prefix && prefix !== className; + } + }, + // @cmd-auto-dependency {aliasPrefix : "model.", mvc : true, blame: "all"} + /** + * @cfg {String/String[]} models + * Array of models to require from AppName.model namespace. For example: + * + * Ext.define("MyApp.controller.Foo", { + * extend: "Ext.app.Controller", + * models: ['User', 'Vehicle'] + * }); + * + * This is equivalent to: + * + * Ext.define("MyApp.controller.Foo", { + * extend: "Ext.app.Controller", + * requires: ['MyApp.model.User', 'MyApp.model.Vehicle'], + * + * getUserModel: function() { + * return this.getModel("User"); + * }, + * + * getVehicleModel: function() { + * return this.getModel("Vehicle"); + * } + * }); + * + * **Note:** If the model has a different namespace than that of the + * application you will need to specify the full class name as well as define a path + * in the {@link Ext.Loader#cfg-paths Loader's paths} config or + * {@link Ext.Loader#method-setPath setPath} method. + */ + models: null, + // @cmd-auto-dependency {aliasPrefix: "view.", mvc: true, blame: "all"} + /** + * @cfg {String/String[]} views + * Array of views to require from AppName.view namespace and to generate getter methods for. + * For example: + * + * Ext.define("MyApp.controller.Foo", { + * extend: "Ext.app.Controller", + * views: ['List', 'Detail'] + * }); + * + * This is equivalent to: + * + * Ext.define("MyApp.controller.Foo", { + * extend: "Ext.app.Controller", + * requires: ['MyApp.view.List', 'MyApp.view.Detail'], + * + * getListView: function() { + * return this.getView("List"); + * }, + * + * getDetailView: function() { + * return this.getView("Detail"); + * } + * }); + * + * **Note:** If the view has a different namespace than that of the + * application you will need to specify the full class name as well as define a path + * in the {@link Ext.Loader#cfg-paths Loader's paths} config or + * {@link Ext.Loader#method-setPath setPath} method. + */ + views: null, + // @cmd-auto-dependency {aliasPrefix: "store.", mvc: true, blame: "all"} + /** + * @cfg {String/String[]} stores + * Array of stores to require from AppName.store namespace and to generate getter methods for. + * For example: + * + * Ext.define("MyApp.controller.Foo", { + * extend: "Ext.app.Controller", + * stores: ['Users', 'Vehicles'] + * }); + * + * This is equivalent to: + * + * Ext.define("MyApp.controller.Foo", { + * extend: "Ext.app.Controller", + * + * requires: [ + * 'MyApp.store.Users', + * 'MyApp.store.Vehicles' + * ] + * + * getUsersStore: function() { + * return this.getStore("Users"); + * }, + * + * getVehiclesStore: function() { + * return this.getStore("Vehicles"); + * } + * }); + * + * **Note:** If the store has a different namespace than that of the + * application you will need to specify the full class name as well as define a path + * in the {@link Ext.Loader#cfg-paths Loader's paths} config or + * {@link Ext.Loader#method-setPath setPath} method. + */ + stores: null, + // @cmd-auto-dependency {aliasPrefix: "controller.", mvc: true, blame: "all"} + controllers: null, + config: { + /** + * @cfg {Ext.app.Application} application + * The {@link Ext.app.Application} for this controller accessible via the + * getApplication method. + * @accessor + * @readonly + */ + application: null, + /** + * @cfg {Object/Object[]} refs + * @accessor + * + * The refs config creates a getter method on the controller that internally + * uses Ext.ComponentQuery to fetch the component instance using the configured + * selector. The following example will add the `getList` method to + * the controller and will return the first component in the application + * hierarchy with an xtype of "grid". By default, *undefined* will be returned + * when the query does not locate the target component. + * + * Ext.define('MyApp.controller.Foo', { + * extend: 'Ext.app.Controller', + * + * refs: [{ + * ref: 'list', + * selector: 'grid' + * }] + * }); + * + * The following fields may be used in the ref definition: + * + * - `ref` - name of the reference. + * - `selector` - Ext.ComponentQuery selector to access the component. + * - `autoCreate` - True to create the component automatically if not found on + * page. + * - `forceCreate` - True to force the creation of the component every time + * reference is accessed (when `get` is called). + * - `xtype` - Used to create the component by its xtype with `autoCreate` or + * `forceCreate`. If you don't provide `xtype`, an Ext.Component instance will + * be created. + * + * The following example will create a `getList` and `getUser` method on the + * controller. + * + * Ext.define('MyApp.controller.Foo', { + * extend: 'Ext.app.Controller', + * + * refs: [{ + * list: 'grid', + * user: { + * autoCreate: true, + * selector: 'form', + * xtype: 'form' + * } + * }] + * }); + */ + refs: null, + active: true, + /** + * @private + */ + moduleClassName: null + }, + onClassExtended: function(cls, data, hooks) { + var onBeforeClassCreated = hooks.onBeforeCreated; + hooks.onBeforeCreated = function(cls, data) { + var Controller = Ext.app.Controller, + requires = [], + namespace, proto; + proto = cls.prototype; + namespace = Controller.resolveNamespace(cls, data); + if (namespace) { + proto.$namespace = namespace; + } + Controller.processDependencies(proto, requires, namespace, 'model', data.models); + Controller.processDependencies(proto, requires, namespace, 'view', data.views); + Controller.processDependencies(proto, requires, namespace, 'store', data.stores); + Controller.processDependencies(proto, requires, namespace, 'controller', data.controllers); + Ext.require(requires, Ext.Function.pass(onBeforeClassCreated, arguments, this)); + }; + }, + /** + * Creates new Controller. + * + * @param {Object} [config] Configuration object. + */ + constructor: function(config) { + this.initAutoGetters(); + this.callParent([ + config + ]); + }, + /** + * @private + * Takes either an object and transforms it into an array. The following are valid + * refs values: + * + * refs: { + * myComponent: 'container' + * } + * + * refs: { + * myComponent: { + * selector: 'container' + * } + * } + * + * refs: [ + * { + * ref: 'myComponent', + * selector: 'container' + * } + * ] + * + * @param {Array|Object} refs The refs to normalize + * @return {Array} The normalized array of refs + */ + normalizeRefs: function(refs) { + var me = this, + newRefs = []; + if (refs) { + if (Ext.isObject(refs)) { + Ext.Object.each(refs, function(key, value) { + if (Ext.isString(value)) { + value = { + selector: value + }; + } + value.ref = key; + newRefs.push(value); + }); + } else if (Ext.isArray(refs)) { + newRefs = Ext.Array.merge(newRefs, refs); + } + } + refs = me.refs; + if (refs) { + me.refs = null; + refs = me.normalizeRefs(refs); + if (refs) { + newRefs = Ext.Array.merge(newRefs, refs); + } + } + return newRefs; + }, + /** + * Returns a map of reference names to selectors + * @private + */ + getRefMap: function() { + var me = this, + refMap = me._refMap, + refs, ref, ln, i; + if (!refMap) { + refs = me.getRefs(); + refMap = me._refMap = {}; + if (refs) { + for (i = 0 , ln = refs.length; i < ln; i++) { + ref = refs[i]; + refMap[ref.ref] = ref.selector; + } + } + } + return refMap; + }, + applyId: function(id) { + return id || Ext.app.Controller.getFullName(this.$className, 'controller', this.$namespace).shortName; + }, + applyRefs: function(refs) { + return this.normalizeRefs(Ext.clone(refs)); + }, + /** + * @param {Object} refs The refs to pass to the {@link #ref} method. + * @private + */ + updateRefs: function(refs) { + if (refs) { + this.ref(refs); + } + }, + initAutoGetters: function() { + var proto = this.self.prototype, + prop, fn; + for (prop in proto) { + fn = proto[prop]; + // Look for the marker placed on the getters by processDependencies so that + // we can know what to call cheaply: + if (fn && fn['Ext.app.getter']) { + fn.call(this); + } + } + }, + doInit: function(app) { + var me = this; + if (!me._initialized) { + me.init(app); + me._initialized = true; + } + }, + finishInit: function(app) { + var me = this, + controllers = me.controllers, + controller, i, l; + if (me._initialized && controllers && controllers.length) { + for (i = 0 , l = controllers.length; i < l; i++) { + controller = me.getController(controllers[i]); + controller.finishInit(app); + } + } + }, + /** + * @method + * + * A template method that is called when your application boots. It is called before the + * {@link Ext.app.Application Application}'s launch function is executed so gives a hook point + * to run any code before your Viewport is created. + * + * @param {Ext.app.Application} application + * + * @template + */ + init: Ext.emptyFn, + /** + * @method + * + * A template method like {@link #init}, but called after the viewport is created. + * This is called after the {@link Ext.app.Application#launch launch} method of Application + * is executed. + * + * @param {Ext.app.Application} application + * + * @template + */ + onLaunch: Ext.emptyFn, + /** + * Allow the controller to resume receiving events from the event bus. + * Routes will also be able to begin firing on this controller. + * Also see {@link #deactivate}. + */ + activate: function() { + this.setActive(true); + }, + /** + * Prevent this controller from receiving events from the event bus. + * Routes will also not be triggered on inactive controllers unless + * the {@link Ext.route.Route#allowInactive} flag is set. + * Also see {@link #activate}. + */ + deactivate: function() { + this.setActive(false); + }, + /** + * Checks if this controller is active. See {@link #activate} & + * {@link #deactivate}. + * @return {Boolean} `true` if this controller is active. + */ + isActive: function() { + return this.getActive(); + }, + ref: function(refs) { + var me = this, + i = 0, + length = refs.length, + info, ref, fn; + refs = Ext.Array.from(refs); + me.references = me.references || []; + for (; i < length; i++) { + info = refs[i]; + ref = info.ref; + fn = 'get' + Ext.String.capitalize(ref); + if (!me[fn]) { + me[fn] = Ext.Function.pass(me.getRef, [ + ref, + info + ], me); + } + me.references.push(ref.toLowerCase()); + } + }, + /** + * Registers one or more {@link #refs references}. + * + * @param {Object/Object[]} refs + */ + addRef: function(refs) { + this.ref(refs); + }, + getRef: function(ref, info, config) { + var me = this, + refCache = me.refCache || (me.refCache = {}), + cached = refCache[ref]; + info = info || {}; + config = config || {}; + Ext.apply(info, config); + if (info.forceCreate) { + return Ext.ComponentManager.create(info, 'component'); + } + if (!cached) { + if (info.selector) { + refCache[ref] = cached = Ext.ComponentQuery.query(info.selector)[0]; + } + if (!cached && info.autoCreate) { + refCache[ref] = cached = Ext.ComponentManager.create(info, 'component'); + } + if (cached) { + cached.on('destroy', function() { + refCache[ref] = null; + }); + } + } + return cached; + }, + /** + * Returns `true` if a {@link #refs reference} is registered. + * + * @param {String} ref The name of the ref to check for. + * @return {Boolean} + */ + hasRef: function(ref) { + var references = this.references; + return references && Ext.Array.indexOf(references, ref.toLowerCase()) !== -1; + }, + /** + * Returns instance of a {@link Ext.app.Controller Controller} with the given id. + * When controller doesn't exist yet, it's created. Note that this method depends + * on Application instance and will return undefined when Application is not + * accessible. The only exception is when this Controller instance's id is requested; + * in that case we always return the instance even if Application is no available. + * + * @param {String} id + * + * @return {Ext.app.Controller} controller instance or undefined. + */ + getController: function(id) { + var app = this.getApplication(); + if (id === this.getId()) { + return this; + } + return app && app.getController(id); + }, + /** + * Returns instance of a {@link Ext.data.Store Store} with the given name. + * When store doesn't exist yet, it's created. + * + * @param {String} name + * + * @return {Ext.data.Store} a store instance. + */ + getStore: function(name) { + var storeId, store; + storeId = (name.indexOf('@') === -1) ? name : name.split('@')[0]; + store = Ext.StoreManager.get(storeId); + if (!store) { + name = Ext.app.Controller.getFullName(name, 'store', this.$namespace); + if (name) { + store = Ext.create(name.absoluteName, { + // Use id here. If the store has a configured storeId, + // that will take precedence + id: storeId + }); + } + } + return store; + }, + /** + * Returns a {@link Ext.data.Model Model} class with the given name. + * + * @param {String} modelName + * @return {Ext.Class} A class ultimately derived from `Ext.data.Model`. + */ + getModel: function(modelName) { + var name = Ext.app.Controller.getFullName(modelName, 'model', this.$namespace), + ret = Ext.ClassManager.get(name.absoluteName); + if (!ret) { + ret = Ext.data.schema.Schema.lookupEntity(modelName); + } + return ret; + }, + /** + * Returns instance of a {@link Ext.app.Profile Profile} with the given name. + * + * @param {String} name + * + * @return {String} a profile instance. + */ + getProfile: function(name) { + name = Ext.app.Controller.getFullName(name, 'profile', this.$namespace); + return name; + }, + /** + * Returns a View class with the given name. To create an instance of the view, + * you can use it like it's used by Application to create the Viewport: + * + * this.getView('Viewport').create(); + * + * @param {String} view + * + * @return {Ext.Base} a view class. + */ + getView: function(view) { + var name = Ext.app.Controller.getFullName(view, 'view', this.$namespace); + return name && Ext.ClassManager.get(name.absoluteName); + }, + /** + * @method destroy + * @inheritdoc + * @param destroyRefs (private) + * @param fromApp (private) + */ + destroy: function(destroyRefs, fromApp) { + var me = this, + app = me.application, + refCache, ref; + if (!fromApp && app) { + app.unregister(me); + } + me.application = null; + if (destroyRefs) { + // Possible destroy stores here too? + refCache = me.refCache; + for (ref in refCache) { + if (refCache.hasOwnProperty(ref)) { + Ext.destroy(refCache[ref]); + } + } + } + me.callParent(); + } +}); + +/** + * Represents an Ext JS application, which is typically a single page app using a + * {@link Ext.container.Viewport Viewport}. + * + * An application consists of one or more Views. The behavior of a View is managed by its + * corresponding {@link Ext.app.ViewController ViewController} and {@link Ext.app.ViewModel + * ViewModel}. + * + * Global activities are coordinated by {@link Ext.app.Controller Controllers} which are + * ultimately instantiated by an instance of this (or a derived) class. + * + * Ext.application({ + * name: 'MyApp', + * + * // The name of the initial view to create. With the classic toolkit this class + * // will gain a "viewport" plugin if it does not extend Ext.Viewport. With the + * // modern toolkit, the main view will be added to the Viewport. + * // + * //mainView: 'Main.view.main.Main' + * }); + * + * This does several things. First it creates a global variable called 'MyApp' - all of + * your Application's classes (such as its Models, Views and Controllers) will reside under + * this single namespace, which drastically lowers the chances of colliding global variables. + * + * The MyApp global will also have a getApplication method to get a reference to the current + * application: + * + * var app = MyApp.getApplication(); + * + * # Telling Application about the rest of the app + * + * Because an Ext.app.Application represents an entire app, we should tell it about the other + * parts of the app - namely the Models, Views and Controllers that are bundled with the application. Let's say we have + * a blog management app; we might have Models and Controllers for Posts and Comments, and Views for listing, + * adding and editing Posts and Comments. Here's how we'd tell our Application about all these things: + * + * Ext.application({ + * name: 'Blog', + * + * models: ['Post', 'Comment'], + * + * controllers: ['Posts', 'Comments'], + * + * launch: function() { + * ... + * } + * }); + * + * Note that we didn't actually list the Views directly in the Application itself. This is because Views are managed by + * Controllers, so it makes sense to keep those dependencies there. The Application will load each of the specified + * Controllers using the pathing conventions laid out in the + * [application architecture guide](../guides/application_architecture/application_architecture.html) - in this case + * expecting the controllers to reside in app/controller/Posts.js and app/controller/Comments.js. In turn, each + * Controller simply needs to list the Views it uses and they will be automatically loaded. Here's how our Posts + * controller like be defined: + * + * Ext.define('MyApp.controller.Posts', { + * extend: 'Ext.app.Controller', + * views: ['posts.List', 'posts.Edit'], + * + * //the rest of the Controller here + * }); + * + * Because we told our Application about our Models and Controllers, and our Controllers about their Views, Ext JS will + * automatically load all of our app files for us. This means we don't have to manually add script tags into our html + * files whenever we add a new class, but more importantly it enables us to create a minimized build of our entire + * application using Sencha Cmd. + * + * # Deriving from Ext.app.Application + * + * Typically, applications do not derive directly from Ext.app.Application. Rather, the + * configuration passed to `Ext.application` mimics what you might do in a derived class. + * In some cases, however, it can be desirable to share logic by using a derived class + * from `Ext.app.Application`. + * + * Derivation works as you would expect, but using the derived class should still be the + * job of the `Ext.application` method. + * + * Ext.define('MyApp.Application', { + * extend: 'Ext.app.Application', + * name: 'MyApp', + * ... + * }); + * + * Ext.application('MyApp.Application'); + * + * For more information about writing Ext JS applications, please see + * the [application architecture guide](../guides/application_architecture/application_architecture.html). + */ +Ext.define('Ext.app.Application', { + extend: 'Ext.app.Controller', + requires: [ + 'Ext.util.History', + 'Ext.util.MixedCollection' + ], + isApplication: true, + /** + * @cfg {String} extend A class name to use with the `Ext.application` call. The class must also extend {@link Ext.app.Application}. + * + * Ext.define('MyApp.Application', { + * extend: 'Ext.app.Application', + * + * launch: function() { + * Ext.direct.Manager.addProvider(Ext.REMOTING_API); + * } + * }); + * + * Ext.application({ + * extend: 'MyApp.Application' + * }); + */ + /** + * @cfg {String/String[]} controllers + * Names of {@link Ext.app.Controller controllers} that the app uses. By default, + * the framework will look for the controllers in the "controller" folder within the + * {@link #appFolder}. Controller classes should be named using the syntax of + * "{appName}.controller.{ClassName}" with additional sub-folders under the + * "controller" folder specified within the class name following "controller.". + * + * // by default, the following controller class would be located at: + * // app/controller/Main.js + * controllers: '.Main' // or 'MyApp.controller.Main' + * + * // while the following would be located at: + * // app/controller/customer/Main.js + * controllers: 'customer.Main' // or 'MyApp.controller.customer.Main' + * + * **Note:** If the controller has a different namespace than that of the + * application you will need to specify the full class name as well as define a path + * in the {@link Ext.Loader#cfg-paths Loader's paths} config or + * {@link Ext.Loader#method-setPath setPath} method. + */ + /** + * @cfg {Object} scope + * The scope to execute the {@link #launch} function in. Defaults to the Application instance. + */ + scope: undefined, + /** + * @cfg {String/String[]} [namespaces] + * + * The list of namespace prefixes used in the application to resolve dependencies + * like Views and Stores: + * + * Ext.application({ + * name: 'MyApp', + * + * namespaces: ['Common.code'], + * + * controllers: [ 'Common.code.controller.Foo', 'Bar' ] + * }); + * + * Ext.define('Common.code.controller.Foo', { + * extend: 'Ext.app.Controller', + * + * models: ['Foo'], // Loads Common.code.model.Foo + * views: ['Bar'] // Loads Common.code.view.Bar + * }); + * + * Ext.define('MyApp.controller.Bar', { + * extend: 'Ext.app.Controller', + * + * models: ['Foo'], // Loads MyApp.model.Foo + * views: ['Bar'] // Loads MyApp.view.Bar + * }); + * + * You don't need to include main namespace (MyApp), it will be added to the list + * automatically. + */ + namespaces: [], + /** + * @cfg {Object} paths + * Additional load paths to add to Ext.Loader. + * See {@link Ext.Loader#paths} config for more details. + */ + paths: null, + /** + * @cfg {String} [appFolder="app"] + * The path to the directory which contains all application's classes. + * This path will be registered via {@link Ext.Loader#setPath} for the namespace specified + * in the {@link #name name} config. + */ + // NOTE - this config has to be processed by Ext.application + config: { + /** + * @cfg {String} name + * The name of your application. This will also be the namespace for your views, controllers + * models and stores. Don't use spaces or special characters in the name. **Application name + * is mandatory**. + */ + name: '', + /** + * @cfg {String} appProperty + * The name of a property to be assigned to the main namespace to gain a reference to + * this application. Can be set to an empty value to prevent the reference from + * being created + * + * Ext.application({ + * name: 'MyApp', + * appProperty: 'myProp', + * + * launch: function() { + * console.log(MyApp.myProp === this); + * } + * }); + */ + appProperty: 'app', + // @cmd-auto-dependency { aliasPrefix: "profile.", mvc: true, blame: "all" } + /** + * @cfg {String/String[]} profiles + * Names of the profiles that the app uses. + */ + profiles: [], + /** + * @cfg {Ext.app.Profile} + */ + currentProfile: null, + // @cmd-auto-dependency {aliasPrefix: "view.", mvc: true, blame: "all"} + /** + * @cfg {String/Object/Ext.Component} mainView + * The application class to be used as the main viewport view for the + * application. The view will be configured with the + * {@link Ext.plugin.Viewport viewport plugin} to ensure the view takes up all + * available space in the browser viewport. The main view will be created after + * the application's {@link #init} method is called and before the + * {@link #launch} method. The main view should be an application class type and + * not a class from the framework. + * + * The main view value may be: + * - string representing the full class name of the main view or the partial class name following "AppName.view." (provided your main view class follows that convention). + * - config object for the main view + * - main view class instance + * + * Ext.define('MyApp.view.main.Main', { + * extend: 'Ext.panel.Panel', + * xtype: 'mainview', + * title: 'Main Viewport View' + * }); + * + * Ext.application({ + * name : 'MyApp', + * + * mainView: 'MyApp.view.main.Main' + * // mainView: 'main.Main' + * // mainView: new MyApp.view.main.Main() + * // mainView: { xtype: 'mainview' } + * }); + * + * **Note:** You may also call {@link #setMainView} at runtime if you require + * logic within the application's {@link #launch} method to be processed prior to + * the creation of the main view. + */ + mainView: { + $value: null, + lazy: true + }, + /** + * @cfg {String} [defaultToken=null] The default token to be used at application launch + * if one is not present. Often this is set to something like `'home'`. + */ + defaultToken: null, + /** + * @cfg {String} glyphFontFamily + * The glyphFontFamily to use for this application. Used as the default font-family + * for all components that support a `glyph` config. + */ + glyphFontFamily: null, + // Docs will go in subclasses + quickTips: true, + /** + * @cfg {Object} router + * A configuration object to apply onto the {@link Ext.route.Router Router}. + * @since 6.5.0 + */ + router: null + }, + onClassExtended: function(cls, data, hooks) { + var Controller = Ext.app.Controller, + proto = cls.prototype, + requires = [], + onBeforeClassCreated, paths, namespace, ns; + // Ordinary inheritance does not work here so we collect + // necessary data from current class data and its superclass + namespace = data.name || cls.superclass.name; + if (namespace) { + data.$namespace = namespace; + Ext.app.addNamespaces(namespace); + } + if (data.namespaces) { + Ext.app.addNamespaces(data.namespaces); + } + if (data['paths processed']) { + delete data['paths processed']; + } else { + Ext.app.setupPaths(namespace, ('appFolder' in data) ? data.appFolder : cls.superclass.appFolder, data.paths); + } + // Require all profiles + Controller.processDependencies(proto, requires, namespace, 'profile', data.profiles); + // This hook is used in the classic toolkit to process other configs that need to + // require classes (like tooltips and viewport plugin). + proto.getDependencies(cls, data, requires); + // Any "requires" also have to be processed before we fire up the App instance. + if (requires.length) { + onBeforeClassCreated = hooks.onBeforeCreated; + hooks.onBeforeCreated = function(cls, data) { + var args = Ext.Array.clone(arguments); + // This hook is to allow unit tests to come in and control the + // requires so we don't have to get into the internals of the Loader. + // Not intended to be used for any other purpose. + if (data.__handleRequires) { + data.__handleRequires.call(this, requires, Ext.bind(function() { + return onBeforeClassCreated.apply(this, args); + }, this)); + return; + } + Ext.require(requires, function() { + return onBeforeClassCreated.apply(this, args); + }); + }; + } + }, + getDependencies: Ext.emptyFn, + /** + * Creates new Application. + * @param {Object} [config] Config object. + */ + constructor: function(config) { + var me = this; + Ext.route.Router.application = me; + me.callParent([ + config + ]); + if (Ext.isEmpty(me.getName())) { + Ext.raise("[Ext.app.Application] Name property is required"); + } + me.doInit(me); + Ext.on('appupdate', me.onAppUpdate, me, { + single: true + }); + Ext.Loader.setConfig({ + enabled: true + }); + this.onProfilesReady(); + }, + applyId: function(id) { + return id || this.$className; + }, + updateRouter: function(cfg) { + if (cfg) { + Ext.route.Router.setConfig(cfg); + } + }, + /** + * @method + * @template + * Called automatically when an update to either the Application Cache or the Local Storage Cache is detected. + * This is mainly used during production builds. + * @param {Object} [updateInfo] updateInfo Update information object contains properties for checking which cache triggered the update + */ + onAppUpdate: Ext.emptyFn, + onProfilesReady: function() { + var me = this, + profiles = me.getProfiles(), + length = profiles.length, + current, i, instance; + for (i = 0; i < length; i++) { + instance = Ext.create(profiles[i], { + application: me + }); + if (instance.isActive() && !current) { + current = instance; + me.setCurrentProfile(current); + } + } + if (current) { + current.init(); + } + me.initControllers(); + me.onBeforeLaunch(); + me.finishInitControllers(); + }, + doInit: function(app) { + this.initNamespace(app); + this.callParent([ + app + ]); + }, + initNamespace: function(me) { + var appProperty = me.getAppProperty(), + ns = Ext.namespace(me.getName()); + if (ns) { + ns.getApplication = function() { + return me; + }; + if (appProperty) { + if (!ns[appProperty]) { + ns[appProperty] = me; + } else if (ns[appProperty] !== me) { + Ext.log.warn('An existing reference is being overwritten for ' + name + '.' + appProperty + '. See the appProperty config.'); + } + } + } + }, + initControllers: function() { + var me = this, + controllers = Ext.Array.from(me.controllers), + profile = me.getCurrentProfile(), + i, ln; + me.controllers = new Ext.util.MixedCollection(); + for (i = 0 , ln = controllers.length; i < ln; i++) { + me.getController(controllers[i]); + } + // Also launch controllers for the active profile (if we have one) + // + if (profile) { + controllers = profile.getControllers(); + for (i = 0 , ln = controllers.length; i < ln; i++) { + me.getController(controllers[i]); + } + } + }, + finishInitControllers: function() { + var me = this, + controllers, i, l; + controllers = me.controllers.getRange(); + for (i = 0 , l = controllers.length; i < l; i++) { + controllers[i].finishInit(me); + } + }, + /** + * @method + * @template + * Called automatically when the page has completely loaded. This is an empty function that should be + * overridden by each application that needs to take action on page load. + * @param {String} profile The detected application profile + * @return {Boolean} By default, the Application will dispatch to the configured startup controller and + * action immediately after running the launch function. Return false to prevent this behavior. + */ + launch: Ext.emptyFn, + /** + * @private + */ + onBeforeLaunch: function() { + var me = this, + History = Ext.util.History, + defaultToken = me.getDefaultToken(), + currentProfile = me.getCurrentProfile(), + controllers, c, cLen, controller, token; + me.initMainView(); + if (currentProfile) { + currentProfile.launch(); + } + me.launch.call(me.scope || me); + me.launched = true; + me.fireEvent('launch', me); + controllers = me.controllers.items; + cLen = controllers.length; + for (c = 0; c < cLen; c++) { + controller = controllers[c]; + controller.onLaunch(me); + } + if (!History.ready) { + History.init(); + } + token = History.getToken(); + if (token || token === defaultToken) { + Ext.route.Router.onStateChange(token); + } else if (defaultToken) { + History.replace(defaultToken); + } + // Microloader has detected an Application Cache or LocalStorage Cache update, inform everyone + // that may have added listeners late. + if (Ext.Microloader && Ext.Microloader.appUpdate && Ext.Microloader.appUpdate.updated) { + Ext.Microloader.fireAppUpdate(); + } + // After launch we may as well cleanup the namespace cache + if (!me.cnsTimer) { + me.cnsTimer = Ext.defer(Ext.ClassManager.clearNamespaceCache, 2000, Ext.ClassManager); + } + }, + getModuleClassName: function(name, kind) { + return Ext.app.Controller.getFullName(name, kind, this.getName()).absoluteName; + }, + initMainView: function() { + var me = this, + currentProfile = me.getCurrentProfile(), + mainView; + if (currentProfile) { + mainView = currentProfile.getMainView(); + } + if (mainView) { + me.setMainView(mainView); + } else { + // since mainView is a lazy config we have to call the getter to initialize it + me.getMainView(); + } + }, + applyMainView: function(value) { + var view = this.getView(value); + // Ensure the full component stack is available immediately. + return view.create({ + $initParent: this.viewport + }); + }, + /** + * Create an instance of a controller by name. + * @param {String} name The name of the controller. For a controller with the + * full class name `MyApp.controller.Foo`, the name parameter should be `Foo`. + * If the controller already exists, it will be returned. + * + * @return {Ext.app.Controller} controller + */ + createController: function(name) { + return this.getController(name); + }, + /** + * Destroys a controller, any listeners are unbound. + * @param {String/Ext.app.Controller} controller The controller + */ + destroyController: function(controller) { + if (typeof controller === 'string') { + controller = this.getController(controller, true); + } + Ext.destroy(controller); + }, + /** + * Get an application's controller based on name or id. Generally, the controller id will be the same as the name + * unless otherwise specified. + * @param {String} name The name or id of the controller you are trying to retrieve + * @param {Boolean} [preventCreate] (private) + */ + getController: function(name, preventCreate) { + var me = this, + controllers = me.controllers, + className, controller, len, i, c, all; + // First check with the passed value if we have an explicit id + controller = controllers.get(name); + // In a majority of cases, the controller id will be the same as the name. + // However, when a controller is manually given an id, it will be keyed + // in the collection that way. So if we don't find it, we attempt to loop + // over the existing controllers and find it by classname + if (!controller) { + all = controllers.items; + for (i = 0 , len = all.length; i < len; ++i) { + c = all[i]; + className = c.getModuleClassName(); + if (className && className === name) { + controller = c; + break; + } + } + } + if (!controller && !preventCreate) { + className = me.getModuleClassName(name, 'controller'); + controller = Ext.create(className, { + application: me, + moduleClassName: className + }); + controllers.add(controller); + if (me._initialized) { + controller.doInit(me); + } + } + return controller; + }, + /** + * Unregister a controller from the application. + * @private + * @param {Ext.app.Controller} controller The controller to unregister + */ + unregister: function(controller) { + this.controllers.remove(controller); + }, + getApplication: function() { + return this; + }, + destroy: function(destroyRefs) { + var me = this, + controllers = me.controllers, + ns = Ext.namespace(me.getName()), + appProp = me.getAppProperty(); + Ext.undefer(me.cnsTimer); + Ext.un('appupdate', me.onAppUpdate, me); + Ext.destroy(me.viewport); + if (controllers) { + controllers.each(function(controller) { + controller.destroy(destroyRefs, true); + }); + } + me.controllers = null; + me.callParent([ + destroyRefs, + true + ]); + // Clean up any app reference + if (ns && ns[appProp] === me) { + delete ns[appProp]; + } + if (Ext.route.Router.application === me) { + Ext.route.Router.application = null; + } + if (Ext.app.Application.instance === me) { + Ext.app.Application.instance = null; + } + }, + updateGlyphFontFamily: function(fontFamily) { + Ext.setGlyphFontFamily(fontFamily); + }, + /** + * As a convenience developers can locally qualify profile names (e.g. 'MyProfile' vs + * 'MyApp.profile.MyProfile'). This just makes sure everything ends up fully qualified. + * @private + */ + applyProfiles: function(profiles) { + var me = this; + return Ext.Array.map(profiles, function(profile) { + return me.getModuleClassName(profile, "profile"); + }); + } +}, function() { + /** + * @member Ext + * @method getApplication + * @return {Ext.app.Application} + */ + Ext.getApplication = function() { + return Ext.app.Application.instance; + }; +}); + +// This is an override because it must be loaded very early, possibly before Ext.app.Application +// in dev mode so that Ext.application() can be called. +// Being an override also ensures that it is only included in a built app if Ext.app.Application +// is present. +// +// @override Ext.app.Application +/** + * @method application + * @member Ext + * Loads Ext.app.Application class and starts it up with given configuration after the + * page is ready. + * + * See `Ext.app.Application` for details. + * + * @param {Object/String} config Application config object or name of a class derived + * from Ext.app.Application. + */ +Ext.application = function(config) { + var createApp = function(App) { + // This won't be called until App class has been created. + Ext.onReady(function() { + var Viewport = Ext.viewport; + Viewport = Viewport && Viewport['Viewport']; + if (Viewport && Viewport.setup) { + Viewport.setup(App.prototype.config.viewport); + } + Ext.app.Application.instance = new App(); + }); + }; + if (typeof config === "string") { + Ext.require(config, function() { + createApp(Ext.ClassManager.get(config)); + }); + } else { + config = Ext.apply({ + extend: 'Ext.app.Application' + }, // can be replaced by config! + config); + // We have to process "paths" before creating Application class, + // or `requires` won't work. + Ext.app.setupPaths(config.name, config.appFolder, config.paths); + config['paths processed'] = true; + // Let Ext.define do the hard work but don't assign a class name. + Ext.define(config.name + ".$application", config, function() { + createApp(this); + }); + } +}; + +/** + * @class Ext.app.Application + */ +Ext.define('Ext.overrides.app.Application', { + override: 'Ext.app.Application', + uses: [ + 'Ext.tip.QuickTipManager' + ], + // @cmd-auto-dependency {aliasPrefix: "view.", mvc: true, requires: ["Ext.plugin.Viewport"]} + /** + * @cfg {Boolean/String} [autoCreateViewport=false] + * @deprecated 5.1 Instead use {@link #mainView} + * @member Ext.app.Application + */ + autoCreateViewport: false, + config: { + /** + * @cfg {Boolean} enableQuickTips + * @deprecated 6.2.0 Use {@link #quickTips}. + */ + enableQuickTips: null + }, + /** + * @cfg {Boolean} quickTips + * True to automatically set up Ext.tip.QuickTip support. + * + * @since 6.2.0 + */ + quickTips: true, + updateEnableQuickTips: function(enableQuickTips) { + this.setQuickTips(enableQuickTips); + }, + applyMainView: function(mainView) { + var view, proto, config, protoPlugins, configPlugins; + if (typeof mainView === 'string') { + view = this.getView(mainView); + config = {}; + } else { + config = mainView; + view = Ext.ClassManager.getByConfig(mainView); + } + proto = view.prototype; + if (!proto.isViewport) { + // Need to copy over any plugins defined on the prototype and on the config. + protoPlugins = Ext.Array.from(proto.plugins); + configPlugins = Ext.Array.from(config.plugins); + config = Ext.apply({}, config); + config.plugins = [ + 'viewport' + ].concat(protoPlugins, configPlugins); + } + return view.create(config); + }, + getDependencies: function(cls, data, requires) { + var Controller = Ext.app.Controller, + proto = cls.prototype, + namespace = data.$namespace, + viewportClass = data.autoCreateViewport; + if (viewportClass) { + if (!namespace) { + Ext.raise("[Ext.app.Application] Can't resolve namespace for " + data.$className + ", did you forget to specify 'name' property?"); + } + if (viewportClass === true) { + viewportClass = 'Viewport'; + } else { + requires.push('Ext.plugin.Viewport'); + } + Controller.processDependencies(proto, requires, namespace, 'view', viewportClass); + } + }, + onBeforeLaunch: function() { + var me = this, + autoCreateViewport = me.autoCreateViewport; + if (me.getQuickTips()) { + me.initQuickTips(); + } + if (autoCreateViewport) { + me.initViewport(); + } + this.callParent(arguments); + }, + getViewportName: function() { + var name = null, + autoCreate = this.autoCreateViewport; + if (autoCreate) { + name = (autoCreate === true) ? 'Viewport' : autoCreate; + } + return name; + }, + initViewport: function() { + this.setMainView(this.getViewportName()); + }, + initQuickTips: function() { + Ext.tip.QuickTipManager.init(); + } +}); + +/** + * A Profile represents a range of devices that fall under a common category. For the vast majority of apps that use + * device profiles, the app defines a Phone profile and a Tablet profile. Doing this enables you to easily customize + * the experience for the different sized screens offered by those device types. + * + * Only one Profile can be active at a time, and each Profile defines a simple {@link #isActive} function that should + * return either true or false. The first Profile to return true from its isActive function is set as your Application's + * {@link Ext.app.Application#currentProfile current profile}. + * + * A Profile can define any number of {@link #models}, {@link #views}, {@link #controllers} and {@link #stores} which + * will be loaded if the Profile is activated. It can also define a {@link #launch} function that will be called after + * all of its dependencies have been loaded, just before the {@link Ext.app.Application#launch application launch} + * function is called. + * + * ## Sample Usage + * + * First you need to tell your Application about your Profile(s): + * + * Ext.application({ + * name: 'MyApp', + * profiles: ['Phone', 'Tablet'] + * }); + * + * This will load app/profile/Phone.js and app/profile/Tablet.js. Here's how we might define the Phone profile: + * + * Ext.define('MyApp.profile.Phone', { + * extend: 'Ext.app.Profile', + * + * views: ['Main'], + * + * isActive: function() { + * return Ext.os.is('Phone'); + * } + * }); + * + * The isActive function returns true if we detect that we are running on a phone device. If that is the case the + * Application will set this Profile active and load the 'Main' view specified in the Profile's {@link #views} config. + * + * ## Class Specializations + * + * Because Profiles are specializations of an application, all of the models, views, controllers and stores defined + * in a Profile are expected to be namespaced under the name of the Profile. Here's an expanded form of the example + * above: + * + * Ext.define('MyApp.profile.Phone', { + * extend: 'Ext.app.Profile', + * + * views: ['Main'], + * controllers: ['Signup'], + * models: ['MyApp.model.Group'], + * + * isActive: function() { + * return Ext.os.is('Phone'); + * } + * }); + * + * In this case, the Profile is going to load *app/view/phone/Main.js*, *app/controller/phone/Signup.js* and + * *app/model/Group.js*. Notice that in each of the first two cases the name of the profile ('phone' in this case) was + * injected into the class names. In the third case we specified the full Model name (for Group) so the Profile name + * was not injected. + * + * For a fuller understanding of the ideas behind Profiles and how best to use them in your app, we suggest you read + * the [device profiles guide](/touch/2.4/core_concepts/device_profiles.html). + * + */ +Ext.define('Ext.app.Profile', { + mixins: [ + 'Ext.mixin.Observable' + ], + requires: [ + 'Ext.app.Controller' + ], + /** + * @property {Boolean} + * `true` to identify an object as an instance of `Ext.app.Profile` + */ + isProfile: true, + /** + * @cfg {String} [namespace] + * The namespace that this Profile's classes can be found in. Defaults to the lowercase + * Profile {@link #name}, for example a Profile called MyApp.profile.Phone will by default have a 'phone' + * namespace, which means that this Profile's additional models, stores, views and controllers will be loaded + * from the MyApp.model.phone.*, MyApp.store.phone.*, MyApp.view.phone.* and MyApp.controller.phone.* namespaces + * respectively. + * @accessor + */ + /** + * @cfg {String} [name] + * The name of this Profile. Defaults to the last section of the class name (e.g. a profile + * called MyApp.profile.Phone will default the name to 'Phone'). + * @accessor + */ + config: { + /** + * @cfg {String} mainView + */ + mainView: { + $value: null, + lazy: true + }, + /** + * @cfg {Ext.app.Application} application + * The {@link Ext.app.Application Application} instance to which this Profile is + * bound. This is set automatically. + * @accessor + * @readonly + */ + application: null, + // @cmd-auto-dependency {aliasPrefix: "controller.", profile: true, blame: "all"} + /** + * @cfg {String[]} controllers + * Any additional {@link Ext.app.Controller Controllers} to load for this profile. + * Note that each item here will be prepended with the Profile namespace when loaded. + * + * Example usage: + * + * controllers: [ + * 'Users', + * 'MyApp.controller.Products' + * ] + * + * This will load *MyApp.controller.tablet.Users* and *MyApp.controller.Products*. + * @accessor + */ + controllers: [], + // @cmd-auto-dependency {aliasPrefix : "model.", profile: true, blame: "all"} + /** + * @cfg {String[]} models + * Any additional {@link Ext.app.Application#models Models} to load for this profile. + * Note that each item here will be prepended with the Profile namespace when loaded. + * + * Example usage: + * + * models: [ + * 'Group', + * 'MyApp.model.User' + * ] + * + * This will load *MyApp.model.tablet.Group* and *MyApp.model.User*. + * @accessor + */ + models: [], + // @cmd-auto-dependency {aliasPrefix: "view.", profile: true, isKeyedObject:true, blame: "all" } + /** + * @cfg {Object/String[]} views + * This config allows the active profile to define a set of `xtypes` and map them + * to desired classes and default configurations. Normally an `xtype` is statically + * declared by a {@link Ext.Component component} in its class definition. This + * mechanism allows the active profile to control a set of these types. + * + * Example: + * + * views: { + * // The "main" xtype maps to MyApp.view.tablet.Main + * // + * main: 'MyApp.view.tablet.Main', + * + * // The "inbox" xtype maps to a subclass of MyApp.view.Inbox (created + * // by this mechanism) that sets the "mode" config to "compact". + * // + * inbox: { + * xclass: 'MyApp.view.Inbox', + * mode: 'compact' + * } + * } + * + * Note that class names used in this form must be full class names, unlike the + * historical usage of `views`. Further, these views cannot be accessed using the + * `getView` method but rather via their assigned `xtype`. + * + * The historical usage of this config is enabled when an array is passed. In this + * case, these are simply additional {@link Ext.app.Application#views views} to + * load for this profile. Note that each item here will be prepended with the + * Profile namespace when loaded. + * + * Example usage: + * + * views: [ + * 'Main', + * 'MyApp.view.Login' + * ] + * + * This will load *MyApp.view.tablet.Main* and *MyApp.view.Login*. While supported, + * this usage is discouraged in favor of `xtype` mapping. + * @accessor + */ + views: [], + // @cmd-auto-dependency {aliasPrefix: "store.", profile: true, blame: "all"} + /** + * @cfg {String[]} stores + * Any additional {@link Ext.app.Application#stores Stores} to load for this profile. + * Note that each item here will be prepended with the Profile namespace when loaded. + * + * Example usage: + * + * stores: [ + * 'Users', + * 'MyApp.store.Products' + * ] + * + * This will load *MyApp.store.tablet.Users* and *MyApp.store.Products*. + * @accessor + */ + stores: [] + }, + /** + * Creates a new Profile instance + */ + constructor: function(config) { + this.initConfig(config); + this.mixins.observable.constructor.apply(this, arguments); + }, + /** + * Determines whether or not this Profile is active on the device isActive is executed on. Should return true if + * this profile is meant to be active on this device, false otherwise. Each Profile should implement this function + * (the default implementation just returns false). + * @return {Boolean} True if this Profile should be activated on the device it is running on, false otherwise + */ + isActive: function() { + return false; + }, + /** + * This method is called once the profile is determined to be the active profile. This + * initialization is performed before controllers are initialized and therefore also + * before launch. + * @protected + * @since 6.0.1 + */ + init: function() { + var views = this.getViews(), + xtype; + if (views && !(views instanceof Array)) { + for (xtype in views) { + Ext.ClassManager.setXType(views[xtype], xtype); + } + } + }, + /** + * @method + * The launch function is called by the {@link Ext.app.Application Application} if this Profile's {@link #isActive} + * function returned true. This is typically the best place to run any profile-specific app launch code. Example + * usage: + * + * launch: function() { + * Ext.create('MyApp.view.tablet.Main'); + * } + */ + launch: Ext.emptyFn, + onClassExtended: function(cls, data, hooks) { + var onBeforeClassCreated = hooks.onBeforeCreated; + hooks.onBeforeCreated = function(cls, data) { + var Controller = Ext.app.Controller, + className = cls.$className, + requires = [], + proto = cls.prototype, + views = data.views, + name, namespace; + // Process name and namespace configs here since we need to use the namespace + // in the dependency calculation + name = data.name; + if (name) { + delete data.name; + } else { + name = className.split('.'); + name = name[name.length - 1]; + } + cls._name = name; + cls._namespace = name = (data.namespace || name).toLowerCase(); + delete data.namespace; + namespace = Controller.resolveNamespace(cls, data); + Controller.processDependencies(proto, requires, namespace, 'model', data.models, name); + Controller.processDependencies(proto, requires, namespace, 'store', data.stores, name); + Controller.processDependencies(proto, requires, namespace, 'controller', data.controllers, name); + if (views) { + if (views instanceof Array) { + Controller.processDependencies(proto, requires, namespace, 'view', views, name); + } else { + Ext.app.Profile.processViews(className, views, requires); + } + } + Ext.require(requires, Ext.Function.pass(onBeforeClassCreated, arguments, this)); + }; + }, + getName: function() { + // This used to be a Config but is now processed in onClassExtended so we provide + // the getter for compat. + return this.self._name; + }, + getNamespace: function() { + // This used to be a Config but is now processed in onClassExtended so we provide + // the getter for compat. + return this.self._namespace; + }, + privates: { + statics: { + processViews: function(className, views, requires) { + var body, cls, s, xtype; + for (xtype in views) { + cls = views[xtype]; + if (typeof cls !== 'string') { + s = cls.xclass; + if (!s) { + Ext.raise('Views must specify an xclass'); + } + body = Ext.apply({ + extend: s + }, cls); + delete body.xclass; + // Class names will be App.profile.Tablet$inbox for example + Ext.define(views[xtype] = className + '$' + xtype, body); + cls = s; + } + requires.push(cls); + } + } + } + } +}); + +/** + * @class Ext.app.domain.View + */ +Ext.define('Ext.app.domain.View', { + extend: 'Ext.app.EventDomain', + requires: [ + 'Ext.Widget' + ], + isInstance: true, + constructor: function(controller) { + this.callParent([ + controller + ]); + this.controller = controller; + this.monitoredClasses = [ + Ext.Widget + ]; + }, + match: function(target, selector, controller) { + var out = false; + if (selector === '#') { + out = controller === target.getController(); + } else { + out = target.is(selector); + } + return out; + }, + destroy: function() { + this.controller = null; + this.callParent(); + } +}); + +Ext.define('Ext.overrides.app.domain.View', { + override: 'Ext.app.domain.View', + requires: [ + 'Ext.Component' + ], + constructor: function(controller) { + this.callParent([ + controller + ]); + // The base class handles Ext.Widget, which encompasses + // component for modern, so we only need the override here. + this.monitoredClasses.push(Ext.Component); + } +}); + +/** + * A view controller is a controller that can be attached to a specific view + * instance so it can manage the view and its child components. Each instance of the view + * will have a new view controller, so the instances are isolated. + * + * When a view controller is specified on a view, events and other handlers that use strings as + * values will be automatically connected with the appropriate methods in the controller's class. + * + * Sample usage: + * + * @example + * Ext.define('MyViewController', { + * extend : 'Ext.app.ViewController', + * alias: 'controller.myview', + * + * // This method is called as a "handler" for the Add button in our view + * onAddClick: function() { + * Ext.Msg.alert('Add', 'The Add button was clicked'); + * } + * }); + * + * Ext.define('MyView', { + * extend: 'Ext.Panel', + * controller: 'myview', + * + * items: [{ + * xtype: 'button', + * text: 'Add', + * handler: 'onAddClick', // calls MyViewController's onAddClick method + * }] + * }); + * + * Ext.onReady(function() { + * new MyView({ + * renderTo: Ext.getBody(), + * width: 400, + * height: 200 + * }); + * }); + */ +Ext.define('Ext.app.ViewController', { + extend: 'Ext.app.BaseController', + alias: 'controller.controller', + requires: [ + 'Ext.app.domain.View' + ], + mixins: [ + 'Ext.mixin.Factoryable' + ], + isViewController: true, + /** + * @property factoryConfig + * @inheritdoc + */ + factoryConfig: { + // configure Factoryable + type: 'controller' + }, + config: { + /** + * @cfg {Object} bindings + * A declarative set of bindings to the {@link #getViewModel} for this + * controller. The key should be the method, the value should be + * the bind statement: + * + * Ext.define('MyApp.TestController', { + * extend: 'Ext.app.ViewController', + * + * bindings: { + * onTotalChange: '{total}', + * onCoordsChange: '({x}, {y})', + * onProductChange: { + * amount: '{qty}', + * rating: '{rating}' + * } + * }, + * + * onTotalChange: function(total) { + * console.log(total); + * }, + * + * onCoordsChange: function(coords) { + * console.log('The coordinates are: ', coords); + * }, + * + * onProductChange: function(productInfo) { + * console.log('Amount: ', productInfo.amount, ' Rating: ', productInfo.rating); + * } + * }); + * + * @since 6.5.0 + */ + bindings: { + $value: null, + lazy: true + }, + closeViewAction: 'destroy' + }, + view: null, + constructor: function(config) { + this.compDomain = new Ext.app.domain.View(this); + this.callParent([ + config + ]); + }, + /** + * @method beforeInit + * + * Called before the view initializes. This is called before the view's + * initComponent method has been called. + * @param {Ext.Component} view The view + * @protected + */ + beforeInit: Ext.emptyFn, + /** + * @method init + * + * Called when the view initializes. This is called after the view's initComponent + * method has been called. + * @param {Ext.Component} view The view + * @protected + */ + init: Ext.emptyFn, + /** + * @method initViewModel + * + * Called when the view model instance for an attached view is first created. + * @param {Ext.app.ViewModel} viewModel The ViewModel + * @protected + */ + initViewModel: Ext.emptyFn, + /** + * Destroy the view controller. + */ + destroy: function() { + var me = this, + domain = me.compDomain, + bind, b, key; + if (me.$hasBinds) { + bind = me.getBindings(); + for (key in bind) { + b = bind[key]; + if (b) { + b.destroy(); + } + } + } + if (domain) { + domain.unlisten(me); + domain.destroy(); + } + me.compDomain = me.view = null; + me.callParent(); + }, + /** + * This method closes the associated view. The manner in which this is done (that is, + * the method called to close the view) is specified by `closeViewAction`. + * + * It is common for views to map one or more events to this method to allow the view + * to be closed. + */ + closeView: function() { + var view = this.getView(), + action; + if (view) { + action = this.getCloseViewAction(); + view[action](); + } + }, + control: function(selectors, listeners) { + var obj = selectors; + if (Ext.isString(selectors)) { + obj = {}; + obj[selectors] = listeners; + } + this.compDomain.listen(obj, this); + }, + listen: function(to, controller) { + var component = to.component; + if (component) { + to = Ext.apply({}, to); + delete to.component; + this.control(component); + } + this.callParent([ + to, + controller + ]); + }, + applyId: function(id) { + if (!id) { + id = Ext.id(null, 'controller-'); + } + return id; + }, + /** + * @method getReferences + * @inheritdoc Ext.mixin.Container#method!getReferences + * @since 5.0.0 + */ + getReferences: function() { + var view = this.view; + return view && view.getReferences(); + }, + /** + * Get the view for this controller. + * @return {Ext.Component} The view. + */ + getView: function() { + return this.view; + }, + /** + * Gets a reference to the component with the specified {@link Ext.Component#reference} + * value. + * + * The method is a short-hand for the {@link #lookupReference} method. + * + * @param {String} key The name of the reference to lookup. + * @return {Ext.Component} The component, `null` if the reference doesn't exist. + * @since 6.0.1 + */ + lookup: function(key) { + var view = this.view; + return view && view.lookup(key); + }, + /** + * Gets a reference to the component with the specified {@link Ext.Component#reference} + * value. + * + * The {@link #lookup} method is a short-hand version of this method. + * + * @param {String} key The name of the reference to lookup. + * @return {Ext.Component} The component, `null` if the reference doesn't exist. + * @since 5.0.0 + */ + lookupReference: function(key) { + return this.lookup(key); + }, + /** + * Get a {@link Ext.data.Session} attached to the view for this controller. + * See {@link Ext.Component#lookupSession}. + * + * @return {Ext.data.Session} The session. `null` if no session is found. + * + * @since 5.0.0 + */ + getSession: function() { + var view = this.view; + return view && view.lookupSession(); + }, + /** + * Get a {@link Ext.app.ViewModel} attached to the view for this controller. + * See {@link Ext.Component#lookupViewModel}. + * + * @return {Ext.app.ViewModel} The ViewModel. `null` if no ViewModel is found. + * + * @since 5.0.0 + */ + getViewModel: function() { + var view = this.view; + return view && view.lookupViewModel(); + }, + /** + * Get a {@link Ext.data.Store} attached to the {@link #getViewModel ViewModel} attached to + * this controller. See {@link Ext.app.ViewModel#getStore}. + * @param {String} name The name of the store. + * @return {Ext.data.Store} The store. `null` if no store is found, or there is no + * {@link Ext.app.ViewModel} attached to the view for this controller. + * + * @since 5.0.0 + */ + getStore: function(name) { + var viewModel = this.getViewModel(); + return viewModel ? viewModel.getStore(name) : null; + }, + /** + * Fires an event on the view. See {@link Ext.Component#fireEvent}. + * @param {String} eventName The name of the event to fire. + * @param {Object...} args Variable number of parameters are passed to handlers. + * @return {Boolean} returns false if any of the handlers return false otherwise it returns true. + * @protected + */ + fireViewEvent: function(eventName, args) { + var view = this.view, + result = false, + a = arguments; + if (view) { + if (view !== args) { + a = Ext.Array.slice(a); + a.splice(1, 0, view); + } + // insert view at [1] + result = view.fireEvent.apply(view, a); + } + return result; + }, + /** + * @method setBind + * @hide + */ + applyBindings: function(bindings) { + if (!bindings) { + return null; + } + var me = this, + viewModel = me.getViewModel(), + getBindTemplateScope = me.getBindTemplateScope(), + b, fn, descriptor; + me.$hasBinds = true; + if (!viewModel) { + Ext.raise('Cannot use bind config without a viewModel'); + } + for (fn in bindings) { + descriptor = bindings[fn]; + b = null; + if (descriptor) { + b = viewModel.bind(descriptor, fn, me); + b.getTemplateScope = getBindTemplateScope; + } + bindings[fn] = b; + } + return bindings; + }, + //========================================================================= + privates: { + view: null, + /** + * Set a reference to a component. + * @param {Ext.Component} component The component to reference + * @private + */ + attachReference: function(component) { + var view = this.view; + if (view) { + view.attachReference(component); + } + }, + getBindTemplateScope: function() { + // This method is called as a method on a Binding instance, so the "this" pointer + // is that of the Binding. The "scope" of the Binding is the controller. + return this.scope; + }, + initBindings: function() { + // Force bind creation + this.getBindings(); + }, + /** + * Sets the view for this controller. To be called by the view + * when it initializes. + * @param {Object} view The view. + * + * @private + */ + setView: function(view) { + this.view = view; + if (!this.beforeInit.$nullFn) { + this.beforeInit(view); + } + } + } +}); + +/** + * This class provides an **unordered** collection similar to `Ext.util.Collection`. The + * removal of order maintenance provides a significant performance increase. Further, this + * class does not provide events or other high-level features. It maintains an array of + * `items` and a map to quickly find items by their `id`. + * + * @private + * @since 5.1.1 + */ +Ext.define('Ext.util.Bag', { + isBag: true, + constructor: function() { + /** + * @property {Object[]} items + * An array containing the items. + * @private + * @since 5.1.1 + */ + this.items = []; + /** + * @property {Object} map + * An object used as a map to find items based on their key. + * @private + * @since 5.1.1 + */ + this.map = {}; + }, + /** + * @property {Number} generation + * Mutation counter which is incremented when the collection changes. + * @readonly + * @since 5.1.1 + */ + generation: 0, + /** + * @property {Number} length + * The count of items in the collection. + * @readonly + * @since 5.1.1 + */ + length: 0, + beginUpdate: Ext.emptyFn, + endUpdate: Ext.emptyFn, + add: function(item) { + var me = this, + items = me.items, + map = me.map, + n = 1, + old, i, idx, id, it, ret, was; + if (Ext.isArray(item)) { + old = ret = []; + n = item.length; + } + for (i = 0; i < n; i++) { + id = me.getKey(it = old ? item[i] : item); + idx = map[id]; + if (idx === undefined) { + items.push(it); + map[id] = me.length++; + if (old) { + old.push(it); + } else { + ret = it; + } + } else { + was = items[idx]; + if (old) { + old.push(was); + } else { + ret = was; + } + items[idx] = it; + } + } + ++me.generation; + return ret; + }, + clear: function() { + var me = this, + needsClear = me.generation || me.length, + ret = needsClear ? me.items : []; + if (needsClear) { + me.items = []; + me.length = 0; + me.map = {}; + ++me.generation; + } + return ret; + }, + clone: function() { + var me = this, + ret = new me.self(), + len = me.length; + if (len) { + Ext.apply(ret.map, me.map); + ret.items = me.items.slice(); + ret.length = me.length; + } + return ret; + }, + contains: function(item) { + var ret = false, + map = this.map, + key; + if (item != null) { + key = this.getKey(item); + if (key in map) { + ret = this.items[map[key]] === item; + } + } + return ret; + }, + containsKey: function(key) { + return key in this.map; + }, + destroy: function() { + this.items = this.map = null; + this.callParent(); + }, + each: function(fn, scope) { + var items = this.items, + len = items.length, + i, ret; + if (len) { + scope = scope || this; + items = items.slice(0); + // safe for re-entrant calls + for (i = 0; i < len; i++) { + ret = fn.call(scope, items[i], i, len); + if (ret === false) { + break; + } + } + } + return ret; + }, + getAt: function(index) { + var out = null; + if (index < this.length) { + out = this.items[index]; + } + return out; + }, + get: function(key) { + return this.getByKey(key); + }, + getByKey: function(key) { + var map = this.map, + ret = (key in map) ? this.items[map[key]] : null; + return ret; + }, + indexOfKey: function(key) { + var map = this.map, + ret = (key in map) ? map[key] : -1; + return ret; + }, + last: function() { + return this.items[this.length - 1]; + }, + updateKey: function(item, oldKey) { + var me = this, + map = me.map, + newKey; + if (!item || !oldKey) { + return; + } + if ((newKey = me.getKey(item)) !== oldKey) { + if (me.getAt(map[oldKey]) === item && !(newKey in map)) { + me.generation++; + map[newKey] = map[oldKey]; + delete map[oldKey]; + } + } else { + // It may be that the item is (somehow) already in the map using the + // newKey or that there is no item in the map with the oldKey. These + // are not errors. + if (newKey in map && me.getAt(map[newKey]) !== item) { + // There is a different item in the map with the newKey which is an + // error. To properly handle this, add the item instead. + Ext.raise('Duplicate newKey "' + newKey + '" for item with oldKey "' + oldKey + '"'); + } + if (oldKey in map && me.getAt(map[oldKey]) !== item) { + // There is a different item in the map with the oldKey which is also + // an error. Do not call this method for items that are not part of + // the collection. + Ext.raise('Incorrect oldKey "' + oldKey + '" for item with newKey "' + newKey + '"'); + } + } + }, + getCount: function() { + return this.length; + }, + getKey: function(item) { + return item.id || item.getId(); + }, + getRange: function(begin, end) { + var items = this.items, + length = items.length, + range; + if (!length) { + range = []; + } else { + range = Ext.Number.clipIndices(length, [ + begin, + end + ]); + range = items.slice(range[0], range[1]); + } + return range; + }, + remove: function(item) { + var me = this, + map = me.map, + items = me.items, + ret = null, + n = 1, + changed, old, i, idx, id, last, was; + if (Ext.isArray(item)) { + n = item.length; + old = ret = []; + } + if (me.length) { + for (i = 0; i < n; i++) { + idx = map[id = me.getKey(old ? item[i] : item)]; + if (idx !== undefined) { + delete map[id]; + was = items[idx]; + if (old) { + old.push(was); + } else { + ret = was; + } + last = items.pop(); + if (idx < --me.length) { + items[idx] = last; + map[me.getKey(last)] = idx; + } + changed = true; + } + } + if (changed) { + ++me.generation; + } + } + return ret; + }, + removeByKey: function(key) { + var item = this.getByKey(key); + if (item) { + this.remove(item); + } + return item || null; + }, + replace: function(item) { + this.add(item); + return item; + }, + sort: function(fn) { + var me = this, + items = me.items, + n = items.length, + item; + if (n) { + Ext.Array.sort(items, fn); + me.map = {}; + while (n-- > 0) { + item = items[n]; + me.map[me.getKey(item)] = n; + } + ++me.generation; + } + } +}); + +/** + * This class is used to bulk schedule a set of `Ext.util.Schedulable` items. The items + * in the scheduler request time by calling their `schedule` method and when the time has + * arrived its `react` method is called. + * + * The `react` methods are called in dependency order as determined by the sorting process. + * The sorting process relies on each item to implement its own `sort` method. + * + * @private + */ +Ext.define('Ext.util.Scheduler', { + mixins: [ + 'Ext.mixin.Observable' + ], + requires: [ + 'Ext.util.Bag' + ], + busyCounter: 0, + lastBusyCounter: 0, + destroyed: false, + firing: null, + notifyIndex: -1, + nextId: 0, + orderedItems: null, + passes: 0, + scheduledCount: 0, + validIdRe: null, + config: { + /** + * @cfg {Number} cycleLimit + * The maximum number of iterations to make over the items in one `notify` call. + * This is used to prevent run away logic from looping infinitely. If this limit + * is exceeded, an error is thrown (in development builds). + * @private + */ + cycleLimit: 5, + /** + * @cfg {String/Function} preSort + * If provided the `Schedulable` items will be pre-sorted by this function or + * property value before the dependency sort. + */ + preSort: null, + /** + * @cfg {Number} tickDelay + * The number of milliseconds to delay notification after the first `schedule` + * request. + */ + tickDelay: 5 + }, + /** + * @property {Boolean} suspendOnNotify + * `true` to suspend layouts when the scheduler is triggering bindings. Setting this to `false` + * may mean multiple layout runs on a single bind call which could affect performance. + */ + suspendOnNotify: true, + constructor: function(config) { + if (Ext.util.Scheduler.instances) { + Ext.util.Scheduler.instances.push(this); + } else { + Ext.util.Scheduler.instances = [ + this + ]; + } + this.id = Ext.util.Scheduler.count = (Ext.util.Scheduler.count || 0) + 1; + this.mixins.observable.constructor.call(this, config); + this.items = new Ext.util.Bag(); + }, + destroy: function() { + var me = this, + timer = me.timer; + if (timer) { + window.clearTimeout(timer); + me.timer = null; + } + me.items.destroy(); + me.items = me.orderedItems = null; + me.callParent(); + Ext.Array.remove(Ext.util.Scheduler.instances, this); + }, + /** + * Adds an item to the scheduler. This is called internally by the `constructor` of + * `{@link Ext.util.Schedulable}`. + * + * @param {Object} item The item to add. + * @private + * @since 5.0.0 + */ + add: function(item) { + var me = this, + items = me.items; + if (items === me.firing) { + me.items = items = items.clone(); + } + item.id = item.id || ++me.nextId; + item.scheduler = me; + items.add(item); + if (!me.sortMap) { + // If we are sorting we don't want to invalidate this... we will pick up the + // new items just fine. + me.orderedItems = null; + } + }, + /** + * Removes an item to the scheduler. This is called internally by the `destroy` method + * of `{@link Ext.util.Schedulable}`. + * + * @param {Object} item The item to remove. + * @private + * @since 5.0.0 + */ + remove: function(item) { + var me = this, + items = me.items; + if (me.destroyed) { + return; + } + if (me.sortMap) { + Ext.raise('Items cannot be removed during sort'); + } + if (items === me.firing) { + me.items = items = items.clone(); + } + if (item.scheduled) { + me.unscheduleItem(item); + item.scheduled = false; + } + items.remove(item); + me.orderedItems = null; + }, + /** + * This method is called internally as needed to sort or resort the items in their + * proper dependency order. + * + * @private + * @since 5.0.0 + */ + sort: function() { + var me = this, + items = me.items, + sortMap = {}, + preSort = me.getPreSort(), + i, item; + me.orderedItems = []; + me.sortMap = sortMap; + me.sortStack = []; + if (preSort) { + items.sort(preSort); + } + items = items.items; + // grab the items array + // We reference items.length since items can be added during this loop + for (i = 0; i < items.length; ++i) { + item = items[i]; + if (!sortMap[item.id]) { + me.sortItem(item); + } + } + me.sortMap = null; + me.sortStack = null; + }, + /** + * Adds one item to the sorted items array. This can be called by the `sort` method of + * `{@link Ext.util.Sortable sortable}` objects to add an item on which it depends. + * + * @param {Object} item The item to add. + * @return {Ext.util.Scheduler} This instance. + * @since 5.0.0 + */ + sortItem: function(item) { + var me = this, + sortMap = me.sortMap, + orderedItems = me.orderedItems, + itemId; + if (!item.scheduler) { + me.add(item); + } + itemId = item.id; + if (item.scheduler !== me) { + Ext.raise('Item ' + itemId + ' belongs to another Scheduler'); + } + me.sortStack.push(item); + if (sortMap[itemId] === 0) { + for (var cycle = [], + i = 0; i < me.sortStack.length; ++i) { + cycle[i] = me.sortStack[i].getFullName(); + } + Ext.raise('Dependency cycle detected: ' + cycle.join('\n --> ')); + } + if (!(itemId in sortMap)) { + // In production builds the above "if" will kick out the items that have + // already been added (which it must) but also those that are being added + // and have created a cycle (by virtue of the setting to 0). This check + // should not be needed if cycles were all detected and removed in dev but + // this is better than infinite recursion. + sortMap[itemId] = 0; + if (!item.sort.$nullFn) { + item.sort(); + } + sortMap[itemId] = 1; + item.order = me.orderedItems.length; + orderedItems.push(item); + } + me.sortStack.pop(); + return me; + }, + /** + * Adds multiple items to the sorted items array. This can be called by the `sort` + * method of `{@link Ext.util.Sortable sortable}` objects to add items on which it + * depends. + * + * @param {Object/Object[]} items The items to add. If this is an object, the values + * are considered the items and the keys are ignored. + * @return {Ext.util.Scheduler} This instance. + * @since 5.0.0 + */ + sortItems: function(items) { + var me = this, + sortItem = me.sortItem; + if (items) { + if (items instanceof Array) { + Ext.each(items, sortItem, me); + } else { + Ext.Object.eachValue(items, sortItem, me); + } + } + return me; + }, + applyPreSort: function(preSort) { + if (typeof preSort === 'function') { + return preSort; + } + var parts = preSort.split(','), + direction = [], + length = parts.length, + c, i, s; + for (i = 0; i < length; ++i) { + direction[i] = 1; + s = parts[i]; + if ((c = s.charAt(0)) === '-') { + direction[i] = -1; + } else if (c !== '+') { + c = 0; + } + if (c) { + parts[i] = s.substring(1); + } + } + return function(lhs, rhs) { + var ret = 0, + i, prop, v1, v2; + for (i = 0; !ret && i < length; ++i) { + prop = parts[i]; + v1 = lhs[prop]; + v2 = rhs[prop]; + ret = direction[i] * ((v1 < v2) ? -1 : ((v2 < v1) ? 1 : 0)); + } + return ret; + }; + }, + //------------------------------------------------------------------------- + // Callback scheduling + // + /** + * This method can be called to force the delivery of any scheduled items. This is + * called automatically on a timer when items request service. + * + * @since 5.0.0 + */ + notify: function() { + var me = this, + timer = me.timer, + cyclesLeft = me.getCycleLimit(), + globalEvents = Ext.GlobalEvents, + suspend = me.suspendOnNotify, + busyCounter, i, item, len, queue, firedEvent; + if (timer) { + window.clearTimeout(timer); + me.timer = null; + } + // Only process the queue if we are not already notifying + // and there are notifications to deliver. + if (!me.firing && me.scheduledCount) { + if (suspend) { + Ext.suspendLayouts(); + } + while (me.scheduledCount) { + if (cyclesLeft) { + --cyclesLeft; + } else { + me.firing = null; + if (me.onCycleLimitExceeded) { + me.onCycleLimitExceeded(); + } + break; + } + if (!firedEvent) { + firedEvent = true; + if (globalEvents.hasListeners.beforebindnotify) { + globalEvents.fireEvent('beforebindnotify', me); + } + } + ++me.passes; + // We need to sort before we start firing because items can be added as we + // loop. + if (!(queue = me.orderedItems)) { + me.sort(); + queue = me.orderedItems; + } + len = queue.length; + if (len) { + me.firing = me.items; + for (i = 0; i < len; ++i) { + item = queue[i]; + if (item.scheduled) { + item.scheduled = false; + --me.scheduledCount; + me.notifyIndex = i; + //Ext.log('React: ' + item.getFullName()); + // This sequence allows the reaction to schedule items further + // down the queue without a second pass but also to schedule an + // item that is "upstream" or even itself. + item.react(); + if (!me.scheduledCount) { + break; + } + } + } + } + } + me.firing = null; + me.notifyIndex = -1; + if (suspend) { + Ext.resumeLayouts(true); + } + } + // The last thing we do is check for idle state transition (now that whatever + // else that was queued up has been dispatched): + if ((busyCounter = me.busyCounter) !== me.lastBusyCounter) { + if (!(me.lastBusyCounter = busyCounter)) { + // Since the counters are not equal, we were busy and are not anymore, + // so we can fire the idle event: + me.fireEvent('idle', me); + } + } + }, + /** + * The method called by the timer. This cleans up the state and calls `notify`. + * @private + * @since 5.0.0 + */ + onTick: function() { + this.timer = null; + this.notify(); + }, + /** + * Called to indicate that an item needs to be scheduled. This should not be called + * directly. Call the item's `{@link Ext.util.Schedulable#schedule schedule}` method + * instead. + * @param {Object} item + * @private + * @since 5.0.0 + */ + scheduleItem: function(item) { + var me = this; + ++me.scheduledCount; + //Ext.log('Schedule: ' + item.getFullName()); + if (!me.timer && !me.firing) { + me.scheduleTick(); + } + }, + /** + * This method starts the timer that will execute the next `notify`. + * @param {Object} item + * @private + * @since 5.0.0 + */ + scheduleTick: function() { + var me = this; + if (!me.destroyed && !me.timer) { + me.timer = Ext.defer(me.onTick, me.getTickDelay(), me); + } + }, + /** + * Called to indicate that an item needs to be removed from the schedule. This should + * not be called directly. Call the item's `{@link Ext.util.Schedulable#unschedule unschedule}` + * method instead. + * @param {Object} item + * @private + * @since 5.0.0 + */ + unscheduleItem: function(item) { + if (this.scheduledCount) { + --this.scheduledCount; + } + }, + // + //------------------------------------------------------------------------- + // Busy/Idle state tracking + // + /** + * This method should be called when items become busy or idle. These changes are + * useful outside to do things like update modal masks or status indicators. The + * changes are delivered as `busy` and `idle` events. + * + * @param {Number} adjustment Should be `1` or `-1` only to indicate transition to + * busy state or from busy state, respectively. + * @since 5.0.0 + */ + adjustBusy: function(adjustment) { + var me = this, + busyCounter = me.busyCounter + adjustment; + me.busyCounter = busyCounter; + if (busyCounter) { + // If we are now busy but were not previously, fire the busy event immediately + // and update lastBusyCounter. + if (!me.lastBusyCounter) { + me.lastBusyCounter = busyCounter; + me.fireEvent('busy', me); + } + } else if (me.lastBusyCounter && !me.timer) { + // If we are now not busy but were previously, defer this to make sure that + // we don't quickly start with some other activity. + me.scheduleTick(); + } + }, + /** + * Returns `true` if this object contains one or more busy items. + * @return {Boolean} + * @since 5.0.0 + */ + isBusy: function() { + return !this.isIdle(); + }, + /** + * Returns `true` if this object contains no busy items. + * @return {Boolean} + * @since 5.0.0 + */ + isIdle: function() { + return !(this.busyCounter + this.lastBusyCounter); + }, + // + debugHooks: { + $enabled: false, + // Disable by default + onCycleLimitExceeded: function() { + Ext.raise('Exceeded cycleLimit ' + this.getCycleLimit()); + }, + scheduleItem: function(item) { + if (!item) { + Ext.raise('scheduleItem: Invalid argument'); + } + Ext.log('Schedule item: ' + item.getFullName() + ' - ' + (this.scheduledCount + 1)); + if (item.order <= this.notifyIndex) { + Ext.log.warn('Suboptimal order: ' + item.order + ' < ' + this.notifyIndex); + } + this.callParent([ + item + ]); + }, + unscheduleItem: function(item) { + if (!this.scheduledCount) { + Ext.raise('Invalid scheduleCount'); + } + this.callParent([ + item + ]); + Ext.log('Unschedule item: ' + item.getFullName() + ' - ' + this.scheduledCount); + } + } +}); + +/** + * Provides a mechanism to run one or more {@link Ext.data.operation.Operation operations} + * in a given order. Fires the `operationcomplete` event after the completion of each + * Operation, and the `complete` event when all Operations have been successfully executed. + * Fires an `exception` event if any of the Operations encounter an exception. + * + * Usually these are only used internally by {@link Ext.data.proxy.Proxy} classes. + */ +Ext.define('Ext.data.Batch', { + mixins: { + observable: 'Ext.mixin.Observable' + }, + config: { + /** + * @cfg {Boolean} pauseOnException + * True to pause the execution of the batch if any operation encounters an exception + * (defaults to false). If you set this to true you are responsible for implementing the appropriate + * handling logic and restarting or discarding the batch as needed. There are different ways you could + * do this, e.g. by handling the batch's {@link #event-exception} event directly, or perhaps by overriding + * {@link Ext.data.ProxyStore#onBatchException onBatchException} at the store level. If you do pause + * and attempt to handle the exception you can call {@link #retry} to process the same operation again. + * + * Note that {@link Ext.data.operation.Operation operations} are atomic, so any operations that may have succeeded + * prior to an exception (and up until pausing the batch) will be finalized at the server level and will + * not be automatically reversible. Any transactional / rollback behavior that might be desired would have + * to be implemented at the application level. Pausing on exception will likely be most beneficial when + * used in coordination with such a scheme, where an exception might actually affect subsequent operations + * in the same batch and so should be handled before continuing with the next operation. + * + * If you have not implemented transactional operation handling then this option should typically be left + * to the default of false (e.g. process as many operations as possible, and handle any exceptions + * asynchronously without holding up the rest of the batch). + */ + pauseOnException: false + }, + /** + * @property {Number} current + * The index of the current operation being executed. + * @private + */ + current: -1, + /** + * @property {Number} total + * The total number of operations in this batch. + * @private + */ + total: 0, + /** + * @property {Boolean} running + * True if the batch is currently running. + * @private + */ + running: false, + /** + * @property {Boolean} complete + * True if this batch has been executed completely. + * @private + */ + complete: false, + /** + * @property {Boolean} exception + * True if this batch has encountered an exception. This is cleared at the start of each operation. + * @private + */ + exception: false, + /** + * Creates new Batch object. + * @param {Object} [config] Config object + */ + constructor: function(config) { + var me = this; + me.mixins.observable.constructor.call(me, config); + /** + * @event complete + * Fired when all operations of this batch have been completed + * @param {Ext.data.Batch} batch The batch object + * @param {Object} operation The last operation that was executed + */ + /** + * @event exception + * Fired when a operation encountered an exception + * @param {Ext.data.Batch} batch The batch object + * @param {Object} operation The operation that encountered the exception + */ + /** + * @event operationcomplete + * Fired when each operation of the batch completes + * @param {Ext.data.Batch} batch The batch object + * @param {Object} operation The operation that just completed + */ + /** + * Ordered array of operations that will be executed by this batch + * @property {Ext.data.operation.Operation[]} operations + * @private + */ + me.operations = []; + /** + * Ordered array of operations that raised an exception during the most recent + * batch execution and did not successfully complete + * @property {Ext.data.operation.Operation[]} exceptions + */ + me.exceptions = []; + }, + /** + * Adds a new operation to this batch at the end of the {@link #operations} array + * @param {Ext.data.operation.Operation/Ext.data.operation.Operation[]} operation + * The {@link Ext.data.operation.Operation Operation} object or an array of operations. + * @return {Ext.data.Batch} this + */ + add: function(operation) { + var me = this, + i, len; + if (Ext.isArray(operation)) { + for (i = 0 , len = operation.length; i < len; ++i) { + me.add(operation[i]); + } + } else { + me.total++; + operation.setBatch(me); + me.operations.push(operation); + } + return me; + }, + /** + * Sorts the `{@link Ext.data.operation.Operation operations}` based on their type and + * the foreign key dependencies of the entities. Consider a simple Parent and Child + * case where the Child has a "parentId" field. If this batch contains two `create` + * operations, one of a Parent and one for its Child, the server must receive and + * process the `create` of the Parent before the Child can be created. + * + * In the case of `destroy` operations this order is reversed. The Child entity must be + * destroyed before the Parent to avoid any foreign key constraints (a Child with an + * invalid parentId field). + * + * Further, `create` operations must all occur before `update` operations to ensure + * that all entities exist that might be now referenced by the updates. The created + * entities can safely reference already existing entities. + * + * Finally, `destroy` operations are sorted after `update` operations to allow those + * updates to remove references to the soon-to-be-deleted entities. + */ + sort: function() { + this.operations.sort(this.sortFn); + }, + sortFn: function(operation1, operation2) { + var ret = operation1.order - operation2.order; + if (ret) { + return ret; + } + var entityType1 = operation1.entityType, + entityType2 = operation2.entityType, + rank; + // Since the orders are equal, the operations are the same type. Read operations + // have no records, so report equality. + if (!entityType1 || !entityType2) { + return 0; + } + // Otherwise, determine the entity rank for the entities involved in the two + // operations. + if (!(rank = entityType1.rank)) { + // Time to perform the topo-sort based on foreign-key references. + entityType1.schema.rankEntities(); + // Now the rank is available for all entities. + rank = entityType1.rank; + } + return (rank - entityType2.rank) * operation1.foreignKeyDirection; + }, + /** + * Kicks off execution of the batch, continuing from the next operation if the previous + * operation encountered an exception, or if execution was paused. Use this method to start + * the batch for the first time or to restart a paused batch by skipping the current + * unsuccessful operation. + * + * To retry processing the current operation before continuing to the rest of the batch (e.g. + * because you explicitly handled the operation's exception), call {@link #retry} instead. + * + * Note that if the batch is already running any call to start will be ignored. + * @param {Number} [index] (private) + * @return {Ext.data.Batch} this + */ + start: function(index) { + var me = this; + if (!me.operations.length || me.running) { + return me; + } + me.exceptions.length = 0; + me.exception = false; + me.running = true; + return me.runOperation(Ext.isDefined(index) ? index : me.current + 1); + }, + /** + * Kicks off execution of the batch, continuing from the current operation. This is intended + * for restarting a {@link #pause paused} batch after an exception, and the operation that raised + * the exception will now be retried. The batch will then continue with its normal processing until + * all operations are complete or another exception is encountered. + * + * Note that if the batch is already running any call to retry will be ignored. + * + * @return {Ext.data.Batch} this + */ + retry: function() { + return this.start(this.current); + }, + /** + * @private + * Runs the next operation, relative to this.current. + * @return {Ext.data.Batch} this + */ + runNextOperation: function() { + var me = this; + if (me.running) { + me.runOperation(me.current + 1); + } + return me; + }, + /** + * Pauses execution of the batch, but does not cancel the current operation + * @return {Ext.data.Batch} this + */ + pause: function() { + this.running = false; + return this; + }, + /** + * Gets the operations for this batch. + * @return {Ext.data.operation.Operation[]} The operations. + */ + getOperations: function() { + return this.operations; + }, + /** + * Gets any operations that have returned without success in this batch. + * @return {Ext.data.operation.Operation[]} The exceptions + */ + getExceptions: function() { + return this.exceptions; + }, + /** + * Gets the currently running operation. Will return null if the batch has + * not started or is completed. + * @return {Ext.data.operation.Operation} The operation + */ + getCurrent: function() { + var out = null, + current = this.current; + if (!(current === -1 || this.complete)) { + out = this.operations[current]; + } + return out; + }, + /** + * Gets the total number of operations in this batch. + * @return {Number} The total + */ + getTotal: function() { + return this.total; + }, + /** + * Checks if this batch is running. + * @return {Boolean} `true` if this batch is running. + */ + isRunning: function() { + return this.running; + }, + /** + * Checks if this batch is complete. + * @return {Boolean} `true` if this batch is complete. + */ + isComplete: function() { + return this.complete; + }, + /** + * Checks if this batch has any exceptions. + * @return {Boolean} `true` if this batch has any exceptions. + */ + hasException: function() { + return this.exception; + }, + /** + * Executes an operation by its numeric index in the {@link #operations} array + * @param {Number} index The operation index to run + * @return {Ext.data.Batch} this + * + * @private + */ + runOperation: function(index) { + var me = this, + operations = me.operations, + operation = operations[index]; + if (operation === undefined) { + me.running = false; + me.complete = true; + me.fireEvent('complete', me, operations[operations.length - 1]); + } else { + me.current = index; + operation.setInternalCallback(me.onOperationComplete); + operation.setInternalScope(me); + operation.execute(); + } + return me; + }, + onOperationComplete: function(operation) { + var me = this, + exception = operation.hasException(); + if (exception) { + me.exception = true; + me.exceptions.push(operation); + me.fireEvent('exception', me, operation); + } + if (exception && me.getPauseOnException()) { + me.pause(); + } else { + me.fireEvent('operationcomplete', me, operation); + me.runNextOperation(); + } + } +}); + +/** + * This class manages one side of a `Matrix`. + * @private + */ +Ext.define('Ext.data.matrix.Slice', { + constructor: function(side, id) { + /** + * @property {String/Number} id + * The id of the interested entity. Based on whether this slice is on the "left" + * or "right" of the matrix, this id identities the respective entity. + * @readonly + */ + this.id = id; + /** + * @property {Ext.data.matrix.Side} side + * The side of the matrix to which this slice belongs. + */ + this.side = side; + /** + * + */ + this.members = {}; + }, + attach: function(store) { + var me = this; + Ext.Assert.falsey(me.store, 'Store is already attached'); + me.store = store; + store.matrix = me; + store.on('load', me.onStoreLoad, me, { + single: true + }); + }, + commit: function() { + var members = this.members, + id; + for (id in members) { + members[id][2] = 0; + } + }, + onStoreLoad: function(store) { + this.update(store.getData().items, 0); + }, + update: function(recordsOrIds, state) { + if (!(recordsOrIds instanceof Array)) { + Ext.raise('Only array of records or record ids are supported'); + } + var me = this, + MatrixSlice = Ext.data.matrix.Slice, + side = me.side, + assocIndex = side.index, + length = recordsOrIds.length, + id = me.id, + members = me.members, + otherSide = side.inverse, + otherSlices = otherSide.slices, + assoc, call, i, item, otherId, otherSlice, record; + for (i = 0; i < length; ++i) { + call = record = null; + item = recordsOrIds[i]; + otherId = item.isEntity ? (record = item).id : item; + assoc = members[otherId]; + // If we're in a created state and we're asking to remove it, don't move it to + // removed state, just blow it away completely. + if (state < 0 && assoc && assoc[2] === 1) { + delete members[otherId]; + otherSlice = otherSlices[otherId]; + if (otherSlice) { + delete otherSlice.members[id]; + } + call = 1; + } else { + if (!assoc) { + // Note - when we create a new matrix tuple we must catalog it on both + // sides of the matrix or risk losing it on only one side. To gather all + // of the tuples we need only visit one side. + assoc = [ + otherId, + otherId, + state + ]; + assoc[assocIndex] = id; + members[otherId] = assoc; + otherSlice = otherSlices[otherId]; + if (!otherSlice) { + otherSlices[otherId] = otherSlice = new MatrixSlice(otherSide, otherId); + } + otherSlice.members[id] = assoc; + call = 1; + } else if (state !== assoc[2] && state !== 0 && !(state === 1 && assoc[2] === 0)) { + // If they aren't equal and we're setting it to 0, favour the current state, except + // in the case where it's trying to mark as added when we already have it as present + assoc[2] = state; + otherSlice = otherSlices[otherId]; + // because the assoc exists the other side will have a slice + call = 1; + } + } + if (call) { + if (me.notify) { + me.notify.call(me.scope, me, otherId, state); + } + if (otherSlice && otherSlice.notify) { + otherSlice.notify.call(otherSlice.scope, otherSlice, id, state); + } + } + } + }, + updateId: function(newId) { + var me = this, + oldId = me.id, + side = me.side, + slices = side.slices, + slice = slices[oldId], + members = slice.members, + index = side.index, + otherSlices = side.inverse.slices, + assoc, otherId, otherMembers; + me.id = newId; + slices[newId] = slice; + delete slices[oldId]; + for (otherId in members) { + assoc = members[otherId]; + assoc[index] = newId; + otherMembers = otherSlices[otherId].members; + otherMembers[newId] = otherMembers[oldId]; + delete otherMembers[oldId]; + } + }, + destroy: function() { + var me = this, + store = me.store; + if (store) { + store.matrix = null; + store.un('load', me.onStoreLoad, me); + } + me.notify = me.scope = me.store = me.side = me.members = null; + me.callParent(); + } +}); + +/** + * This class manages one side of a `Matrix`. + * @private + */ +Ext.define('Ext.data.matrix.Side', { + requires: [ + 'Ext.data.matrix.Slice' + ], + /** + * @property {Ext.data.matrix.Side} inverse + * Reference to the opposite side of the matrix. + * @readonly + */ + constructor: function(matrix, index, role) { + var me = this; + /** + * @property {Ext.data.matrix.Matrix} matrix + * @readonly + */ + me.matrix = matrix; + /** + * @property {Number} index + * Either 0 or 1 which is the index of our id value in an association entry. + * @readonly + */ + me.index = index; + /** + * @property {Ext.data.schema.Role} role + * The role for this side of the matrix. + * @readonly + */ + me.role = role; + /** + * @property {Object} slices + * Keyed by the id for this side of the matrix to yield a `Slice`. + * @readonly + */ + me.slices = {}; + }, + commit: function() { + var slices = this.slices, + id; + for (id in slices) { + slices[id].commit(); + } + }, + get: function(id1, id2) { + var me = this, + slices = me.slices, + slice = slices[id1] || (slices[id1] = new Ext.data.matrix.Slice(me, id1)); + return (id2 || id2 === 0) ? slice.members[id2] : slice; + }, + update: function(id1, id2, state) { + var slice = this.get(id1); + return slice.update(id2, state); + }, + updateId: function(oldId, newId) { + var slice = this.get(oldId); + if (slice) { + slice.updateId(newId); + } + }, + destroy: function() { + var me = this, + slices = me.slices, + id; + for (id in slices) { + slices[id].destroy(); + } + me.inverse = me.matrix = me.role = me.slices = null; + me.callParent(); + } +}); + +/** + * This class manages a many-to-many matrix for a `Session`. + * @private + */ +Ext.define('Ext.data.matrix.Matrix', { + requires: [ + 'Ext.data.matrix.Side' + ], + /** + * @property {Ext.data.schema.ManyToMany} association + * The `ManyToMany` association for this matrix. + * @readonly + */ + /** + * @property {Ext.data.Session} session + * The `Session` owning this matrix. + * @readonly + */ + /* + * data: [ + * [ leftId, rightId, -1/0/1 ], // === DELETED/UNMODIFIED/ADDED + * ... + * ], + * + * left: new Ext.data.matrix.Side({ + * matrix: me, + * index: 0, + * inverse: right, + * slices: { + * leftId: new Ext.data.matrix.Slice({ + * id: leftId, + * side: left, + * members: { + * rightId: data[0] + * } + * }) + * } + * }, + * + * right: new Ext.data.matrix.Side({ + * matrix: me, + * index: 1, + * inverse: left, + * slices: { + * rightId: new Ext.data.matrix.Slice({ + * id: rightId, + * side: right, + * members: { + * leftId: data[0] + * } + * }) + * }) + * } + */ + constructor: function(session, matrix) { + var me = this, + association = matrix.isManyToMany ? matrix : session.getSchema().getAssociation(matrix), + Side = Ext.data.matrix.Side, + left = new Side(me, 0, association.left), + right = new Side(me, 1, association.right); + Ext.Assert.truthy(association.isManyToMany, 'Association is not many-to-many'); + me.association = association; + me.session = session; + me.left = left; + me.right = right; + left.inverse = right; + right.inverse = left; + }, + commit: function() { + this.left.commit(); + this.right.commit(); + }, + update: function(id1, id2, state) { + return this.left.update(id1, id2, state); + }, + updateId: function(record, oldId, newId) { + var Type = record.self, + left = this.left, + right = this.right, + matchSide; + // Are we interested in this record? Check types + if (Type === left.role.cls) { + matchSide = left; + } + if (Type === right.role.cls) { + matchSide = right; + } + if (matchSide) { + matchSide.updateId(oldId, newId); + } + }, + destroy: function() { + var me = this; + me.left.destroy(); + me.right.destroy(); + me.association = me.session = me.left = me.right = null; + me.callParent(); + } +}); + +/** + * This class is used internally by `{@link Ext.data.Session#getChanges}` to build + * up an object describing changes in the session. It is not intended for public use but + * can be used as an example of the visitor `{@link Ext.data.Session#visitData}` + * requires. + * @protected + * @since 5.0.0 + */ +Ext.define('Ext.data.session.ChangesVisitor', { + constructor: function(session) { + var me = this, + crud; + me.session = session; + crud = session.getCrudProperties(); + me.result = null; + me.writerOptions = {}; + /* + * Keyed by the $className of a Model, e.g. "Foo", and to cache data from + * Foo.getProxy().getWriter (called "writer" in the pseudo code below): + * + * Foo: { + * drop: { + * all: writer.getWriteAllFields(), + * }, + * allDataOptions: Ext.apply(Ext.Object.chain(writer.getAllDataOptions()), { + * serialize: true + * }), + * partialDataOptions: Ext.apply(Ext.Object.chain(writer.getPartialDataOptions()), { + * serialize: true + * }) + * } + */ + me.createKey = crud.create; + me.readKey = crud.read; + me.updateKey = crud.update; + me.dropKey = crud.drop; + }, + onDirtyRecord: function(record) { + var me = this, + crud = me.crud, + created = record.phantom, + dropped = record.dropped, + updated = !created && !dropped, + type = record.$className, + prop = (created || dropped) ? 'allDataOptions' : 'partialDataOptions', + writerOptions = me.writerOptions, + name = record.entityName, + options, bucket, entry, result; + if (created && dropped) { + return false; + } + crud = created ? me.createKey : (dropped ? me.dropKey : me.updateKey); + writerOptions = writerOptions[type] || (writerOptions[type] = {}); + if (dropped) { + // If the Writer says "writeAllFields" then we want to use allDataOptions + // for the prop (set already). Otherwise we just want to encode the id. + if (!(options = writerOptions.drop)) { + writerOptions.drop = options = { + all: record.getProxy().getWriter().getWriteAllFields() + }; + } + if (!options.all) { + entry = record.id; + } + } + // else entry is unset so we'll ask for the prop and call record.getData + if (!entry) { + // Consult the Writer for the entity to determine its preferences for writing + // complete or partial data. We rely on the serialization of the record's + // getData method whereas the Writer has its own ideas on the matter. + if (!(options = writerOptions[prop])) { + options = record.getProxy().getWriter().getConfig(prop); + writerOptions[prop] = options = Ext.Object.chain(options); + me.setupOptions(options); + } + entry = record.getData(options); + } + // User: { + // C: [ + // { id: 20, name: 'Don' } + // ], + // U: [ + // { id: 30, name: 'Don' } + // ], + // D: [ 40, 50 ] + // } + result = me.result || (me.result = {}); + bucket = result[name] || (result[name] = {}); + bucket = bucket[crud] || (bucket[crud] = []); + bucket.push(entry); + }, + setupOptions: function(options) { + options.serialize = true; + }, + onMatrixChange: function(association, id1, id2, state) { + var me = this, + name = association.left.type, + // e.g., "User" + assocName = association.right.role, + // e.g., "groups" + operation = state < 0 ? me.dropKey : me.createKey, + bucket, result; + // User: { + // groups: { + // C: { + // 20: [ 30, 40 ] // associate User 20 w/Groups 30 & 40 + // }, + // D: { + // 10: [ 50 ] // disassociate User 10 w/Group 50 + // } + // } + // } + result = me.result || (me.result = {}); + bucket = result[name] || (result[name] = {}); + // User + bucket = bucket[assocName] || (bucket[assocName] = {}); + // groups + bucket = bucket[operation] || (bucket[operation] = {}); + // C or D + bucket = bucket[id1] || (bucket[id1] = []); + bucket.push(id2); + } +}); + +/** + * This visitor class adds extra capability to consider changes as + * they would be considered for a parent session. + * @protected + * @since 5.0.0 + */ +Ext.define('Ext.data.session.ChildChangesVisitor', { + extend: 'Ext.data.session.ChangesVisitor', + constructor: function() { + this.seen = {}; + this.callParent(arguments); + }, + setupOptions: function(options) { + this.callParent([ + options + ]); + options.serialize = false; + }, + onDirtyRecord: function(record) { + if (this.callParent(arguments) !== false) { + // We have a record that we have updated in ourselves, but not in the parent. + // We need to read it in + if (!record.$source && (record.dropped || !record.phantom)) { + this.readEntity(record); + } + } + }, + readEntity: function(record) { + var me = this, + readKey = me.readKey, + name = record.entityName, + id = record.id, + seen = me.seen, + seenKey = name + id, + result, bucket; + // Already read it, jump out + if (seen[seenKey]) { + return; + } + seen[seenKey] = true; + result = me.result || (me.result = {}); + bucket = result[name] || (result[name] = {}); + bucket = bucket[readKey] || (bucket[readKey] = []); + bucket.push(Ext.apply({}, record.modified, record.data)); + } +}); + +/** + * This class is used internally by `{@link Ext.data.Session#getSaveBatch}` and is + * not intended for direct use. It can be studied as an example of implementing a visitor + * to pass to `{@link Ext.data.Session#visitData}`. + * @protected + * @since 5.0.0 + */ +Ext.define('Ext.data.session.BatchVisitor', { + map: null, + constructor: function(batch) { + this.batch = batch; + }, + getBatch: function(sort) { + var map = this.map, + batch = this.batch, + bucket, entity, name, operation, operationType, proxy, batchActions, records, len, i; + if (map) { + if (!batch) { + batch = new Ext.data.Batch(); + } + for (name in map) { + bucket = map[name]; + entity = bucket.entity; + // the entity class + proxy = entity.getProxy(); + batchActions = proxy.getBatchActions(); + delete bucket.entity; + // so we don't think its an operation + for (operationType in bucket) { + if (batchActions) { + operation = proxy.createOperation(operationType, { + records: bucket[operationType] + }); + operation.entityType = entity; + batch.add(operation); + } else { + records = bucket[operationType]; + for (i = 0 , len = records.length; i < len; ++i) { + operation = proxy.createOperation(operationType, { + records: [ + records[i] + ] + }); + operation.entityType = entity; + batch.add(operation); + } + } + } + } + } + if (batch && sort !== false) { + batch.sort(); + } + return batch; + }, + onDirtyRecord: function(record) { + var me = this, + operation = record.phantom ? 'create' : (record.dropped ? 'destroy' : 'update'), + name = record.$className, + map = (me.map || (me.map = {})), + bucket = (map[name] || (map[name] = { + entity: record.self + })); + // User: { + // entity: User, + // create: [ + // { id: 20, name: 'Don' } + // ] + // } + bucket = bucket[operation] || (bucket[operation] = []); + bucket.push(record); + } +}); + +/** + * This mixin provides a `dirty` config that tracks the modified state of an object. If + * the class using this mixin is {@link Ext.mixin.Observable observable}, changes to the + * `dirty` config will fire the `dirtychange` event. + * @protected + * @since 6.2.0 + */ +Ext.define('Ext.mixin.Dirty', { + mixinId: 'dirty', + /** + * @event dirtychange + * Fires when a change in the object's {@link #cfg-dirty} state is detected. + * + * **Note:** In order for this event to fire, the class that mixes in this mixin + * must be `{@link Ext.mixin.Observable Observable}`. + * + * @param {Ext.Base} this + * @param {Boolean} dirty Whether or not the object is now dirty. + */ + config: { + /** + * @cfg {Boolean} dirty + * This config property describes the modified state of this object. In most + * cases this config's value is maintained by the object and should be considered + * readonly. The class implementor should be the only one to call the setter. + */ + dirty: { + $value: false, + lazy: true + } + }, + dirty: false, + // on the prototype as false (not undefined) + /** + * @property {Number} _dirtyRecordCount + * The number of newly created, modified or dropped records. + * @private + * @readonly + */ + _dirtyRecordCount: 0, + /** + * @cfg {Boolean} ignoreDirty + * This config property indicates that the `dirty` state of this object should be + * ignored. Because this capability is mixed in at a class level, this config can + * be helpful when some instances do not participate in dirty state tracking. + * + * This option should be set at construction time. When set to `true`, the object + * will always have `dirty` value of `false`. + */ + ignoreDirty: false, + /** + * @cfg {Boolean} recordStateIsDirtyState + * Set this config at construction time (or on the class body) to automatically set + * the `dirty` state based on the records passed to `trackRecordState`. + * + * This config defaults to `true` but only has an effect when the record tracking + * methods are called (`trackRecordState`, `untrackRecordState` and `clearRecordStates`). + * @protected + */ + recordStateIsDirtyState: true, + /** + * Returns `true` if this object is `dirty`. + */ + isDirty: function() { + // This alias matches the Ext.form.field.* family. + return this.getDirty(); + }, + applyDirty: function(dirty) { + return this.ignoreDirty ? false : dirty; + }, + updateDirty: function(dirty) { + var me = this; + // Store the property directly in case we are used in an "_dirty" world. + me.dirty = dirty; + if (me.fireEvent && !me.isDirtyInitializing) { + me.fireDirtyChange(); + } + }, + /** + * Clears all record state tracking. This state is maintained by `trackRecordState` + * and `untrackRecordState`. + * @protected + */ + clearRecordStates: function() { + var me = this, + counters = me._crudCounters; + if (counters) { + counters.C = counters.U = counters.D = 0; + } + me._dirtyRecordCount = 0; + if (me.recordStateIsDirtyState) { + me.setDirty(false); + } + }, + fireDirtyChange: function() { + var me = this; + if (!me.ignoreDirty && me.hasListeners.dirtychange) { + me.fireEvent('dirtychange', me, me.dirty); + } + }, + /** + * This method is called to track a given record in the total number of dirty records + * (modified, created or dropped). See `untrackRecordState` and `clearRecordStates`. + * + * @param {Ext.data.Model} record The record to track. + * @param {Boolean} initial Pass `true` the first time a record is introduced. + * @return {Boolean} Returns `true` if the state of dirty records has changed. + * @protected + */ + trackRecordState: function(record, initial) { + var me = this, + counters = me._crudCounters || (me._crudCounters = { + C: 0, + R: 0, + U: 0, + D: 0 + }), + dirtyRecordCountWas = me._dirtyRecordCount, + state = record.crudState, + stateWas = record.crudStateWas, + changed, dirtyRecordCount; + if (initial || state !== stateWas) { + if (!initial && stateWas) { + --counters[stateWas]; + } + if (!(record.phantom && state === 'D')) { + ++counters[state]; + } + me.checkCounters(); + me._dirtyRecordCount = dirtyRecordCount = counters.C + counters.U + counters.D; + changed = !dirtyRecordCount !== !dirtyRecordCountWas; + if (changed && me.recordStateIsDirtyState) { + me.setDirty(dirtyRecordCount > 0); + } + } + return changed; + }, + /** + * This method is called to remove the tracking of a given record from the total number + * of dirty records (modified, created or dropped). The record passed to this method + * must have been previously passed to `trackRecordState`. + * + * @param {Ext.data.Model} record The record to stop tracking. + * @return {Boolean} Returns `true` if the state of dirty records has changed. + * @protected + */ + untrackRecordState: function(record) { + var me = this, + counters = me._crudCounters, + dirtyRecordCountWas = me._dirtyRecordCount, + state = record.crudState, + changed, dirtyRecordCount; + // If it's erased and dropped, it will have already been tracked + if (counters && state !== 'D' && !record.erased) { + --counters[state]; + me.checkCounters(); + me._dirtyRecordCount = dirtyRecordCount = counters.C + counters.U + counters.D; + changed = !dirtyRecordCount !== !dirtyRecordCountWas; + if (changed && me.recordStateIsDirtyState) { + me.setDirty(dirtyRecordCount > 0); + } + } + return changed; + }, + checkCounters: function() { + var counters = this._crudCounters, + key; + for (key in counters) { + if (counters[key] < 0) { + Ext.raise('Invalid state for ' + key); + } + } + } +}); + +/** + * This class manages models and their associations. Instances of `Session` are typically + * associated with some `Component` (perhaps the Viewport or a Window) and then used by + * their `{@link Ext.app.ViewModel view models}` to enable data binding. + * + * The primary job of a Session is to manage a collection of records of many different + * types and their associations. This often starts by loading records when requested (via + * bind - see below) and culminates when it is time to save to the server. + * + * Because the Session tracks all records it loads, it ensures that for any given type of + * model, only one record exists with a given `id`. This means that all edits of that + * record are properly targeted at that one instance. + * + * Similarly, when associations are loaded, the `Ext.data.Store` created to hold the + * associated records is tracked by the Session. So all requests for the "OrderItems" of + * a particular Order id will result in the same Store. Adding and removing items from + * that Order then is sure to remain consistent. + * + * # Data + * + * Since the Session is managing all this data, there are several methods it provides + * to give convenient access to that data. The most important of these is `update` and + * `getChanges`. + * + * The `update` and `getChanges` methods both operate on object that contains a summary + * of records and associations and different CRUD operations. + * + * ## Saving + * + * There are two basic ways to save the contents of a Session: `getChanges` and + * `getSaveBatch`. We've already seen `getChanges`. The data contained in the CRUD object + * can be translated into whatever shape is needed by the server. + * + * To leverage the `{@link Ext.data.Model#proxy proxy}` facilities defined by each Model + * class, there is the `getSaveBatch` method. That method returns an `Ext.data.Batch` + * object populated with the necessary `create`, `update` and `destory` operations to + * save all of the changes in the Session. + * + * ## Conflicts + * + * If data is loaded from the server (for example a store load) and there is an existing record, + * the {@link Ext.data.Model#method-mergeData `mergeData`} method will be called to resolve the conflict. + * + * @since 5.0.0 + */ +Ext.define('Ext.data.Session', { + requires: [ + 'Ext.data.schema.Schema', + 'Ext.data.Batch', + 'Ext.data.matrix.Matrix', + 'Ext.data.session.ChangesVisitor', + 'Ext.data.session.ChildChangesVisitor', + 'Ext.data.session.BatchVisitor' + ], + mixins: [ + 'Ext.mixin.Dirty', + 'Ext.mixin.Observable' + ], + isSession: true, + config: { + /** + * @cfg {String/Ext.data.schema.Schema} schema + */ + schema: 'default', + /** + * @cfg {Ext.data.Session} parent + * The parent session for this session. + */ + parent: null, + /** + * @cfg {Boolean} autoDestroy + * `true` to automatically destroy this session when a component it is attached + * to is destroyed. This should be set to false if the session is intended to be + * used across multiple root level components. + * + * @since 5.0.1 + */ + autoDestroy: true, + crudProperties: { + create: 'C', + read: 'R', + update: 'U', + drop: 'D' + } + }, + crudOperations: [ + { + type: 'R', + entityMethod: 'readEntities' + }, + { + type: 'C', + entityMethod: 'createEntities' + }, + { + type: 'U', + entityMethod: 'updateEntities' + }, + { + type: 'D', + entityMethod: 'dropEntities' + } + ], + crudKeys: { + C: 1, + R: 1, + U: 1, + D: 1 + }, + statics: { + nextId: 1 + }, + constructor: function(config) { + var me = this; + /* + * { + * User: { + * 1: { + * record: user1Instance, + * refs: { + * posts: { + * 101: post101Instance, + * 102: post202Instance + * } + * } + * } + * } + * } + */ + me.data = {}; + /* + * { + * UserGroups: new Ext.data.matrix.Matrix({ + * association: UserGroups + * }) + * } + */ + me.matrices = {}; + me.id = Ext.data.Session.nextId++; + me.identifierCache = {}; + // Bind ourselves so we're always called in our own scope. + me.recordCreator = me.recordCreator.bind(me); + me.mixins.observable.constructor.call(me, config); + }, + destroy: function() { + var me = this, + matrices = me.matrices, + data = me.data, + entityName, entities, record, id; + for (id in matrices) { + matrices[id].destroy(); + } + for (entityName in data) { + entities = data[entityName]; + for (id in entities) { + record = entities[id].record; + if (record) { + // Clear up any source if we pushed one on, remove + // the session reference + record.$source = null; + // While we don't actually call join() for the session, we need to + // tell the records that they are being detached from the session in + // some way. + record.unjoin(me); + } + } + } + // see also evict() + me.identifierCache = me.recordCreator = me.matrices = me.data = null; + me.setSchema(null); + me.callParent(); + }, + /** + * Adds an existing record instance to the session. The record + * may not belong to another session. The record cannot be a phantom record, instead + * use {@link #createRecord}. + * @param {Ext.data.Model} record The record to adopt. + */ + adopt: function(record) { + var me = this, + associations = record.associations, + roleName; + me.checkModelType(record.self); + if (record.session && record.session !== me) { + Ext.raise('Record already belongs to an existing session'); + } + if (record.session !== me) { + me.add(record); + if (associations) { + for (roleName in associations) { + associations[roleName].adoptAssociated(record, me); + } + } + } + }, + /** + * Marks the session as "clean" by calling {@link Ext.data.Model#commit} on each record + * that is known to the session. + * + * - Phantom records will no longer be phantom. + * - Modified records will no longer be dirty. + * - Dropped records will be erased. + * + * @since 5.1.0 + */ + commit: function() { + var me = this, + data = me.data, + matrices = me.matrices, + dirtyWas = me.getDirty(), + entityName, entities, id, record; + me.suspendEvent('dirtychange'); + for (entityName in data) { + entities = data[entityName]; + for (id in entities) { + record = entities[id].record; + if (record) { + record.commit(); + } + } + } + for (id in matrices) { + matrices[id].commit(); + } + me.clearRecordStates(); + me.resumeEvent('dirtychange'); + if (me.getDirty() !== dirtyWas) { + me.fireDirtyChange(); + } + }, + /** + * Creates a new record and tracks it in this session. + * + * @param {String/Ext.Class} type The `entityName` or the actual class of record to create. + * @param {Object} [data] The data for the record. + * @param {Boolean} [preventAdd] (private) `true` to prevent the record from being added to the session + * @return {Ext.data.Model} The new record. + */ + createRecord: function(type, data, preventAdd) { + this.checkModelType(type); + var Model = type.$isClass ? type : this.getSchema().getEntity(type), + parent = this.getParent(), + id; + // If we have no data, we're creating a phantom + if (data && parent) { + id = Model.getIdFromData(data); + if (parent.peekRecord(Model, id)) { + Ext.raise('A parent session already contains an entry for ' + Model.entityName + ': ' + id); + } + } + // By passing the session to the constructor, it will call session.add() + return new Model(data, preventAdd ? null : this); + }, + /** + * Returns an object describing all of the modified fields, created or dropped records + * and many-to-many association changes maintained by this session. + * + * @return {Object} An object in the CRUD format (see the intro docs). `null` if there are no changes. + */ + getChanges: function() { + var visitor = new Ext.data.session.ChangesVisitor(this); + this.visitData(visitor); + return visitor.result; + }, + /** + * The same functionality as {@link #getChanges}, however we also take into account our + * parent session. + * + * @return {Object} An object in the CRUD format (see the intro docs). `null` if there are no changes. + * + * @protected + */ + getChangesForParent: function() { + var visitor = new Ext.data.session.ChildChangesVisitor(this); + this.visitData(visitor); + return visitor.result; + }, + /** + * Get a cached record from the session. If the record does not exist, it will + * be created. If the `autoLoad` parameter is not set to `false`, the record will + * be loaded via the {@link Ext.data.Model#proxy proxy} of the Model. + * + * If this session is configured with a `{@link #parent}` session, a *copy* of any existing record + * in the `parent` will be adopted into this session. If the `parent` does not contain the record, + * the record will be created and *not* inserted into the parent. + * + * See also {@link #peekRecord}. + * + * @param {String/Ext.Class/Ext.data.Model} type The `entityName` or the actual class of record to create. + * This may also be a record instance, where the type and id will be inferred from the record. If the record is + * not attached to a session, it will be adopted. If it exists in a parent, an appropriate copy will be made as + * described. + * @param {Object} id The id of the record. + * @param {Boolean/Object} [autoLoad=true] `false` to prevent the record from being loaded if + * it does not exist. If this parameter is an object, it will be passed to the {@link Ext.data.Model#method!load} call. + * @return {Ext.data.Model} The record. + */ + getRecord: function(type, id, autoLoad) { + var me = this, + wasInstance = type.isModel, + record, Model, parent, parentRec; + if (wasInstance) { + wasInstance = type; + id = type.id; + type = type.self; + } + record = me.peekRecord(type, id); + if (!record) { + Model = type.$isClass ? type : me.getSchema().getEntity(type); + parent = me.getParent(); + if (parent) { + parentRec = parent.peekRecord(Model, id); + } + if (parentRec) { + if (parentRec.isLoading()) { + // If the parent is loading, it's as though it doesn't have + // the record, so we can't copy it, but we don't want to + // adopt it either. + wasInstance = false; + } else { + record = parentRec.copy(undefined, me); + record.$source = parentRec; + } + } + if (!record) { + if (wasInstance) { + record = wasInstance; + me.adopt(record); + } else { + record = Model.createWithId(id, null, me); + if (autoLoad !== false) { + record.load(Ext.isObject(autoLoad) ? autoLoad : undefined); + } + } + } + } + return record; + }, + /** + * Returns an `Ext.data.Batch` containing the `Ext.data.operation.Operation` instances + * that are needed to save all of the changes in this session. This sorting is based + * on operation type, associations and foreign keys. Generally speaking the operations + * in the batch can be committed to a server sequentially and the server will never be + * sent a request with an invalid (client-generated) id in a foreign key field. + * + * @param {Boolean} [sort=true] Pass `false` to disable the batch operation sort. + * @return {Ext.data.Batch} + */ + getSaveBatch: function(sort) { + var visitor = new Ext.data.session.BatchVisitor(); + this.visitData(visitor); + return visitor.getBatch(sort); + }, + /** + * Triggered when an associated item from {@link #update} references a record + * that does not exist in the session. + * @param {Ext.Class} entityType The entity type. + * @param {Object} id The id of the model. + * + * @protected + * @template + */ + onInvalidAssociationEntity: function(entityType, id) { + Ext.raise('Unable to read association entity: ' + this.getModelIdentifier(entityType, id)); + }, + /** + * Triggered when an drop block from {@link #update} tries to create a record + * that already exists. + * @param {Ext.Class} entityType The entity type. + * @param {Object} id The id of the model. + * + * @protected + * @template + */ + onInvalidEntityCreate: function(entityType, id) { + Ext.raise('Cannot create, record already not exists: ' + this.getModelIdentifier(entityType, id)); + }, + /** + * Triggered when an drop block from {@link #update} references a record + * that does not exist in the session. + * @param {Ext.Class} entityType The entity type. + * @param {Object} id The id of the model. + * + * @protected + * @template + */ + onInvalidEntityDrop: function(entityType, id) { + Ext.raise('Cannot drop, record does not exist: ' + this.getModelIdentifier(entityType, id)); + }, + /** + * Triggered when an drop block from {@link #update} tries to create a record + * that already exists. + * @param {Ext.Class} entityType The entity type. + * @param {Object} id The id of the model. + * + * @protected + * @template + */ + onInvalidEntityRead: function(entityType, id) { + Ext.raise('Cannot read, record already not exists: ' + this.getModelIdentifier(entityType, id)); + }, + /** + * Triggered when an update block from {@link #update} references a record + * that does not exist in the session. + * @param {Ext.Class} entityType The entity type. + * @param {Object} id The id of the model. + * @param {Boolean} dropped `true` if the record was dropped. + * + * @protected + * @template + */ + onInvalidEntityUpdate: function(entityType, id, dropped) { + if (dropped) { + Ext.raise('Cannot update, record dropped: ' + this.getModelIdentifier(entityType, id)); + } else { + Ext.raise('Cannot update, record does not exist: ' + this.getModelIdentifier(entityType, id)); + } + }, + /** + * Gets an existing record from the session. The record will *not* be created if it does + * not exist. + * + * See also: {@link #getRecord}. + * + * @param {String/Ext.Class} type The `entityName` or the actual class of record to create. + * @param {Object} id The id of the record. + * @param {Boolean} [deep=false] `true` to consult + * @return {Ext.data.Model} The record, `null` if it does not exist. + */ + peekRecord: function(type, id, deep) { + // Duplicate some of this logic from getEntry here to prevent the creation + // of entries when asking for the existence of records. We may not need them + this.checkModelType(type); + var entityType = type.$isClass ? type : this.getSchema().getEntity(type), + entityName = entityType.entityName, + entry = this.data[entityName], + ret, parent; + entry = entry && entry[id]; + ret = entry && entry.record; + if (!ret && deep) { + parent = this.getParent(); + ret = parent && parent.peekRecord(type, id, deep); + } + return ret || null; + }, + /** + * Save any changes in this session to a {@link #parent} session. + */ + save: function() { + var me = this, + parent = me.getParent(), + visitor; + if (parent) { + visitor = new Ext.data.session.ChildChangesVisitor(me); + me.visitData(visitor); + parent.update(visitor.result); + me.commit(); + } else { + Ext.raise('Cannot commit session, no parent exists'); + } + }, + /** + * Create a child session with this session as the {@link #parent}. + * @return {Ext.data.Session} The copied session. + */ + spawn: function() { + return new this.self({ + schema: this.getSchema(), + parent: this + }); + }, + /** + * Complete a bulk update for this session. + * @param {Object} data Data in the CRUD format (see the intro docs). + */ + update: function(data) { + var me = this, + schema = me.getSchema(), + crudOperations = me.crudOperations, + len = crudOperations.length, + crudKeys = me.crudKeys, + dirtyWas = me.getDirty(), + entityName, entityType, entityInfo, i, operation, item, associations, key, role, associationData; + me.suspendEvent('dirtychange'); + // Force the schema to process any pending drops + me.getSchema().processKeyChecks(true); + // Do a first pass to setup all the entities first + for (entityName in data) { + entityType = schema.getEntity(entityName); + if (!entityType) { + Ext.raise('Invalid entity type: ' + entityName); + } + entityInfo = data[entityName]; + for (i = 0; i < len; ++i) { + operation = crudOperations[i]; + item = entityInfo[operation.type]; + if (item) { + me[operation.entityMethod](entityType, item); + } + } + } + // A second pass to process associations once we have all the entities in place + for (entityName in data) { + entityType = schema.getEntity(entityName); + associations = entityType.associations; + entityInfo = data[entityName]; + for (key in entityInfo) { + // Skip over CRUD, just looking for associations here + if (crudKeys[key]) { + + continue; + } + role = associations[key]; + if (!role) { + Ext.raise('Invalid association key for ' + entityName + ', "' + key + '"'); + } + associationData = entityInfo[role.role]; + role.processUpdate(me, associationData); + } + } + me.resumeEvent('dirtychange'); + if (me.getDirty() !== dirtyWas) { + me.fireDirtyChange(); + } + }, + //------------------------------------------------------------------------- + /** + * Template method, will be called by Model after a record is committed. + * @param {Ext.data.Model} record The record. + * + * @protected + * @since 6.2.0 + */ + afterCommit: function(record) { + this.trackRecordState(record); + }, + /** + * Template method, will be called by Model after a record is dropped. + * @param {Ext.data.Model} record The record. + * + * @protected + * @since 6.2.0 + */ + afterDrop: function(record) { + this.trackRecordState(record); + }, + /** + * Template method, will be called by Model after a record is edited. + * @param {Ext.data.Model} record The record. + * + * @protected + * @since 6.2.0 + */ + afterEdit: function(record) { + this.trackRecordState(record); + }, + /** + * Template method, will be called by Model after a record is erased (a drop + * that is committed). + * @param {Ext.data.Model} record The record. + * + * @protected + */ + afterErase: function(record) { + this.evict(record); + }, + /** + * Template method, will be called by Model after a record is rejected. + * @param {Ext.data.Model} record The record. + * + * @protected + * @since 6.5.1 + */ + afterReject: function(record) { + this.trackRecordState(record); + }, + privates: { + /** + * Add a record instance to this session. Called by model. + * @param {Ext.data.Model} record The record. + * + * @private + */ + add: function(record) { + var me = this, + id = record.id, + entry = me.getEntry(record.self, id), + associations, roleName; + if (entry.record) { + Ext.raise('Duplicate id ' + record.id + ' for ' + record.entityName); + } + record.session = me; + entry.record = record; + me.trackRecordState(record, true); + me.registerReferences(record); + associations = record.associations; + for (roleName in associations) { + associations[roleName].checkMembership(me, record); + } + }, + /** + * @private + */ + applySchema: function(schema) { + return Ext.data.schema.Schema.get(schema); + }, + /** + * Checks if the model type being referenced is valid for this session. That includes checking + * if the model name is correct & is one used in this {@link #schema} for this session. Will raise + * an exception if the model type is not correct. + * @param {String/Ext.Class} name The model name or model type. + * + * @private + */ + checkModelType: function(name) { + if (name.$isClass) { + name = name.entityName; + } + if (!name) { + Ext.raise('Unable to use anonymous models in a Session'); + } else if (!this.getSchema().getEntity(name)) { + Ext.raise('Unknown entity type ' + name); + } + }, + /** + * Process a create block of entities from the {@link #update} method. + * @param {Ext.Class} entityType The entity type. + * @param {Object[]} items The data objects to create. + * + * @private + */ + createEntities: function(entityType, items) { + var me = this, + len = items.length, + i, data, rec, id; + for (i = 0; i < len; ++i) { + data = items[i]; + id = entityType.getIdFromData(data); + rec = me.peekRecord(entityType, id); + if (!rec) { + // Wait until after creating the record before adding it to the session, + // instead of allowing the Model constructor to call session.add(). + // This allows us to first initialize the phantom and crudState properties. + // so that the session sets its dirty state correctly when add() is called. + // The Model constructor usually handles setting phantom/crudState, + // but in this case it will not detect the record as phantom because + // we are passing an id (generated by the child session) to the Model + // constructor. + rec = me.createRecord(entityType, data, true); + rec.phantom = true; + rec.crudState = 'C'; + me.add(rec); + // Be sure to set this after "notifying" the session. + rec.crudStateWas = 'C'; + } else { + me.onInvalidEntityCreate(entityType, id); + } + } + }, + /** + * Process a drop block for entities from the {@link #update} method. + * @param {Ext.Class} entityType The entity type. + * @param {Object[]} ids The identifiers of the items to drop. + * + * @private + */ + dropEntities: function(entityType, ids) { + var len = ids.length, + i, rec, id, extractId; + if (len) { + // Handle writeAllFields here, we may not have an array of raw ids + extractId = Ext.isObject(ids[0]); + } + for (i = 0; i < len; ++i) { + id = ids[i]; + if (extractId) { + id = entityType.getIdFromData(id); + } + rec = this.peekRecord(entityType, id); + if (rec) { + rec.drop(); + } else { + this.onInvalidEntityDrop(entityType, id); + } + } + }, + /** + * Remove a record and any references from the session. + * @param {Ext.data.Model} record The record + * + * @private + */ + evict: function(record) { + var me = this, + entityName = record.entityName, + entities = me.data[entityName], + id = record.id; + if (entities && entities[id]) { + me.untrackRecordState(record); + // While we don't actually call join() for the session, we need to + // tell the records that they are being detached from the session in + // some way. + record.unjoin(me); + delete entities[id]; + } + }, + // see also destroy() + /** + * Transforms a list of ids into a list of records for a particular type. + * @param {Ext.Class} entityType The entity type. + * @param {Object[]} ids The ids to transform. + * @return {Ext.data.Model[]} The models corresponding to the ids. + */ + getEntityList: function(entityType, ids) { + var len = ids.length, + i, id, rec, invalid; + for (i = 0; i < len; ++i) { + id = ids[i]; + rec = this.peekRecord(entityType, id); + if (rec) { + ids[i] = rec; + } else { + invalid = true; + ids[i] = null; + this.onInvalidAssociationEntity(entityType, id); + } + } + if (invalid) { + ids = Ext.Array.clean(ids); + } + return ids; + }, + /** + * Return an entry for the data property for a particular type/id. + * @param {String/Ext.Class} type The entity name or model type. + * @param {Object} id The id of the record + * @return {Object} The data entry. + * + * @private + */ + getEntry: function(type, id) { + if (type.isModel) { + id = type.getId(); + type = type.self; + } + var entityType = type.$isClass ? type : this.getSchema().getEntity(type), + entityName = entityType.entityName, + data = this.data, + entry; + entry = data[entityName] || (data[entityName] = {}); + entry = entry[id] || (entry[id] = {}); + return entry; + }, + getRefs: function(record, role, includeParent) { + var entry = this.getEntry(record), + refs = entry && entry.refs && entry.refs[role.role], + parent = includeParent && this.getParent(), + parentRefs, id, rec; + if (parent) { + parentRefs = parent.getRefs(record, role); + if (parentRefs) { + for (id in parentRefs) { + rec = parentRefs[id]; + if ((!refs || !refs[id])) { + // We don't know about this record but the parent does. We need to + // pull it down so it may be edited as part of the collection + this.getRecord(rec.self, rec.id); + } + } + // Recalculate our refs after we pull down all the required records + refs = entry && entry.refs && entry.refs[role.role]; + } + } + return refs || null; + }, + getIdentifier: function(entityType) { + var parent = this.getParent(), + cache, identifier, key, ret; + if (parent) { + ret = parent.getIdentifier(entityType); + } else { + cache = this.identifierCache; + identifier = entityType.identifier; + key = identifier.getId() || entityType.entityName; + ret = cache[key]; + if (!ret) { + if (identifier.clone) { + ret = identifier.clone({ + id: null + }); + } else { + ret = identifier; + } + cache[key] = ret; + } + } + return ret; + }, + getMatrix: function(matrix, preventCreate) { + var name = matrix.isManyToMany ? matrix.name : matrix, + matrices = this.matrices, + ret; + ret = matrices[name]; + if (!ret && !preventCreate) { + ret = matrices[name] = new Ext.data.matrix.Matrix(this, matrix); + } + return ret || null; + }, + getMatrixSlice: function(role, id) { + var matrix = this.getMatrix(role.association), + side = matrix[role.side]; + return side.get(id); + }, + /** + * Gets a user friendly identifier for a Model. + * @param {Ext.Class} entityType The entity type. + * @param {Object} id The id of the entity. + * @return {String} The identifier. + */ + getModelIdentifier: function(entityType, id) { + return id + '@' + entityType.entityName; + }, + onIdChanged: function(record, oldId, newId) { + var me = this, + matrices = me.matrices, + entityName = record.entityName, + id = record.id, + bucket = me.data[entityName], + entry = bucket[oldId], + associations = record.associations, + refs = entry.refs, + setNoRefs = me._setNoRefs, + association, fieldName, matrix, refId, role, roleName, roleRefs, key; + if (bucket[newId]) { + Ext.raise('Cannot change ' + entityName + ' id from ' + oldId + ' to ' + newId + ' id already exists'); + } + delete bucket[oldId]; + bucket[newId] = entry; + for (key in matrices) { + matrices[key].updateId(record, oldId, newId); + } + if (refs) { + for (roleName in refs) { + roleRefs = refs[roleName]; + role = associations[roleName]; + association = role.association; + if (!association.isManyToMany) { + fieldName = association.field.name; + for (refId in roleRefs) { + roleRefs[refId].set(fieldName, id, setNoRefs); + } + } + } + } + me.registerReferences(record, oldId); + }, + processManyBlock: function(entityType, role, items, processor) { + var me = this, + id, record, records, store; + if (items) { + for (id in items) { + record = me.peekRecord(entityType, id); + if (record) { + records = me.getEntityList(role.cls, items[id]); + store = role.getAssociatedItem(record); + me[processor](role, store, record, records); + } else { + me.onInvalidAssociationEntity(entityType, id); + } + } + } + }, + processManyCreate: function(role, store, record, records) { + if (store) { + // Will handle any duplicates + store.add(records); + } else { + record[role.getterName](null, null, records); + } + }, + processManyDrop: function(role, store, record, records) { + if (store) { + store.remove(records); + } + }, + processManyRead: function(role, store, record, records) { + if (store) { + store.setRecords(records); + } else { + // We don't have a store. Create it and add the records. + record[role.getterName](null, null, records); + } + }, + /** + * Process a read block of entities from the {@link #update} method. + * @param {Ext.Class} entityType The entity type. + * @param {Object[]} items The data objects to read. + * + * @private + */ + readEntities: function(entityType, items) { + var me = this, + len = items.length, + i, data, rec, id; + for (i = 0; i < len; ++i) { + data = items[i]; + id = entityType.getIdFromData(data); + rec = me.peekRecord(entityType, id); + if (!rec) { + rec = me.createRecord(entityType, data, true); + } else { + me.onInvalidEntityRead(entityType, id); + } + // We've been read from a "server", so we aren't a phantom, + // regardless of whether or not we have an id + rec.phantom = false; + me.add(rec); + } + }, + recordCreator: function(data, Model) { + var me = this, + id = Model.getIdFromData(data), + record = me.peekRecord(Model, id, true); + // It doesn't exist anywhere, create it + if (!record) { + // We may have a stub that is loading the record (in fact this may be the + // call coming from that Reader), but the resolution is simple. By creating + // the record it is registered in the data[entityName][id] entry anyway + // and the stub will deal with it onLoad. + record = new Model(data, me); + } else { + record = me.getRecord(Model, id); + record.mergeData(data); + } + return record; + }, + registerReferences: function(record, oldId) { + var entityName = record.entityName, + id = record.id, + recordData = record.data, + remove = oldId || oldId === 0, + entry, i, fk, len, reference, references, refs, roleName; + // Register this records references to other records + len = (references = record.references).length; + for (i = 0; i < len; ++i) { + reference = references[i]; + // e.g., an orderId field + fk = recordData[reference.name]; + // the orderId + if (fk || fk === 0) { + reference = reference.reference; + // the "order" association role + entityName = reference.type; + roleName = reference.inverse.role; + // Track down the entry for the associated record + entry = this.getEntry(reference.cls, fk); + refs = entry.refs || (entry.refs = {}); + refs = refs[roleName] || (refs[roleName] = {}); + refs[id] = record; + if (remove) { + delete refs[oldId]; + } + } + } + }, + /** + * Process an update block for entities from the {@link #update} method. + * @param {Ext.Class} entityType The entity type. + * @param {Object[]} items The data objects to update. + * + * @private + */ + updateEntities: function(entityType, items) { + var len = items.length, + i, data, rec, id, modified; + // Repeating some code here, but we want to optimize this for speed + if (Ext.isArray(items)) { + for (i = 0; i < len; ++i) { + data = items[i]; + id = entityType.getIdFromData(data); + rec = this.peekRecord(entityType, id); + if (rec) { + rec.set(data); + } else { + this.onInvalidEntityUpdate(entityType, id); + } + } + } else { + for (id in items) { + data = items[id]; + rec = this.peekRecord(entityType, id); + if (rec && !rec.dropped) { + modified = rec.set(data); + } else { + this.onInvalidEntityUpdate(entityType, id, !!rec); + } + } + } + }, + updateReference: function(record, field, newValue, oldValue) { + var reference = field.reference, + entityName = reference.type, + roleName = reference.inverse.role, + id = record.id, + entry, refs; + if (oldValue || oldValue === 0) { + // We must be already in this entry.refs collection + refs = this.getEntry(entityName, oldValue).refs[roleName]; + delete refs[id]; + } + if (newValue || newValue === 0) { + entry = this.getEntry(entityName, newValue); + refs = entry.refs || (entry.refs = {}); + refs = refs[roleName] || (refs[roleName] = {}); + refs[id] = record; + } + }, + /** + * Walks the internal data tracked by this session and calls methods on the provided + * `visitor` object. The visitor can then accumulate whatever data it finds important. + * The visitor object can provide a number of methods, but all are optional. + * + * This method does not enumerate associations since these can be traversed given the + * records that are enumerated. For many-to-many associations, however, this method + * does enumerate the changes because these changes are not "owned" by either side of + * such associations. + * + * @param {Object} visitor + * @param {Function} [visitor.onCleanRecord] This method is called to describe a record + * that is known but unchanged. + * @param {Ext.data.Model} visitor.onCleanRecord.record The unmodified record. + * @param {Function} [visitor.onDirtyRecord] This method is called to describe a record + * that has either been created, dropped or modified. + * @param {Ext.data.Model} visitor.onDirtyRecord.record The modified record. + * @param {Function} [visitor.onMatrixChange] This method is called to describe a + * change in a many-to-many association (a "matrix"). + * @param {Ext.data.schema.Association} visitor.onMatrixChange.association The object + * describing the many-to-many ("matrix") association. + * @param {Mixed} visitor.onMatrixChange.leftId The `idProperty` of the record on the + * "left" of the association. + * @param {Mixed} visitor.onMatrixChange.rightId The `idProperty` of the record on the + * "right" of the association. + * @param {Number} visitor.onMatrixChange.state A negative number if the two records + * are being disassociated or a positive number if they are being associated. For + * example, when adding User 10 to Group 20, this would be 1. When removing the User + * this argument would be -1. + * @return {Object} The visitor instance + */ + visitData: function(visitor) { + var me = this, + data = me.data, + matrices = me.matrices, + all, assoc, id, id2, matrix, members, name, record, slice, slices, state; + // Force the schema to process any pending drops + me.getSchema().processKeyChecks(true); + for (name in data) { + all = data[name]; + // all entities of type "name" + for (id in all) { + record = all[id].record; + if (record) { + if (record.phantom || record.dirty || record.dropped) { + if (visitor.onDirtyRecord) { + visitor.onDirtyRecord(record); + } + } else if (visitor.onCleanRecord) { + visitor.onCleanRecord(record); + } + } + } + } + if (visitor.onMatrixChange) { + for (name in matrices) { + matrix = matrices[name].left; + // e.g., UserGroups.left (Users) + slices = matrix.slices; + assoc = matrix.role.association; + for (id in slices) { + slice = slices[id]; + members = slice.members; + for (id2 in members) { + state = (record = members[id2])[2]; + if (state) { + visitor.onMatrixChange(assoc, record[0], record[1], state); + } + } + } + } + } + return visitor; + }, + //--------------------------------------------------------------------- + // Record callbacks called because we are the "session" for the record. + _setNoRefs: { + refs: false + } + } +}); + +/** + * This is a base class for objects that can be managed by `Ext.util.Scheduler`. + * @private + */ +Ext.define('Ext.util.Schedulable', { + 'abstract': true, + isSchedulable: true, + scheduled: false, + constructor: function() { + this.getScheduler().add(this); + }, + destroy: function() { + var me = this, + scheduler = me.getScheduler(); + if (scheduler && !scheduler.destroyed) { + scheduler.remove(me); + } + me.scheduler = null; + me.schedule = me.react = Ext.emptyFn; + me.callParent(); + }, + getFullName: function() { + return this.name || this.id; + }, + privates: { + /** + * This method returns the `Scheduler` for this item. + * @return {Ext.util.Scheduler} + */ + getScheduler: function() { + return this.scheduler; + }, + /** + * Schedules this item with the associated `Ext.util.Scheduler`. + */ + schedule: function() { + var me = this, + scheduler; + if (!me.scheduled) { + scheduler = me.getScheduler(); + if (scheduler) { + me.scheduled = true; + if (me.onSchedule) { + me.onSchedule(); + } + scheduler.scheduleItem(me); + } + } + }, + /** + * Unschedules this item with the associated `Ext.util.Scheduler`. + */ + unschedule: function() { + var me = this, + scheduler; + if (me.scheduled) { + scheduler = me.getScheduler(); + if (scheduler && !scheduler.destroyed) { + scheduler.unscheduleItem(me); + } + me.scheduled = false; + } + }, + /** + * @method sort + * This method should be overridden by items that have dependencies to insert. The + * standard form would be: + * + * sort: function () { + * this.getScheduler().sortItems(this.dependencies); + * } + * + * This example assumes the item has a "dependencies" array to pass to the scheduler. + */ + // Can't use Ext.emptyFn here to avoid setting $private: true on it + sort: function() {} + } +}); + +/** + * This class is the base for `Binding` and `MultiBinding`. + * @private + */ +Ext.define('Ext.app.bind.BaseBinding', { + extend: 'Ext.util.Schedulable', + isBinding: true, + calls: 0, + kind: 20, + defaultOptions: {}, + lastValue: undefined, + /** + * @cfg {Boolean} [single=false] + * This option instructs the binding to call its `destroy` method immediately after + * delivering the initial value. + * @since 5.0.0 + */ + constructor: function(owner, callback, scope, options) { + var me = this; + me.options = options; + me.owner = owner; + me.scope = scope; + me.callback = callback; + if (!callback) { + Ext.raise('Callback is required'); + } + // If given a string callback name, preserve the late binding: + me.lateBound = Ext.isString(callback); + if (options && options.deep) { + me.deep = true; + } + me.callParent(); + }, + destroy: function() { + var me = this, + owner = me.owner; + if (owner) { + owner.onBindDestroy(me); + } + me.callParent(); + me.scope = me.callback = me.owner = null; + }, + isReadOnly: function() { + return true; + }, + privates: { + getScheduler: function() { + var owner = this.owner; + return owner && owner.getScheduler(); + }, + getSession: function() { + var owner = this.owner; + return owner.isSession ? owner : owner.getSession(); + }, + notify: function(value) { + var me = this, + options = me.options || me.defaultOptions, + previous = me.lastValue; + // We want to deliver if: + // 1) We've never been called + // 2) We're a deep binding, which means that our object reference may not have changed, + // but something under us has changed. For example a link stub or a model field binding + // 3) If the value has changed + // 4) If the value is an array. It's difficult to tell if the underlying data changed + if (!me.calls || me.deep || me.valueChanged(value, previous)) { + ++me.calls; + me.lastValue = value; + if (me.lateBound) { + // Interestingly, lateBound-ness may be more efficient since it does + // not use the "call" method. + me.scope[me.callback](value, previous, me); + } else { + me.callback.call(me.scope, value, previous, me); + } + if (options.single) { + me.destroy(); + } + } + }, + valueChanged: function(value, previous) { + var ret = true; + if (previous !== value) { + if (value && previous && value instanceof Date && previous instanceof Date) { + ret = value.getTime() !== previous.getTime(); + } + } else { + ret = Ext.isArray(value); + } + return ret; + } + } +}); + +/** + * This class is created to manage a direct bind. `Ext.app.ViewModel` returns this from + * its {@link Ext.app.ViewModel#method-bind bind} method. + */ +Ext.define('Ext.app.bind.Binding', { + extend: 'Ext.app.bind.BaseBinding', + /** + * @cfg {Boolean} [deep=false] + * Normally a binding is only notified of changes to its bound property, but if that + * property is an object it is sometimes helpful to be notified of changes to its + * properties. To receive notifications of changes to all properties of a bound object, + * set this to `true`. + * @since 5.0.0 + */ + constructor: function(stub, callback, scope, options) { + var me = this; + me.callParent([ + stub.owner, + callback, + scope, + options + ]); + me.stub = stub; + me.depth = stub.depth; + // We need to announce the current value, so if the stub is available + // will generate its own announcement to all bindings) then we need to schedule + if (stub.isAvailable() && !stub.scheduled) { + me.schedule(); + } + }, + /** + * Destroys this binding. No further calls will be made to the callback method. No + * methods should be called on this binding after calling this method. + * @param {Boolean} [fromParent] (private) + * @since 5.0.0 + */ + destroy: function(fromParent) { + var me = this, + stub = me.stub; + if (stub && !fromParent) { + stub.unbind(me); + me.stub = null; + } + me.callParent(); + }, + /** + * Binds to the `validation` association for the bound property. For example, when a + * binding is bound to something like this: + * + * var binding = viewModel.bind('{theUser.name}', ...); + * + * The validation status for the "name" property can be requested like so: + * + * var validationBinding = binding.bindValidation(fn, scope); + * + * Calling this method in the above example would be equivalent to the following bind: + * + * var validationBinding = viewModel.bind('{theUser.validation.name}', fn, scope); + * + * The primary reason to use this method is in cases where the original bind expression + * is not known. + * + * For example, this method is used by `Ext.form.field.Base` when given the + * `{@link Ext.Component#modelValidation modelValidation}` config is set. As such it + * not common for users to need to call this method. + * + * @param {Function} callback The function to call when the validation changes. + * @param {Object} [scope] The scope on which to call the `callback`. + * @return {Ext.app.bind.Binding} A binding to the validation of the bound property. + * @since 5.0.0 + */ + bindValidation: function(callback, scope) { + var stub = this.stub; + return stub && stub.bindValidation(callback, scope); + }, + /** + * Bind to a model field for validation + * @param {Function/String} callback The function to call or the name of the function on the scope + * @param {Object} scope The scope for the callback + * @return {Ext.app.bind.Binding} The binding, if available + * + * @private + */ + bindValidationField: function(callback, scope) { + var stub = this.stub; + return stub && stub.bindValidationField(callback, scope); + }, + /** + * Returns the diagnostic name for this binding. + * @return {String} + * @since 5.0.0 + */ + getFullName: function() { + return this.fullName || (this.fullName = '@(' + this.stub.getFullName() + ')'); + }, + /** + * Returns the current value of the bound property. If this binding is not + * {@link #isAvailable available} the value will be `undefined`. + * @return {Mixed} The value of the bound property. + * @since 5.0.0 + */ + getValue: function() { + var me = this, + stub = me.stub; + return stub && stub.getValue(); + }, + /** + * Returns `true` if the bound property is available. If this returns `false`, + * it generally means the value is not reachable because the a parent value is + * not present. + * @return {Boolean} + * @since 5.1.2 + */ + isAvailable: function() { + var stub = this.stub; + return stub && stub.isAvailable(); + }, + /** + * Returns `true` if the bound property is loading. In the general case this means + * that the value is just not available yet. In specific cases, when the bound property + * is an `Ext.data.Model` it means that a request to the server is in progress to get + * the record. For an `Ext.data.Store` it means that + * `{@link Ext.data.Store#method-load load}` has been called on the store but it is + * still in progress. + * @return {Boolean} + * @since 5.0.0 + */ + isLoading: function() { + var stub = this.stub; + return stub && stub.isLoading(); + }, + /** + * This method returns `true` if this binding can only be read. If this method returns + * `false` then the binding can be set using `setValue` (meaning this binding can be + * a two-way binding). + * @return {Boolean} + * @since 5.0.0 + */ + isReadOnly: function() { + var stub = this.stub, + options = this.options, + ret = true; + if (!(options && options.twoWay === false)) { + if (stub) { + ret = stub.isReadOnly(); + } + } + return ret; + }, + /** + * Tells the bound property to refresh itself. This has meaning when the bound property + * is something like an `Ext.data.Model` and an `Ext.data.Store` but does nothing in + * most cases. + * @since 5.0.0 + */ + refresh: function() {}, + //TODO - maybe nothing to do here but entities/stores would have work to do + /** + * Sets the value of the bound property. This will throw an error in debug mode if + * this binding `isReadOnly`. This method will climb to set data on + * a parent view model of this binding if appropriate. See "Inheriting Data" in the {@link Ext.app.ViewModel} + * class introduction for more information. + * @param {Mixed} value The new value. + * @since 5.0.0 + */ + setValue: function(value) { + if (this.isReadOnly()) { + Ext.raise('Cannot setValue on a readonly binding'); + } + this.stub.set(value); + }, + privates: { + getDataObject: function() { + var stub = this.stub; + return stub && stub.getDataObject(); + }, + getRawValue: function() { + var me = this, + stub = me.stub; + return stub && stub.getRawValue(); + }, + isDescendantOf: function(item) { + var stub = this.stub; + return stub ? (item === stub) || stub.isDescendantOf(item) : false; + }, + react: function() { + this.notify(this.getValue()); + }, + schedule: function() { + // If the parent stub is already scheduled, then we will be + // called when the stub hits the next tick. + if (!this.stub.scheduled) { + this.callParent(); + } + }, + sort: function() { + var stub = this.stub; + stub.scheduler.sortItem(stub); + } + } +}); +// Schedulable#sort === emptyFn +//me.callParent(); + +/** + * This class manages bindings for a `Session` or `ViewModel`. + * @private + */ +Ext.define('Ext.app.bind.AbstractStub', { + extend: 'Ext.util.Schedulable', + requires: [ + 'Ext.app.bind.Binding' + ], + children: null, + depth: 0, + generation: 1, + kind: 10, + parent: null, + constructor: function(owner, name) { + var me = this; + /** + * @property {Ext.data.Session/Ext.app.ViewModel} owner + * This property is set at creation of ths stub and should not be changed. + * @readonly + */ + me.owner = owner; + me.name = name; + me.callParent(); + }, + destroy: function() { + var me = this, + children = me.children, + bindings = me.bindings, + len, i, key; + if (bindings) { + for (i = 0 , len = bindings.length; i < len; ++i) { + bindings[i].destroy(true); + } + } + for (key in children) { + children[key].destroy(); + } + if (me.scheduled) { + me.unschedule(); + } + me.callParent(); + }, + add: function(child) { + var me = this; + (me.children || (me.children = {}))[child.name] = child; + child.depth = me.depth + 1; + child.parent = me; + }, + getChild: function(path) { + var pathArray = Ext.isString(path) ? path.split('.') : path; + if (pathArray && pathArray.length) { + return this.descend(pathArray, 0); + } + return this; + }, + getFullName: function() { + var me = this, + name = me.fullName, + parent = me.parent, + s; + if (!name) { + name = me.name || me.id; + if (parent && (s = parent.getFullName())) { + name = ((s.charAt(s.length - 1) !== ':') ? s + '.' : s) + name; + } + me.fullName = name; + } + return name; + }, + getSession: function() { + var owner = this.owner; + return owner.isSession ? owner : owner.getSession(); + }, + bind: function(callback, scope, options) { + var me = this, + binding = new Ext.app.bind.Binding(me, callback, scope, options), + bindings = (me.bindings || (me.bindings = [])); + binding.depth = me.depth; + bindings.push(binding); + return binding; + }, + getValue: function() { + return this.isAvailable() ? this.getRawValue() : null; + }, + graft: function(replacement) { + var me = this, + bindings = me.bindings, + name = me.name, + i; + // Clear these so that when we call destroy we won't damage anything: + me.parent = me.bindings = null; + me.destroy(); + // we may be scheduled + replacement.depth = me.depth; + replacement.bindings = bindings; + replacement.generation = me.generation + 1; + replacement.name = name; + replacement.id = me.id; + replacement.path = me.path; + // Now for the fun part... + if (bindings) { + for (i = bindings.length; i-- > 0; ) { + bindings[i].stub = replacement; + } + } + return replacement; + }, + isDescendantOf: function(item) { + for (var parent = this; parent = parent.parent; ) { + if (parent === item) { + return true; + } + } + return false; + }, + isAvailable: function() { + return true; + }, + isLoading: function() { + return false; + }, + onSchedule: function() { + // When a stub changes, say "foo.bar.baz" we may need to notify bindings on our + // parents "foo.bar" and "foo", This is true especially when these are targets of + // links. To economize on this we require that bindings that want to be notified + // of changes to sub-properties of their target set the "deep" property to true. + for (var i, len, binding, bindings, + p = this.parent; p; p = p.parent) { + bindings = p.bindings; + if (bindings) { + for (i = 0 , len = bindings.length; i < len; ++i) { + binding = bindings[i]; + if (binding.deep && !binding.scheduled) { + binding.schedule(); + } + } + } + } + }, + react: function() { + var bindings = this.bindings, + binding, i, len; + if (bindings) { + for (i = 0 , len = bindings.length; i < len; ++i) { + binding = bindings[i]; + if (!binding.scheduled) { + binding.schedule(); + } + } + } + }, + unbind: function(binding) { + var bindings = this.bindings; + if (bindings && bindings.length) { + Ext.Array.remove(bindings, binding); + } + }, + privates: { + collect: function() { + var children = this.children, + bindings = this.bindings, + totalCount = 0, + count = 0, + child, key; + if (children) { + for (key in children) { + child = children[key]; + count = child.collect(); + if (count === 0) { + // The child (and any deep children) have no bindings, + // so we can consider it a dead node. + child.destroy(); + delete children[key]; + } + totalCount += count; + } + } + if (bindings) { + totalCount += bindings.length; + } + return totalCount; + }, + getScheduler: function() { + var owner = this.owner; + return owner && owner.getScheduler(); + }, + sort: function() { + var parent = this.parent; + if (parent) { + // We sort our parent first because if it is something like a link we need + // it to determine the value of the root-level property before we can dot + // our way into it. This is especially important for formulas that might + // throw errors if the links have not published results before they run. + this.scheduler.sortItem(parent); + } + } + } +}); +// Schedulable#sort === emptyFn +//me.callParent(); + +/** + * This class and its derived classes are used to manage access to the properties of an + * object stored in a `Session`. + * @private + */ +Ext.define('Ext.app.bind.Stub', { + extend: 'Ext.app.bind.AbstractStub', + requires: [ + 'Ext.app.bind.Binding' + ], + isStub: true, + dirty: true, + formula: null, + validationKey: 'validation', + constructor: function(owner, name, parent) { + var me = this, + path = name; + me.callParent([ + owner, + name + ]); + me.boundValue = null; + if (parent) { + parent.add(me); + if (!parent.isRootStub) { + path = parent.path + '.' + name; + } + me.checkHadValue(); + } + me.path = path; + }, + destroy: function() { + var me = this, + formula = me.formula, + storeBinding = me.storeBinding; + if (formula) { + formula.destroy(); + } + if (storeBinding) { + storeBinding.destroy(); + } + me.detachBound(); + me.callParent(); + }, + bindValidation: function(callback, scope) { + var parent = this.parent; + return parent && parent.descend([ + this.validationKey, + this.name + ]).bind(callback, scope); + }, + bindValidationField: function(callback, scope) { + var parent = this.parent, + name = this.name, + lateBound = typeof callback === 'string', + ret; + if (parent) { + ret = parent.bind(function(value) { + var field = null; + if (value && value.isModel) { + field = value.getField(name); + } + if (lateBound) { + scope[callback](field, value, this); + } else { + callback.call(scope, field, value, this); + } + }); + } + return ret || null; + }, + descend: function(path, index) { + var me = this, + children = me.children || (me.children = {}), + pos = index || 0, + name = path[pos++], + ret; + if (!(ret = children[name])) { + ret = new Ext.app.bind.Stub(me.owner, name, me); + } + if (pos < path.length) { + ret = ret.descend(path, pos); + } + return ret; + }, + getChildValue: function(parentData) { + var me = this, + name = me.name, + bindMappings = me.bindMappings, + storeMappings = bindMappings.store, + modelMappings = bindMappings.model, + ret; + if (!parentData && !Ext.isString(parentData)) { + // since these forms of falsey values (0, false, etc.) are not things we + // can index into, this child stub must be null. + ret = me.hadValue ? null : undefined; + } else { + ret = me.inspectValue(parentData); + if (!ret) { + if (parentData.isEntity) { + // If we get here, we know it's not an association + if (modelMappings[name]) { + ret = parentData[modelMappings[name]](); + } else { + ret = parentData.data[name]; + } + } else if (parentData.isStore && storeMappings[name]) { + ret = parentData[storeMappings[name]](); + } else { + ret = parentData[name]; + if (ret === undefined && me.hadValue) { + ret = null; + } + } + } + } + return ret; + }, + getDataObject: function() { + var me = this, + parentData = me.parent.getDataObject(), + // RootStub does not get here + name = me.name, + ret = parentData ? parentData[name] : null, + storeMappings = me.bindMappings.store, + associations; + if (!ret) { + if (parentData && parentData.isEntity) { + // Check if the item is an association, if it is, grab it but don't load it. + associations = parentData.associations; + if (associations && name in associations) { + ret = parentData[associations[name].getterName](); + } + } + } else if (parentData.isStore && name in storeMappings) { + ret = parentData[storeMappings[name]](); + } + if (!ret || !(ret.$className || Ext.isObject(ret))) { + parentData[name] = ret = {}; + // We're implicitly setting a value on the object here + me.hadValue = true; + // If we're creating the parent data object, invalidate the dirty + // flag on our children. + me.invalidate(true, true); + } + return ret; + }, + getRawValue: function() { + // NOTE: The RootStub class does not call here so we will *always* have a parent + // unless dark energy has won and the laws of physics have broken down. + return this.getChildValue(this.getParentValue()); + }, + graft: function(replacement) { + var me = this, + parent = me.parent, + children = me.children, + name = me.name, + i, ret; + replacement.parent = parent; + replacement.children = children; + if (parent) { + parent.children[name] = replacement; + } + if (children) { + for (i in children) { + children[i].parent = replacement; + } + } + me.children = null; + replacement.checkHadValue(); + ret = me.callParent([ + replacement + ]); + ret.invalidate(true, true); + return ret; + }, + isAvailable: function() { + return this.checkAvailability(); + }, + isLoading: function() { + return !this.checkAvailability(true); + }, + invalidate: function(deep, dirtyOnly) { + var me = this, + children = me.children, + name; + me.dirty = true; + me.checkHadValue(); + if (!dirtyOnly && me.isAvailable()) { + if (!me.scheduled) { + // If we have no children, we're a leaf + me.schedule(); + } + } + if (deep && children) { + for (name in children) { + children[name].invalidate(deep, dirtyOnly); + } + } + }, + isReadOnly: function() { + var formula = this.formula; + return !!(formula && !formula.set); + }, + set: function(value, preventClimb) { + var me = this, + parent = me.parent, + name = me.name, + formula = me.formula, + parentData, associations, association, formulaStub, setterName; + if (formula && !formula.settingValue && formula.set) { + formula.setValue(value); + return; + } else if (me.isLinkStub) { + formulaStub = me.getLinkFormulaStub(); + formula = formulaStub ? formulaStub.formula : null; + if (formula) { + if (formulaStub.isReadOnly()) { + Ext.raise('Cannot setValue on a readonly formula'); + } + formula.setValue(value); + return; + } + } + // To set a child property, the parent must be an object... + parentData = parent.getDataObject(); + if (parentData.isEntity) { + associations = parentData.associations; + if (associations && (name in associations)) { + association = associations[name]; + setterName = association.setterName; + if (setterName) { + parentData[setterName](value); + } + // We may be setting a record here, force the value to recalculate + me.invalidate(true); + } else { + // If not an association then it is a data field + parentData.set(name, value); + } + } + // Setting fields or associated records will fire change notifications so we + // handle the side effects there + else if ((value && value.constructor === Object) || !(value === parentData[name] && parentData.hasOwnProperty(name))) { + // The hasOwnProperty check is important, even though the value might be the same here, that value + // could exist in a viewmodel above us + if (preventClimb || !me.setByLink(value)) { + if (value === undefined) { + delete parentData[name]; + } else { + parentData[name] = value; + } + me.inspectValue(parentData); + // We have children, but we're overwriting the value with something else, so + // we need to schedule our children + me.invalidate(true); + } + } + }, + onStoreDataChanged: function() { + this.invalidate(true); + }, + afterLoad: function(record) { + this.invalidate(true); + }, + afterCommit: function(record) { + // Essentially the same as an edit, but we don't know what changed. + this.afterEdit(record, null); + }, + afterEdit: function(record, modifiedFieldNames) { + var children = this.children, + len = modifiedFieldNames && modifiedFieldNames.length, + associations = record.associations, + bindMappings = this.bindMappings.model, + key, i, child, name, ref; + // No point checking anything if we don't have children + if (children) { + if (len) { + // We know what changed, check for it and schedule it. + for (i = 0; i < len; ++i) { + name = modifiedFieldNames[i]; + child = children[name]; + if (!child) { + ref = record.fieldsMap[name]; + ref = ref && ref.reference; + child = ref && children[ref.role]; + } + if (child) { + child.invalidate(true); + } + } + } else { + // We don't know what changed, so loop over everything. + // If the child is not an association, then it's a field so we + // need to trigger them so we can respond to field changes + for (key in children) { + if (!(associations && key in associations)) { + children[key].invalidate(true); + } + } + } + // Whether we know what changed or not, valid/dirty are meta properties so + // trigger them regardless + for (key in bindMappings) { + child = children[key]; + if (child) { + child.invalidate(); + } + } + } + this.invalidate(); + }, + afterReject: function(record) { + // Essentially the same as an edit, but we don't know what changed. + this.afterEdit(record, null); + }, + afterAssociatedRecordSet: function(record, associated, role) { + var children = this.children, + key = role.role; + if (children && key in children) { + children[key].invalidate(true); + } + }, + setByLink: function(value) { + var me = this, + n = 0, + ret = false, + i, link, path, stub, root, name; + for (stub = me; stub; stub = stub.parent) { + if (stub.isLinkStub) { + link = stub; + if (n) { + for (path = [] , i = 0 , stub = me; stub !== link; stub = stub.parent) { + ++i; + path[n - i] = stub.name; + } + } + break; + } + ++n; + } + stub = null; + if (link) { + root = link.parent; + name = link.name; + if (!root.shouldClimb(name)) { + // Write to root, descend to stub + stub = root.insertChild(name); + } else { + stub = link.getTargetStub(); + } + } + if (stub) { + // We are a child of a link stub and that stub links to a Stub, so forward the set + // call over there. This is needed to fire the bindings on that side of the link + // and that will also arrive back here since we are a linked to it. + if (path) { + stub = stub.descend(path); + } + stub.set(value); + ret = true; + } + return ret; + }, + setFormula: function(formula) { + var me = this, + oldFormula = me.formula; + if (oldFormula) { + oldFormula.destroy(); + } + // The new formula will bind to what it needs and that will schedule it (and then + // us when it sets our value). + me.formula = new Ext.app.bind.Formula(me, formula); + }, + react: function() { + var me = this, + bound = this.boundValue, + children = me.children, + generation; + if (bound) { + if (bound.isValidation) { + bound.refresh(); + generation = bound.generation; + // Don't react if we haven't changed + if (me.lastValidationGeneration === generation) { + return; + } + me.lastValidationGeneration = generation; + } else if (bound.isModel) { + // At this point we're guaranteed to have a non-validation model + // Check if we're interested in it, if so, validate it and let + // the record fire off any changes + if (children && children[me.validationKey]) { + // Trigger validity checks + bound.isValid(); + } + } + } + this.callParent(); + }, + privates: { + bindMappings: { + store: { + count: 'getCount', + first: 'first', + last: 'last', + loading: 'hasPendingLoad', + totalCount: 'getTotalCount' + }, + model: { + dirty: 'isDirty', + phantom: 'isPhantom', + valid: 'isValid' + } + }, + checkAvailability: function(isLoading) { + var me = this, + parent = me.parent, + bindMappings = me.bindMappings, + name = me.name, + available = !!(parent && parent.checkAvailability(isLoading)), + associations, parentValue, value, availableSet, loading; + if (available) { + parentValue = me.getParentValue(); + value = me.inspectValue(parentValue); + // If we get a value back, it's something we can ask for the loading state + if (value) { + if (isLoading) { + available = !value.hasPendingLoad(); + } else { + // If it's a store, it should be always available, even if loading + if (value.isStore) { + available = true; + } else { + // If it's a model and it's loading, only available if it's after + // the first time + available = !value.isLoading() || value.loadCount > 0; + } + } + } else { + if (parentValue) { + if (parentValue.isModel) { + if (bindMappings.model[name]) { + available = !parent.isLoading(); + availableSet = true; + } else { + associations = parentValue.associations; + // At this point, we know the value is not a record or a store, otherwise + // something would have been returned from inspectValue. We also check here + // that we are not a defined association, because we don't treat it like a field. + // Otherwise, we are a field on a model, so we're never in a loading state. + if (!(associations && name in associations)) { + available = true; + availableSet = true; + } + } + } else if (parentValue.isStore && bindMappings.store[name] && name !== 'loading') { + available = !parent.isLoading(); + availableSet = true; + } + } + if (!availableSet) { + available = me.hadValue || me.getRawValue() !== undefined; + } + } + } + return available; + }, + checkHadValue: function() { + if (!this.hadValue) { + this.hadValue = this.getRawValue() !== undefined; + } + }, + collect: function() { + var me = this, + result = me.callParent(), + storeBinding = me.storeBinding ? 1 : 0, + formula = me.formula ? 1 : 0; + return result + storeBinding + formula; + }, + getLinkFormulaStub: function() { + // Setting the value on a link backed by a formula should set the + // formula. So we climb the hierarchy until we find the rootStub + // and set it there if it be a formula. + var stub = this; + while (stub.isLinkStub) { + stub = stub.binding.stub; + } + return stub.formula ? stub : null; + }, + getParentValue: function() { + var me = this; + // Cache the value of the parent here. Inside onSchedule we clear the value + // because it may be invalidated. + if (me.dirty) { + me.parentValue = me.parent.getValue(); + me.dirty = false; + } + return me.parentValue; + }, + setStore: function(storeBinding) { + this.storeBinding = storeBinding; + }, + inspectValue: function(parentData) { + var me = this, + name = me.name, + current = me.boundValue, + boundValue = null, + associations, raw, changed, associatedEntity; + if (parentData && parentData.isEntity) { + associations = parentData.associations; + if (associations && (name in associations)) { + boundValue = parentData[associations[name].getterName](); + } else if (name === me.validationKey) { + boundValue = parentData.getValidation(); + // Binding a new one, reset the generation + me.lastValidationGeneration = null; + } + } else if (parentData) { + raw = parentData[name]; + if (raw && (raw.isModel || raw.isStore)) { + boundValue = raw; + } + } + // Check if we have a current binding that changed. If so, we need + // to detach ourselves from it + changed = current !== boundValue; + if (changed) { + if (current) { + me.detachBound(); + } + if (boundValue) { + if (boundValue.isModel) { + boundValue.join(me); + } else { + // Only want to trigger automatic loading if we've come from an association. Otherwise leave + // the user in charge of that. + associatedEntity = boundValue.associatedEntity; + if (associatedEntity && boundValue.autoLoad !== false && !boundValue.complete && !boundValue.hasPendingLoad()) { + boundValue.load(); + } + // We only want to listen for the first load, since the actual + // store object won't change from then on + boundValue.on({ + scope: me, + // Capture beginload/load so we can bind to the loading state of the store. + // We need load because a load may be unsuccessful which means datachanged won't fire + // beginload is used because it's fired: + // a) After we're sure to load (beforeload could be vetoed) + // b) After the loading flag is set to true. This is important + // because we fire the datachanged handler which needs to check if + // the store is available (loading) to publish values. + beginload: 'onStoreDataChanged', + load: 'onStoreDataChanged', + datachanged: 'onStoreDataChanged', + destroy: 'onDestroyBound' + }); + } + } + me.boundValue = boundValue; + } + return boundValue; + }, + detachBound: function() { + var me = this, + current = me.boundValue; + if (current && !current.destroyed) { + if (current.isModel) { + current.unjoin(me); + } else { + current.un({ + scope: me, + beginload: 'onStoreDataChanged', + load: 'onStoreDataChanged', + datachanged: 'onStoreDataChanged', + destroy: 'onDestroyBound' + }); + } + } + }, + onDestroyBound: function() { + if (!this.owner.destroying) { + this.set(null); + } + }, + sort: function() { + var me = this, + formula = me.formula, + scheduler = me.scheduler, + storeBinding = me.storeBinding; + me.callParent(); + if (storeBinding) { + scheduler.sortItem(storeBinding); + } + if (formula) { + // Our formula must run before we do so it can set the value on us. Our + // bindings in turn depend on us so they will be scheduled as part of the + // current sweep if the formula produces a different result. + scheduler.sortItem(formula); + } + } + } +}); + +/** + * This class manages stubs associated with `link` requests. These bind to some other + * descriptor and forward changes from there. + * @private + */ +Ext.define('Ext.app.bind.LinkStub', { + extend: 'Ext.app.bind.Stub', + isLinkStub: true, + binding: null, + destroy: function() { + var me = this, + binding = me.binding, + owner = me.owner; + if (binding) { + me.binding = null; + binding.destroy(); + if (owner) { + delete owner.linkData[me.name]; + } + } + me.target = null; + me.callParent(); + }, + getFullName: function() { + var me = this; + return me.fullName || (me.fullName = '(' + me.callParent() + ' -> ' + me.binding.getFullName() + ')'); + }, + getDataObject: function() { + var binding = this.binding, + root = this.parent, + name = this.name, + rootData, ret; + if (root.isRootStub && !root.shouldClimb(name)) { + rootData = root.owner.getData(); + if (!rootData.hasOwnProperty(name)) { + rootData[name] = ret = {}; + } + } else { + ret = binding && binding.getDataObject(); + } + return ret; + }, + getRawValue: function() { + var binding = this.binding; + return binding && binding.getRawValue(); + }, + getValue: function() { + var binding = this.binding; + return binding && binding.getValue(); + }, + getTargetStub: function() { + var binding = this.binding; + return binding && binding.stub; + }, + isAvailable: function() { + var binding = this.binding; + return binding ? binding.isAvailable() : false; + }, + isLoading: function() { + var binding = this.binding; + return binding ? binding.isLoading() : false; + }, + link: function(bindDescriptor, target) { + var me = this, + binding = me.binding; + if (binding) { + binding.destroy(); + } + target = me.target = target || me.owner; + me.linkDescriptor = bindDescriptor; + me.binding = target.bind(bindDescriptor, me.onChange, me); + me.binding.deep = true; + }, + onChange: function() { + this.invalidate(true); + }, + react: function() { + var me = this, + linkData = me.owner.linkData; + linkData[me.name] = me.getValue(); + me.callParent(); + }, + privates: { + collect: function() { + var me = this, + result = me.callParent(), + binding = me.binding ? 1 : 0; + return result + binding; + }, + sort: function() { + var binding = this.binding; + if (binding) { + // We want to make sure our binding reacts before we do so that it can provide + // whatever value we might need first. + this.scheduler.sortItem(binding); + } + } + } +}); + +/** + * This class is the root stub for managing a `ViewModel`. + * @private + */ +Ext.define('Ext.app.bind.RootStub', { + extend: 'Ext.app.bind.AbstractStub', + requires: [ + 'Ext.app.bind.LinkStub', + 'Ext.app.bind.Stub' + ], + isRootStub: true, + depth: 0, + createRootChild: function(name, direct) { + var me = this, + owner = me.owner, + ownerData = owner.getData(), + children = me.children, + previous = children && children[name], + parentStub = previous ? null : me, + parentVM, stub; + if (direct || ownerData.hasOwnProperty(name) || !(parentVM = owner.getParent())) { + stub = new Ext.app.bind.Stub(owner, name, parentStub); + } else { + stub = new Ext.app.bind.LinkStub(owner, name, parentStub); + stub.link('{' + name + '}', parentVM); + } + if (previous) { + previous.graft(stub); + } + return stub; + }, + createStubChild: function(name) { + return this.createRootChild(name, true); + }, + descend: function(path, index) { + var me = this, + children = me.children, + pos = index || 0, + name = path[pos++], + ret = (children && children[name]) || me.createRootChild(name); + if (pos < path.length) { + ret = ret.descend(path, pos); + } + return ret; + }, + getFullName: function() { + return this.fullName || (this.fullName = this.owner.id + ':'); + }, + // The root Stub is associated with the owner's "data" object + getDataObject: function() { + return this.owner.data; + }, + getRawValue: function() { + return this.owner.data; + }, + getValue: function() { + return this.owner.data; + }, + isDescendantOf: function() { + return false; + }, + set: function(value, preventClimb) { + if (!value || value.constructor !== Object) { + Ext.raise('Only an object can be set at the root'); + } + var me = this, + children = me.children || (me.children = {}), + owner = me.owner, + data = owner.data, + parentVM = owner.getParent(), + stub, v, key, setSelf, created; + for (key in value) { + if (key.indexOf('.') >= 0) { + Ext.raise('Value names cannot contain dots'); + } + // Setting the value. + // Ensure the Stub exists for the name, and set its value. + v = value[key]; + if (v !== undefined) { + stub = children[key]; + setSelf = preventClimb || !me.shouldClimb(key); + if (!stub) { + stub = me.createRootChild(key, setSelf); + created = true; + } else if (setSelf && stub.isLinkStub && !stub.getLinkFormulaStub()) { + stub = me.insertChild(key); + } + if (!created || !data.hasOwnProperty(value)) { + owner.invalidateChildLinks(key); + } + stub.set(v, setSelf); + } + // Clearing the value. Delete the data item + // Invalidate the Stub if it exists. + else if (data.hasOwnProperty(key)) { + delete data[key]; + stub = children[key]; + if (stub) { + if (!stub.isLinkStub && parentVM) { + stub = me.createRootChild(key); + } + owner.invalidateChildLinks(key, true); + stub.invalidate(true); + } + } + } + }, + schedule: Ext.emptyFn, + unschedule: Ext.emptyFn, + privates: { + checkAvailability: function() { + // Always available + return true; + }, + insertChild: function(name) { + return this.createRootChild(name, true); + }, + invalidateChildLink: function(name, clear) { + var children = this.children, + stub = children && children[name]; + if (stub && stub.isLinkStub && !stub.getLinkFormulaStub()) { + stub = this.createRootChild(name); + if (clear) { + stub.invalidate(true); + } + this.owner.invalidateChildLinks(name, clear); + } + }, + shouldClimb: function(name) { + var parent = this.owner.getParent(); + while (parent) { + if (parent.getData().hasOwnProperty(name)) { + return true; + } + parent = parent.getParent(); + } + return false; + } + } +}); + +/** + * This class is created to manage a multi-bind against a `ViewModel`. + */ +Ext.define('Ext.app.bind.Multi', { + extend: 'Ext.app.bind.BaseBinding', + isMultiBinding: true, + missing: 1, + // Multi binds have to be deep. We construct a single object/array and we only + // ever fire by notifying with that value which will never change. As such, we + // need to notify any child bindings so they can check if their individual + // bindings have changed. + deep: true, + /** + * @cfg {Boolean} trackStatics + * This option tracks for static branches of the root object which can be pruned using + * {@link #pruneStaticKeys}. This can be useful to only get the dynamic parts of a multi bind: + * + * { + * a: 1, + * b: '{someBind}', + * c: ['a', 'b', 'c'], + * d: ['a', 'b', '{someBind}'], + * e: { + * y: 1, + * z: 2 + * }, + * f: { + * y: 1, + * z: '{someBind}' + * } + * } + * + * // Will produce + * { + * b: value, + * d: ['a', 'b', value], + * f: { + * y: 1, + * z: value + * } + * } + * @private + * @since 5.1.0 + */ + constructor: function(descriptor, owner, callback, scope, options) { + var me = this, + trackStatics = options && options.trackStatics; + me.callParent([ + owner, + callback, + scope, + options + ]); + me.bindings = []; + me.literal = descriptor.$literal; + if (descriptor.constructor === Object) { + if (trackStatics) { + me.staticKeys = []; + } + me.addObject(descriptor, me.lastValue = {}, me.staticKeys); + } else { + me.addArray(descriptor, me.lastValue = []); + } + // We started at missing == 1 so that no immediate callbacks would hit 0 before + // adding all bindings... so now we decrement by 1 to balance things and see if + // we are at 0. + if (!--me.missing && !me.scheduled) { + me.schedule(); + } + }, + destroy: function() { + var me = this; + me.bindings = Ext.destroy(me.bindings); + me.callParent(); + }, + add: function(descriptor, data, property) { + var me = this, + owner = me.owner, + bindings = me.bindings, + method = me.literal ? (descriptor.reference ? 'bindEntity' : 'bindExpression') : 'bind', + binding, depth; + ++me.missing; + binding = owner[method](descriptor, function(value) { + data[property] = value; + if (binding.calls === 1) { + --me.missing; + } + if (!me.missing && !me.scheduled) { + me.schedule(); + } + }, //TODO - split bind options between us and the sub-binds (pass null for now) + me, null); + depth = binding.depth; + if (!bindings.length || depth < me.depth) { + me.depth = depth; + } + bindings.push(binding); + return !this.isBindingStatic(binding); + }, + addArray: function(multiBindDescr, array) { + var me = this, + n = multiBindDescr.length, + hasDynamic = false, + dynamic, b, i; + for (i = 0; i < n; ++i) { + b = multiBindDescr[i]; + if (b && (b.reference || Ext.isString(b))) { + dynamic = me.add(b, array, i); + } else if (Ext.isArray(b)) { + dynamic = me.addArray(b, array[i] = []); + } else if (b && b.constructor === Object) { + dynamic = me.addObject(b, array[i] = {}); + } else { + array[i] = b; + dynamic = false; + } + hasDynamic = hasDynamic || dynamic; + } + return hasDynamic; + }, + addObject: function(multiBindDescr, object, staticKeys) { + var me = this, + hasDynamic = false, + dynamic, b, name; + for (name in multiBindDescr) { + b = multiBindDescr[name]; + if (b && (b.reference || Ext.isString(b))) { + dynamic = me.add(b, object, name); + } else if (Ext.isArray(b)) { + dynamic = me.addArray(b, object[name] = []); + } else if (b && b.constructor === Object) { + dynamic = me.addObject(b, object[name] = {}); + } else { + object[name] = b; + dynamic = false; + } + if (staticKeys && !dynamic) { + staticKeys.push(name); + } + hasDynamic = hasDynamic || dynamic; + } + return hasDynamic; + }, + getFullName: function() { + var me = this, + fullName = me.fullName, + bindings = me.bindings, + length = bindings.length, + i; + if (!fullName) { + fullName = '@['; + for (i = 0; i < length; ++i) { + if (i) { + fullName += ','; + } + fullName += bindings[i].getFullName(); + } + fullName += ']'; + me.fullName = fullName; + } + return fullName; + }, + getRawValue: function() { + return this.lastValue; + }, + isDescendantOf: function() { + return false; + }, + isLoading: function() { + for (var bindings = this.bindings, + n = bindings.length; n-- > 0; ) { + if (bindings[n].isLoading()) { + return true; + } + } + return false; + }, + isAvailable: function() { + for (var bindings = this.bindings, + n = bindings.length; n-- > 0; ) { + if (bindings[n].isAvailable()) { + return true; + } + } + return false; + }, + isBindingStatic: function(binding) { + return binding.isTemplateBinding && binding.isStatic; + }, + isStatic: function() { + var bindings = this.bindings, + len = bindings.length, + i, binding; + for (i = 0; i < len; ++i) { + binding = bindings[i]; + if (!this.isBindingStatic(binding)) { + return false; + } + } + return true; + }, + pruneStaticKeys: function() { + var value = Ext.apply({}, this.lastValue), + keys = this.staticKeys, + len = keys.length, + i; + for (i = 0; i < len; ++i) { + delete value[keys[i]]; + } + return value; + }, + react: function() { + this.notify(this.lastValue); + }, + refresh: function() {}, + // @TODO + privates: { + sort: function() { + this.scheduler.sortItems(this.bindings); + } + } +}); +// Schedulable#sort === emptyFn +//me.callParent(); + +/** + * This class manages a formula defined for an `Ext.app.ViewModel`. + * + * ## Formula Basics + * + * Formulas in a `ViewModel` can be defined as simply as just a function: + * + * formulas: { + * xy: function (get) { return get('x') * get('y'); } + * } + * + * When you need to be more explicit, "xy" can become an object. The following means the + * same thing as above: + * + * formulas: { + * xy: { + * get: function (get) { return get('x') * get('y'); } + * } + * } + * + * ### Data Dependencies + * + * One of the important aspects of a `ViewModel` is notification of change. In order to + * manage this, a `ViewModel` *must* know the dependencies between data. In the above case + * this is accomplished by **parsing the text of the function**. While this is convenient + * and reduces the maintenance/risk that would come from explicitly listing dependencies + * separately, there are some rules to be aware of: + * + * * All dependencies are resolved by matching the binding statements in the getter function. + * * If you need to use these values in other ways, cache them as a `var` (following + * the first rule to capture the value) and use that `var`. + * + * In the above formulas, the "xy" formula depends on "x" and "y" in the `ViewModel`. As + * these values change, the formula is called to produce the correct value for "xy". This + * in turn can be used by other formulas. For example: + * + * formulas: { + * xy: function (get) { // "get" is arbitrary but a good convention + * return get('x') * get('y'); + * }, + * + * xyz: function (get) { + * return get('xy') * get('z'); + * } + * } + * + * In the above, "xyz" depends on "xy" and "z" values in the `ViewModel`. + * + * ### The Getter Method + * + * The argument passed to the formula is a function that allows you to retrieve + * the matched bind statements. + * + * formulas: { + * foo: function (get) { + * return get('theUser.address.city'); + * } + * } + * + * In the above, the dependency is resolved to `theUser.address.city`. The formula will not + * be triggered until the value for `city` is present. + * + * ### Capturing Values + * + * If values need to be used repeatedly, you can use a `var` as long as the Rules are not + * broken. + * + * formulas: { + * x2y2: function (get) { + * // These are still "visible" as "get('x')" and "get('y')" so this is OK: + * var x = get('x'), + * y = get('y'); + * + * return x * x * y * y; + * } + * } + * + * ## Explicit Binding + * + * While function parsing is convenient, there are times it is not the best solution. In + * these cases, an explicit `bind` can be given. To revisit the previous example with an + * explicit binding: + * + * formulas: { + * zip: { + * bind: '{foo.bar.zip}', + * + * get: function (zip) { + * // NOTE: the only thing we get is what our bind produces. + * return zip * 2; + * } + * } + * } + * + * In this case we have given the formula an explicit `bind` value so it will no longer + * parse the `get` function. Instead, it will call `{@link Ext.app.ViewModel#bind}` with + * the value of the `bind` property and pass the produced value to `get` whenever it + * changes. + * + * ## Settable Formulas + * + * When a formula is "reversible" it can be given a `set` method to allow it to participate + * in two-way binding. For example: + * + * formulas: { + * fullName: { + * get: function (get) { + * var ret = get('firstName') || ''; + * + * if (get('lastName')) { + * ret += ' ' + get('lastName'); + * } + * + * return ret; + * }, + * + * set: function (value) { + * var space = value.indexOf(' '), + * split = (space < 0) ? value.length : space; + * + * this.set({ + * firstName: value.substring(0, split), + * lastName: value.substring(split + 1) + * }); + * } + * } + * } + * + * When the `set` method is called the `this` reference is the `Ext.app.ViewModel` so it + * just calls its `{@link Ext.app.ViewModel#method-set set method}`. + * + * ## Single Run Formulas + * + * If a formula only needs to produce an initial value, it can be marked as `single`. + * + * formulas: { + * xy: { + * single: true, + * + * get: function (get) { + * return get('x') * get('y'); + * } + * } + * } + * + * This formulas `get` method will be called with `x` and `y` once and then its binding + * to these properties will be destroyed. This means the `get` method (and hence the value + * of `xy`) will only be executed/calculated once. + */ +Ext.define('Ext.app.bind.Formula', { + extend: 'Ext.util.Schedulable', + requires: [ + 'Ext.util.LruCache' + ], + statics: { + getFormulaParser: function(name) { + var cache = this.formulaCache, + parser, s; + if (!cache) { + cache = this.formulaCache = new Ext.util.LruCache({ + maxSize: 20 + }); + } + parser = cache.get(name); + if (!parser) { + // Unescaped: [^\.a-z0-9_]NAMEHERE\(\s*(['"])(.*?)\1\s*\) + s = '[^\\.a-z0-9_]' + Ext.String.escapeRegex(name) + '\\(\\s*([\'"])(.*?)\\1\\s*\\)'; + parser = new RegExp(s, 'gi'); + cache.add(name, parser); + } + return parser; + } + }, + isFormula: true, + calculation: null, + explicit: false, + /** + * @cfg {Object} [bind] + * An explicit bind request to produce data to provide the `get` function. If this is + * specified, the result of this bind is the first argument to `get`. If not given, + * then `get` receives a getter function that can retrieve bind expressions. For details on what can + * be specified for this property see `{@link Ext.app.ViewModel#bind}`. + * @since 5.0.0 + */ + /** + * @cfg {Function} get + * The function to call to calculate the formula's value. The `get` method executes + * with a `this` pointer of the `ViewModel` and receives a getter function or the result of a configured `bind`. + * @since 5.0.0 + */ + /** + * @cfg {Function} [set] + * If provided this method allows a formula to be set. This method is typically called + * when `{@link Ext.app.bind.Binding#setValue}` is called. The `set` method executes + * with a `this` pointer of the `ViewModel`. Whatever values need to be updated can + * be set by calling `{@link Ext.app.ViewModel#set}`. + * @since 5.0.0 + */ + set: null, + /** + * @cfg {Boolean} [single=false] + * This option instructs the binding to call its `destroy` method immediately after + * delivering the initial value. + * @since 5.0.0 + */ + single: false, + fnKeywordArgumentNamesRe: /^function\s*[^\(]*\(\s*([^,\)\s]+)/, + fnKeywordRe: /^\s*function/, + replaceParenRe: /[\(\)]/g, + constructor: function(stub, formula) { + var me = this, + owner = stub.owner, + bindTo, expressions, getter, options; + me.owner = owner; + me.stub = stub; + me.callParent(); + if (formula instanceof Function) { + me.get = getter = formula; + } else { + me.get = getter = formula.get; + me.set = formula.set; + expressions = formula.bind; + if (formula.single) { + me.single = formula.single; + } + if (expressions) { + bindTo = expressions.bindTo; + if (bindTo) { + options = Ext.apply({}, expressions); + delete options.bindTo; + expressions = bindTo; + } + } + } + if (!getter) { + Ext.raise('Must specify a getter method for a formula'); + } + if (expressions) { + me.explicit = true; + } else { + expressions = getter.$expressions || me.parseFormula(getter); + } + me.binding = owner.bind(expressions, me.onChange, me, options); + }, + destroy: function() { + var me = this, + binding = me.binding, + stub = me.stub; + if (binding) { + binding.destroy(); + me.binding = null; + } + if (stub) { + stub.formula = null; + } + me.callParent(); + // Save for last because this is used to remove us from the Scheduler + me.getterFn = me.owner = null; + }, + getFullName: function() { + return this.fullName || (this.fullName = this.stub.getFullName() + '=' + this.callParent() + ')'); + }, + getRawValue: function() { + return this.calculation; + }, + onChange: function() { + if (!this.scheduled) { + this.schedule(); + } + }, + parseFormula: function(formula) { + var str = Ext.Function.toCode(formula), + defaultProp = 'get', + expressions = { + $literal: true + }, + match, getterProp, formulaRe, expr; + if (this.fnKeywordRe.test(str)) { + match = this.fnKeywordArgumentNamesRe.exec(str); + if (match) { + getterProp = match[1]; + } + } else { + match = str.split('=>')[0]; + if (match) { + match = Ext.String.trim(match.replace(this.replaceParenRe, '')).split(','); + getterProp = match[0]; + } + } + getterProp = getterProp || defaultProp; + formulaRe = Ext.app.bind.Formula.getFormulaParser(getterProp); + while ((match = formulaRe.exec(str))) { + expr = match[2]; + expressions[expr] = expr; + } + expressions.$literal = true; + // We store the parse results on the function object because we might reuse the + // formula function (typically when a ViewModel class is created a 2nd+ time). + formula.$expressions = expressions; + return expressions; + }, + react: function() { + var me = this, + owner = me.owner, + data = me.binding.lastValue, + getterFn = me.getterFn, + arg; + if (me.explicit) { + arg = data; + } else { + arg = owner.getFormulaFn(data); + } + me.settingValue = true; + me.stub.set(me.calculation = me.get.call(owner, arg)); + me.settingValue = false; + if (me.single) { + me.destroy(); + } + }, + setValue: function(value) { + this.set.call(this.stub.owner, value); + }, + privates: { + getScheduler: function() { + var owner = this.owner; + return owner && owner.getScheduler(); + }, + sort: function() { + var me = this, + binding = me.binding; + // Our binding may be single:true + if (!binding.destroyed) { + me.scheduler.sortItem(binding); + } + } + } +}); +// Schedulable#sort === emptyFn +//me.callParent(); + +/** + * This class is a base for classes that want to provide a `fly` static method. + * + * For example: + * + * Ext.define('Foo.util.Thing', { + * extend: 'Ext.util.Fly', + * + * // useful stuff + * }); + * + * var thing = Ext.util.Thing.fly(42); // passes 42 to the reset method + * + * // use "thing" + * + * thing.release(); // return to the pool for future reuse + * + * @private + */ +Ext.define('Ext.util.Fly', { + inheritableStatics: { + flyPoolSize: 2, + /** + * @method + * Returns a flyweight instance. These instances should be returned when no + * longer needed by calling `release`. + * + * Additional arguments passed to this method will be passed on to the `reset` + * method. + * + * @return {Ext.util.Fly} the flyweight instance + */ + fly: function() { + var T = this, + flyweights = T.flyweights || (T.flyweights = []), + instance = flyweights.length ? flyweights.pop() : new T(); + instance.reset.apply(instance, arguments); + return instance; + } + }, + /** + * This method should be called when a flyweight instance is no longer needed and + * should be returned to the flyweight pool. + */ + release: function() { + var me = this, + T = me.self, + flyweights = T.flyweights || (T.flyweights = []); + me.reset(); + if (flyweights.length < T.flyPoolSize) { + flyweights.push(me); + } + }, + /** + * Resets this instance to prepare for use. Derived classes may accept additional + * arguments. + * + * When called with no arguments, the class should relinquish any resources it can + * and prepare to wait for potential reuse. + * + * @method reset + * @chainable + * @return {Ext.util.Fly} this + */ + reset: Ext.emptyFn +}); + +/** + * This class is used to parse a string into a series of tokens. The syntax of the string + * is JavaScript-like. This class is useful for creating higher-level parsers to allow + * them to assemble tokens into a meaningful language (such as bind properties). + * + * The following set of punctuation characters are supported: + * + * + - * / ! , : [ ] { } ( ) + * + * This class does not currently separate the dot operator but instead includes it in a + * single "ident" token. Whitespace between tokens is skipped. + * + * Tokens are parsed on-demand when `next` or `peek` are called. As much as possible, + * the returned tokens are reused (e.g., to represent tokens like ":" the same object is + * always returned). For tokens that contain values, a new object must be created to + * return the value. Even so, the `is` property that describes the data is a reused object + * in all cases. + * + * var tokenizer; // see below for getting instance + * + * for (;;) { + * if (!(token = tokenizer.next())) { + * // When null is returned, there are no more tokens + * + * break; + * } + * + * var is = token.is; // the token's classification object + * + * if (is.error) { + * // Once an error is encountered, it will always be returned by + * // peek or next. The error is cleared by calling reset(). + * + * console.log('Syntax error', token.message); + * break; + * } + * + * if (is.ident) { + * // an identifier... + * // use token.value to access the name or dot-path + * + * var t = tokenizer.peek(); // don't consume next token (yet) + * + * if (t && t.is.parenOpen) { + * tokenizer.next(); // we'll take this one + * + * parseThingsInParens(); + * + * t = tokenizer.next(); + * + * mustBeCloseParen(t); + * } + * } + * else if (is.literal) { + * // a literal value (null, true/false, string, number) + * // use token.value to access the value + * } + * else if (is.at) { + * // @ + * } + * } + * + * For details on the returned token see the `peek` method. + * + * There is a pool of flyweight instances to reduce memory allocation. + * + * var tokenizer = Ext.parse.Tokenizer.fly('some.thing:foo()'); + * + * // use tokenizer (see above) + * + * tokenizer.release(); // returns the fly to the flyweigt pool + * + * The `release` method returns the flyweight to the pool for later reuse. Failure to call + * `release` will leave the flyweight empty which simply forces the `fly` method to always + * create new instances on each call. + * + * A tokenizer can also be reused by calling its `reset` method and giving it new text to + * tokenize. + * + * this.tokenizer = new Ext.parse.Tokenizer(); + * + * // Later... + * + * this.tokenizer.reset('some.thing:foo()'); + * + * // use tokenizer (see above) + * + * this.tokenizer.reset(); + * + * The final call to `reset` is optional but will avoid holding large text strings or + * parsed results that rae no longer needed. + * + * @private + */ +Ext.define('Ext.parse.Tokenizer', function(Tokenizer) { + var flyweights = (Tokenizer.flyweights = []), + BOOLEAN = { + literal: true, + "boolean": true + }, + ERROR = { + error: true + }, + IDENT = { + ident: true + }, + LITERAL = { + literal: true + }, + NULL = { + literal: true, + nil: true + }, + NUMBER = { + literal: true, + number: true + }, + STRING = { + literal: true, + string: true + }; + return { + extend: 'Ext.util.Fly', + isTokenizer: true, + statics: { + BOOLEAN: BOOLEAN, + ERROR: ERROR, + IDENT: IDENT, + LITERAL: LITERAL, + NULL: NULL, + NUMBER: NUMBER, + STRING: STRING + }, + config: { + /** + * @cfg {Object} keywords + * A map of keywords that should be mapped to other token types. By default the + * `null`, `true` and `false` keywords are mapped to their respective literal + * value tokens. + */ + keywords: { + 'null': { + type: 'literal', + is: NULL, + value: null + }, + 'false': { + type: 'literal', + is: BOOLEAN, + value: false + }, + 'true': { + type: 'literal', + is: BOOLEAN, + value: true + } + }, + /** + * @cfg {Object} operators + * A map of operators and their names. The keys are the operator text and the + * name (the values) are placed in the token's `is` object as `true`. + */ + operators: { + '+': 'plus', + '-': 'minus', + '*': 'multiply', + '/': 'divide', + '!': 'bang', + ',': 'comma', + ':': 'colon', + '[': 'arrayOpen', + ']': 'arrayClose', + '{': 'curlyOpen', + '}': 'curlyClose', + '(': 'parenOpen', + ')': 'parenClose' + } + }, + /** + * This property is set to an `Error` instance if the parser encounters a syntax + * error. + * @property {Object} error + * @readonly + */ + error: null, + /** + * This property is set to the character index of the current token. This value can + * be captured immediately after calling the `peek` or `next` method to know the + * index of the returned token. This value is not included in the returned token to + * allow those tokens that could otherwise be immutable to be reused. + * @property {Number} index + * @readonly + */ + index: -1, + constructor: function(config) { + this.operators = {}; + this.initConfig(config); + }, + /** + * Advance the token stream and return the next token. See `{@link #peek}` for a + * description of the returned token. + * + * After calling this method, the next call to it or `peek` will not return the same + * token but instead the token that follows the one returned. + * + * @return {Object} The next token in the stream (now consumed). + */ + next: function() { + var token = this.peek(); + this.head = undefined; + // indicates that more parsing is needed (see peek) + return token; + }, + /** + * Peeks at the next token stream and returns it. The token remains as the next token + * and will be returned again by the next call to this method or `next`. + * + * At the end of the token stream, the token returned will be `null`. + * + * If a syntax error is encountered, the returned token will be an `Error` object. It + * has the standard `message` property and also additional properties to make it more + * like a standard token: `error: true`, `type: 'error'` and `at` (the index in the + * string where the syntax error started. + * + * @return {Object} The next token in the stream (not yet consumed). + * + * @return {String} return.type The type of the token. This will be one of the + * following values: `ident`, `literal` and `error` or the text of a operator + * (i.e., "@", "!", ",", ":", "[", "]", "{", "}", "(" or ")"). + * + * @return {String} return.value The value of a `"literal"` token. + * + * @return {Object} return.is An object containing boolean properties based on type. + * @return {Boolean} return.is.literal True if the token is a literal value. + * @return {Boolean} return.is.boolean True if the token is a literal boolean value. + * @return {Boolean} return.is.error True if the token is an error. + * @return {Boolean} return.is.ident True if the token is an identifier. + * @return {Boolean} return.is.nil True if the token is the `null` keyword. + * @return {Boolean} return.is.number True if the token is a number literal. + * @return {Boolean} return.is.string True if the token is a string literal. + * @return {Boolean} return.is.operator True if the token is a operator (i.e., + * "@!,:[]{}()"). operators will also have one of these boolean proprieties, in + * the respective order: `at`, `bang`, `comma`, `colon`, `arrayOpen`, `arrayClose`, + * `curlyOpen`, `curlyClose`, `parentOpen` and `parenClose`). + */ + peek: function() { + var me = this, + error = me.error, + token = me.head; + if (error) { + return error; + } + if (token === undefined) { + me.head = token = me.advance(); + } + return token; + }, + /** + * Returns this flyweight instance to the flyweight pool for reuse. + */ + release: function() { + this.reset(); + if (flyweights.length < Tokenizer.flyPoolSize) { + flyweights.push(this); + } + }, + /** + * Resets the tokenizer for a new string at a given offset (defaults to 0). + * + * @param {String} text The text to tokenize. + * @param {Number} [pos=0] The character position at which to start. + * @param {Number} [end] The index of the first character beyond the token range. + * @returns {Ext.parse.Tokenizer} + */ + reset: function(text, pos, end) { + var me = this; + me.error = null; + me.head = undefined; + me.index = -1; + me.text = text || null; + me.pos = pos || 0; + me.end = (text && end == null) ? text.length : end; + return me; + }, + privates: { + digitRe: /[0-9]/, + identFirstRe: /[a-z_$]/i, + identRe: /[0-9a-z_$]/i, + spaceRe: /[ \t]/, + /** + * The index one beyond the last character of the input text. This defaults to + * the `text.length`. + * @property {Number} end + * @readonly + */ + end: 0, + /** + * The current token at the head of the token stream. This will be `undefined` + * if the next token must be parsed from `text`. It is `null` if there are no + * more tokens. + * @property {Object} head + * @readonly + */ + head: undefined, + /** + * The current character position in the `text` from which the next token will + * be parsed. + * @property {Number} pos + * @readonly + */ + pos: 0, + /** + * The text to be tokenized. + * @property {String} text + * @readonly + */ + text: null, + applyOperators: function(ops) { + var operators = this.operators, + block, c, def, i, len, name, op; + /* + Builds a map one character at a time (i.e., a "trie"): + + operators: { + '=': { + '=': { + token: // the "==" token + }, + + token: // the "=" token + } + } + */ + for (op in ops) { + block = operators; + name = ops[op]; + len = op.length; + for (i = 0; i < len; ++i) { + c = op.charAt(i); + block = block[c] || (block[c] = {}); + } + if (name) { + block.token = def = { + type: 'operator', + value: op, + is: { + operator: true + } + }; + def.is[name] = true; + } else { + block.token = null; + } + } + }, + /** + * Parses and returns the next token from `text` starting at `pos`. + * @return {Object} The next token + */ + advance: function() { + var me = this, + spaceRe = me.spaceRe, + text = me.text, + length = me.end, + c; + while (me.pos < length) { + c = text.charAt(me.pos); + if (spaceRe.test(c)) { + ++me.pos; + // consume the whitespace + + continue; + } + me.index = me.pos; + return me.parse(c); + } + return null; + }, + /** + * Parses the current token that starts with the provided character `c` and + * located at the current `pos` in the `text`. + * @param {String} c The current character. + * @return {Object} The next token + */ + parse: function(c) { + var me = this, + digitRe = me.digitRe, + text = me.text, + length = me.end, + ret; + // Handle ".123" + if (c === '.' && me.pos + 1 < length) { + if (digitRe.test(text.charAt(me.pos + 1))) { + ret = me.parseNumber(); + } + } + if (!ret && me.operators[c]) { + ret = me.parseOperator(c); + } + if (!ret) { + if (c === '"' || c === "'") { + ret = me.parseString(); + } else if (digitRe.test(c)) { + ret = me.parseNumber(); + } else if (me.identFirstRe.test(c)) { + ret = me.parseIdent(); + } else { + ret = me.syntaxError('Unexpected character'); + } + } + return ret; + }, + /** + * Parses the next identifier token. + * @return {Object} The next token. + */ + parseIdent: function() { + var me = this, + identRe = me.identRe, + keywords = me.getKeywords(), + includeDots = !me.operators['.'], + text = me.text, + start = me.pos, + end = start, + length = me.end, + prev = 0, + c, value; + while (end < length) { + c = text.charAt(end); + if (includeDots && c === '.') { + if (prev === '.') { + return me.syntaxError(end, 'Unexpected dot operator'); + } + ++end; + } else if (identRe.test(c)) { + ++end; + } else { + break; + } + prev = c; + } + if (prev === '.') { + return me.syntaxError(end - 1, 'Unexpected dot operator'); + } + value = text.substring(start, me.pos = end); + return (keywords && keywords[value]) || { + type: 'ident', + is: IDENT, + value: value + }; + }, + /** + * Parses the next number literal token. + * @return {Object} The next token. + */ + parseNumber: function() { + var me = this, + digitRe = me.digitRe, + text = me.text, + start = me.pos, + length = me.end, + c, decimal, exp, token; + while (me.pos < length) { + c = text.charAt(me.pos); + if (c === '-' || c === '+') { + if (me.pos !== start) { + return me.syntaxError(start, 'Invalid number'); + } + ++me.pos; + } else if (c === '.') { + if (decimal) { + break; + } + decimal = true; + ++me.pos; + } else if (c === 'e' || c === 'E') { + if (exp) { + break; + } + decimal = exp = true; + // exp from here on, no decimal allowed + c = text.charAt(++me.pos); + // consume E and peek ahead + if (c === '-' || c === '+') { + ++me.pos; + } + } + // keep the exp sign + else if (digitRe.test(c)) { + ++me.pos; + } else { + break; + } + } + token = { + type: 'literal', + is: NUMBER, + // Beware parseFloat as it will stop parsing and return what it could + // parse. For example parseFloat('1x') == 1 whereas +'1x' == NaN. + value: +text.substring(start, me.pos) + }; + if (!isFinite(token.value)) { + token = me.syntaxError(start, 'Invalid number'); + } + return token; + }, + parseOperator: function(c) { + var me = this, + block = me.operators, + text = me.text, + length = me.end, + end = me.pos, + match, matchEnd, token; + while (block[c]) { + block = block[c]; + token = block.token; + ++end; + if (token) { + match = token; + matchEnd = end; + } + if (end < length) { + c = text.charAt(end); + } else { + break; + } + } + if (match) { + me.pos = matchEnd; + } + return match; + }, + /** + * Parses the next string literal token. + * @return {Object} The next token. + */ + parseString: function() { + var me = this, + text = me.text, + pos = me.pos, + start = pos, + length = me.end, + str = '', + c, closed, quote; + quote = text.charAt(pos++); + while (pos < length) { + c = text.charAt(pos++); + if (c === quote) { + closed = true; + break; + } + if (c === '\\' && pos < length) { + c = text.charAt(pos++); + } + // Processing escapes means we cannot use substring() to pick up the + // text as a single chunk... + str += c; + } + me.pos = pos; + if (!closed) { + return me.syntaxError(start, 'Unterminated string'); + } + return { + type: 'literal', + is: STRING, + value: str + }; + }, + /** + * This method is called when a syntax error is encountered. It updates `error` + * and returns the error token. + * @param {Number} at The index of the syntax error (optional). + * @param {String} message The error message. + * @return {Object} The error token. + */ + syntaxError: function(at, message) { + if (typeof at === 'string') { + message = at; + at = this.pos; + } + var suffix = (at == null) ? '' : (' (at index ' + at + ')'), + error = new Error(message + suffix); + error.type = 'error'; + error.is = ERROR; + if (suffix) { + error.at = at; + } + return this.error = error; + } + } + }; +}); + +/** + * This class represents a symbol in the parser. + * @private + */ +Ext.define('Ext.parse.Symbol', { + priority: 0, + /** + * This property holds the name of the property to update when a config provided is + * not an object (just a value). + * @property {String} defaultProperty + */ + constructor: function(id, config) { + var me = this, + defaultProperty = me.defaultProperty; + if (config && typeof config === 'object') { + Ext.apply(me, config); + } else if (config !== undefined && defaultProperty) { + me[defaultProperty] = config; + } + me.id = id; + }, + dump: function() { + var me = this, + ret = { + at: me.at, + arity: me.arity + }, + i; + if ('value' in me) { + ret.value = me.value; + } + if (me.lhs) { + ret.lhs = me.lhs.dump(); + ret.rhs = me.rhs.dump(); + } + if (me.operand) { + ret.operand = me.operand.dump(); + } + if (me.args) { + ret.args = []; + for (i = 0; i < me.args.length; ++i) { + ret.args.push(me.args[i].dump()); + } + } + return ret; + }, + /** + * This abstract method is implemented by operators that follow their operand (like + * a binary operator). When the symbol is encountered in an expression this method + * is called. The name "led" stands for "left denotation". + * + * @param {Ext.parse.Symbol} left + */ + led: function() { + this.parser.syntaxError(this.at, 'Missing operator'); + }, + /** + * This abstract method is implemented by operators that precede their operand (like + * a unary operator). When the symbol is encountered in an expression this method + * is called. The name "nud" stands for "null denotation". + */ + nud: function() { + this.parser.syntaxError(this.at, 'Undefined'); + }, + /** + * This method updates this symbol given an additional config object. This is used + * when a symbol is placed in multiple categories (such `infix` and `prefix`). The + * `priority` is the most likely value to update, but also a `led` or `nud` method + * may be provided to complete the symbol. + * + * @param {Object} config + */ + update: function(config) { + if (config && typeof config === 'object') { + var me = this, + priority = config.priority, + led = config.led, + nud = config.nud; + if (me.priority <= priority) { + me.priority = priority; + } + if (led) { + me.led = led; + } + if (nud) { + me.nud = nud; + } + } + } +}); + +/** + * This class represents a constant in the parser. + * @private + */ +Ext.define('Ext.parse.symbol.Constant', { + extend: 'Ext.parse.Symbol', + arity: 'literal', + isLiteral: true, + defaultProperty: 'value', + constructor: function(id, config) { + this.callParent([ + id, + config + ]); + this._value = this.value; + }, + nud: function() { + var me = this; + // The value property gets smashed by the parser so restore it. + me.value = me._value; + // the next line is here in case this symbol already exists in the symbols table + // and this function overrides that symbol + me.arity = 'literal'; + me.isLiteral = true; + return me; + } +}); + +/** + * This class represents an infix (binary) operator. + * @private + */ +Ext.define('Ext.parse.symbol.Infix', { + extend: 'Ext.parse.Symbol', + arity: 'binary', + isBinary: true, + defaultProperty: 'priority', + led: function(left) { + var me = this; + me.lhs = left; + me.rhs = me.parser.parseExpression(me.priority); + // the next line is here in case this symbol already exists in the symbols table + // and this function overrides that symbol + me.arity = 'binary'; + me.isBinary = true; + return me; + } +}); + +/** + * This class represents an right-associative, infix (binary) operator. + * @private + */ +Ext.define('Ext.parse.symbol.InfixRight', { + extend: 'Ext.parse.symbol.Infix', + led: function(left) { + var me = this; + me.lhs = left; + me.rhs = me.parser.parseExpression(me.priority - 1); + // the next line is here in case this symbol already exists in the symbols table + // and this function overrides that symbol + me.arity = 'binary'; + me.isBinary = true; + return me; + } +}); + +/** + * This class implements the parenthesis operator. + * @private + */ +Ext.define('Ext.parse.symbol.Paren', { + extend: 'Ext.parse.Symbol', + arity: 'binary', + isBinary: true, + priority: 80, + led: function(left) { + // Handles function call operator + var me = this, + args = [], + parser = me.parser, + id = left.id, + type = left.arity; + if (id !== '.' && id !== '[') { + if ((type !== "unary" || id !== "function") && type !== "ident" && id !== "(" && id !== "&&" && id !== "||" && id !== "?") { + parser.syntaxError(left.at, "Expected a variable name."); + } + } + me.arity = 'invoke'; + me.isInvoke = true; + me.operand = left; + me.args = args; + while (parser.token.id !== ')') { + if (args.length) { + parser.advance(','); + } + args.push(parser.parseExpression()); + } + parser.advance(')'); + return me; + }, + nud: function() { + // Handles parenthesized expressions + var parser = this.parser, + ret = parser.parseExpression(); + parser.advance(")"); + return ret; + } +}); + +/** + * This class represents a prefix (unary) operator. + * @private + */ +Ext.define('Ext.parse.symbol.Prefix', { + extend: 'Ext.parse.Symbol', + arity: 'unary', + isUnary: true, + priority: 70, + nud: function() { + var me = this; + me.operand = me.parser.parseExpression(me.priority); + // the next line is here in case this symbol already exists in the symbols table + // and this function overrides that symbol + me.arity = 'unary'; + me.isUnary = true; + return me; + } +}); + +/** + * This class parses simple expressions. The parser can be enhanced by providing any of + * the following configs: + * + * * `constants` + * * `infix` + * * `infixRight` + * * `postfix` + * * `symbols` + * + * The parser requires a `{@link Ext.parse.Tokenizer tokenizer}` which can be configured + * using the `tokenizer` config. The parser keeps the tokenizer instance and recycles it + * as it is itself reused. + * + * See http://javascript.crockford.com/tdop/tdop.html for background on the techniques + * used in this parser. + * @private + */ +Ext.define('Ext.parse.Parser', function() { + var ITSELF = function() { + return this; + }; + return { + extend: 'Ext.util.Fly', + requires: [ + 'Ext.parse.Tokenizer', + 'Ext.parse.symbol.Constant', + 'Ext.parse.symbol.InfixRight', + 'Ext.parse.symbol.Paren', + 'Ext.parse.symbol.Prefix' + ], + isParser: true, + config: { + /** + * @cfg {Object} constants + * A map of identifiers that should be converted to literal value tokens. The + * key in this object is the name of the constant and the value is the constant + * value. + * + * If the value of a key is an object, it is a config object for the + * `{@link Ext.parse.symbol.Constant constant}`. + */ + constants: { + 'null': null, + 'false': false, + 'true': true + }, + /** + * @cfg {Object} infix + * A map of binary operators and their associated precedence (or binding priority). + * These binary operators are left-associative. + * + * If the value of a key is an object, it is a config object for the + * `{@link Ext.parse.symbol.Infix operator}`. + */ + infix: { + //'===': 40, + //'!==': 40, + //'<': 40, + //'<=': 40, + //'>': 40, + //'>=': 40, + '+': 50, + '-': 50, + '*': 60, + '/': 60 + }, + /** + * @cfg {Object} infixRight + * A map of binary operators and their associated precedence (or binding priority). + * These binary operators are right-associative. + * + * If the value of a key is an object, it is a config object for the + * `{@link Ext.parse.symbol.InfixRight operator}`. + */ + infixRight: { + '&&': 30, + '||': 30 + }, + /** + * @cfg {Object} prefix + * A map of unary operators. Typically no value is needed, so `0` is used. + * + * If the value of a key is an object, it is a config object for the + * `{@link Ext.parse.symbol.Prefix operator}`. + */ + prefix: { + '!': 0, + '-': 0, + '+': 0 + }, + /** + * @cfg {Object} symbols + * General language symbols. The values in this object are used as config objects + * to configure the associated `{@link Ext.parse.Symbol symbol}`. If there is no + * configuration, use `0` for the value. + */ + symbols: { + ':': 0, + ',': 0, + ')': 0, + '[': 0, + ']': 0, + '{': 0, + '}': 0, + '(end)': 0, + '(ident)': { + arity: 'ident', + isIdent: true, + nud: ITSELF + }, + '(literal)': { + arity: 'literal', + isLiteral: true, + nud: ITSELF + }, + '(': { + xclass: 'Ext.parse.symbol.Paren' + } + }, + /** + * @cfg {Object/Ext.parse.Tokenizer} tokenizer + * The tokenizer or a config object used to create one. + */ + tokenizer: { + keywords: null + } + }, + // we'll handle keywords here + /** + * @cfg {Ext.parse.Symbol} token + * The current token. These tokens extend this base class and contain additional + * properties such as: + * + * * `at` - The index of the token in the text. + * * `value` - The value of the token (e.g., the name of an identifier). + * + * @readonly + */ + token: null, + constructor: function(config) { + this.symbols = {}; + this.initConfig(config); + }, + /** + * Advances the token stream and returns the next `token`. + * @param {String} [expected] The type of symbol that is expected to follow. + * @return {Ext.parse.Symbol} + */ + advance: function(expected) { + var me = this, + tokenizer = me.tokenizer, + token = tokenizer.peek(), + symbols = me.symbols, + index = tokenizer.index, + is, symbol, value; + if (me.error) { + throw me.error; + } + if (expected) { + me.expect(expected); + } + if (!token) { + return me.token = symbols['(end)']; + } + tokenizer.next(); + is = token.is; + value = token.value; + if (is.ident) { + symbol = symbols[value] || symbols['(ident)']; + } else if (is.operator) { + if (!(symbol = symbols[value])) { + me.syntaxError(token.at, 'Unknown operator "' + value + '"'); + } + } else if (is.literal) { + symbol = symbols['(literal)']; + } else { + me.syntaxError(token.at, 'Unexpected token'); + } + me.token = symbol = Ext.Object.chain(symbol); + symbol.at = index; + symbol.value = value; + if (!symbol.arity) { + symbol.arity = token.type; + } + return symbol; + }, + expect: function(expected) { + var token = this.token; + if (expected !== token.id) { + this.syntaxError(token.at, 'Expected "' + expected + '"'); + } + return this; + }, + /** + * + * @param {Number} [rightPriority=0] The precedence of the current operator. + * @return {Ext.parse.Symbol} The parsed expression tree. + */ + parseExpression: function(rightPriority) { + var me = this, + token = me.token, + left; + rightPriority = rightPriority || 0; + me.advance(); + left = token.nud(); + while (rightPriority < (token = me.token).priority) { + me.advance(); + left = token.led(left); + } + return left; + }, + /** + * Resets this parser given the text to parse or a `Tokenizer`. + * @param {String} text + * @param {Number} [pos=0] The character position at which to start. + * @param {Number} [end] The index of the first character beyond the token range. + * @return {Ext.parse.Parser} + */ + reset: function(text, pos, end) { + var me = this; + me.error = me.token = null; + me.tokenizer.reset(text, pos, end); + me.advance(); + // kick start this.token + return me; + }, + /** + * This method is called when a syntax error is encountered. It updates `error` + * and returns the error token. + * @param {Number} at The index of the syntax error (optional). + * @param {String} message The error message. + * @return {Object} The error token. + */ + syntaxError: function(at, message) { + if (typeof at === 'string') { + message = at; + at = this.pos; + } + var suffix = (at == null) ? '' : (' (at index ' + at + ')'), + error = new Error(message + suffix); + error.type = 'error'; + if (suffix) { + error.at = at; + } + throw this.error = error; + }, + privates: { + /** + * This property is set to an `Error` instance if the parser encounters a syntax + * error. + * @property {Object} error + * @readonly + */ + error: null, + addSymbol: function(id, config, type, update) { + var symbols = this.symbols, + symbol = symbols[id], + cfg, length, i; + if (symbol) { + // If the symbol was already defined then we need to update it + // we either use the config provided in the symbol definition + // or we use the `update` param to build a config object. + // We usually need to update either `led` or `nud` function + if (typeof config === 'object') { + cfg = config; + } else if (update && type) { + update = Ext.Array.from(update); + length = update.length; + cfg = {}; + for (i = 0; i < length; i++) { + cfg[update[i]] = type.prototype[update[i]]; + } + } else { + return symbol; + } + symbol.update(cfg); + } else { + if (config && config.xclass) { + type = Ext.ClassManager.get(config.xclass); + } else { + type = type || Ext.parse.Symbol; + } + symbols[id] = symbol = new type(id, config); + symbol.parser = this; + } + return symbol; + }, + addSymbols: function(symbols, type, update) { + for (var id in symbols) { + this.addSymbol(id, symbols[id], type, update); + } + }, + applyConstants: function(constants) { + this.addSymbols(constants, Ext.parse.symbol.Constant, 'nud'); + }, + applyInfix: function(operators) { + this.addSymbols(operators, Ext.parse.symbol.Infix, 'led'); + }, + applyInfixRight: function(operators) { + this.addSymbols(operators, Ext.parse.symbol.InfixRight, 'led'); + }, + applyPrefix: function(operators) { + this.addSymbols(operators, Ext.parse.symbol.Prefix, 'nud'); + }, + applySymbols: function(symbols) { + this.addSymbols(symbols); + }, + applyTokenizer: function(config) { + var ret = config; + if (config && !config.isTokenizer) { + ret = new Ext.parse.Tokenizer(config); + } + this.tokenizer = ret; + } + } + }; +}); + +/** + * This class parses bind template format expressions. + * @private + */ +Ext.define('Ext.app.bind.Parser', { + extend: 'Ext.parse.Parser', + requires: [ + 'Ext.util.Format' + ], + infix: { + ':': { + priority: 70, + // bind tighter than multiplication + dump: function() { + var me = this, + ret = { + at: me.at, + arity: me.arity, + value: me.value, + operand: me.operand.dump(), + fmt: [] + }, + fmt = me.fmt, + i; + for (i = 0; i < fmt.length; ++i) { + ret.fmt.push(fmt[i].dump()); + } + return ret; + }, + led: function(left) { + // We parse a sequence of ":" separated formatter expressions (like a + // traditional "," operator) and gather the sequence in our "fmt" array + var me = this; + me.arity = 'formatter'; + me.operand = left; + me.fmt = me.parser.parseFmt(); + return me; + } + }, + '?': { + priority: 20, + led: function(left) { + var me = this, + parser = me.parser, + symbol = parser.symbols[':'], + temp; + me.condition = left; + // temporarily set priority of `:` symbol to 0 + temp = symbol.priority; + symbol.priority = 0; + me.tv = parser.parseExpression(0); + me.parser.advance(':'); + // restore priority of `:` + symbol.priority = temp; + me.fv = parser.parseExpression(0); + me.arity = 'ternary'; + return me; + } + }, + '===': 40, + '!==': 40, + '==': 40, + '!=': 40, + '<': 40, + '<=': 40, + '>': 40, + '>=': 40 + }, + symbols: { + '(': { + nud: function() { + // Handles parenthesized expressions + var parser = this.parser, + symbol = parser.symbols[':'], + ret, temp; + // temporarily set priority of `:` symbol to 70 to correctly extract formatters inside parans + temp = symbol.priority; + symbol.priority = 70; + ret = parser.parseExpression(); + parser.advance(")"); + // restore priority of `:` + symbol.priority = temp; + return ret; + } + } + }, + prefix: { + '@': 0 + }, + tokenizer: { + operators: { + '@': 'at', + '?': 'qmark', + '===': 'feq', + '!==': 'fneq', + '==': 'eq', + '!=': 'neq', + '<': 'lt', + '<=': 'lte', + '>': 'gt', + '>=': 'gte', + '&&': 'and', + '||': 'or' + } + }, + /** + * Parses the expression from the current position and compiles it as a function. The expression tokens are + * stored in the provided arguments. + * + * Called by Ext.app.bind.Template. + * + * @param {Array} tokens + * @param {Object} tokensMaps + * @return {Function} + */ + compileExpression: function(tokens, tokensMaps) { + var me = this, + debug, fn; + me.tokens = tokens; + me.tokensMap = tokensMaps; + debug = me.token.value === '@' && me.tokenizer.peek(); + if (debug) { + debug = debug.value === 'debugger'; + if (debug) { + me.advance(); + me.advance(); + } + } + fn = me.parseSlot(me.parseExpression(), debug); + me.tokens = me.tokensMap = null; + return fn; + }, + /** + * Parses the chained format functions and compiles them as a function. + * + * Called by the grid column formatter. + * + * @return {Function} + */ + compileFormat: function() { + var fn; + try { + fn = this.parseSlot({ + arity: 'formatter', + fmt: this.parseFmt(), + operand: { + arity: 'ident', + value: 'dummy' + } + }); + this.expect('(end)'); + } catch (e) { + Ext.raise('Invalid format expression: "' + this.tokenizer.text + '"'); + } + return fn; + }, + privates: { + // Chrome really likes "new Function" to realize the code block (as in it is + // 2x-3x faster to call it than using eval), but Firefox chokes on it badly. + // IE and Opera are also fine with the "new Function" technique. + useEval: Ext.isGecko, + escapeRe: /("|'|\\)/g, + /** + * Parses a series of ":" delimited format expressions. + * @return {Ext.parse.Symbol[]} + * @private + */ + parseFmt: function() { + // We parse a sequence of ":" separated formatter expressions (like a + // traditional "," operator) + var me = this, + fmt = [], + priority = me.symbols[':'].priority, + expr; + do { + if (fmt.length) { + me.advance(); + } + expr = me.parseExpression(priority); + if (expr.isIdent || expr.isInvoke) { + fmt.push(expr); + } else { + me.syntaxError(expr.at, 'Expected formatter name'); + } + } while (me.token.id === ':'); + return fmt; + }, + /** + * Parses the expression tree and compiles it as a function + * + * @param expr + * @param {Boolean} debug + * @return {Function} + * @private + */ + parseSlot: function(expr, debug) { + var me = this, + defs = [], + body = [], + tokens = me.tokens || [], + fn, code, i, length, temp; + me.definitions = defs; + me.body = body; + body.push('return ' + me.compile(expr) + ';'); + // now we have the tokens + length = tokens.length; + code = 'var fm = Ext.util.Format,\nme,'; + temp = 'var a = Ext.Array.from(values);\nme = scope;\n'; + if (tokens.length) { + for (i = 0; i < length; i++) { + code += 'v' + i + ((i == length - 1) ? ';' : ','); + temp += 'v' + i + ' = a[' + i + ']; '; + } + } else { + code += 'v0;'; + temp += 'v0 = a[0];'; + } + defs = Ext.Array.insert(defs, 0, [ + code + ]); + body = Ext.Array.insert(body, 0, [ + temp + ]); + body = body.join('\n'); + if (debug) { + body = 'debugger;\n' + body; + } + defs.push((me.useEval ? '$=' : 'return') + ' function (values, scope) {', body, '}'); + code = defs.join('\n'); + fn = me.useEval ? me.evalFn(code) : (new Function('Ext', code))(Ext); + me.definitions = me.body = null; + return fn; + }, + /** + * Compiles the specified symbol + * + * @param expr + * @return {String} + * @private + */ + compile: function(expr) { + var me = this, + v; + switch (expr.arity) { + case 'ident': + // identifiers are our expression's tokens + return me.addToken(expr.value); + case 'literal': + v = expr.value; + // strings need to be escaped before adding them to formula + return (typeof v === 'string') ? '"' + String(v).replace(me.escapeRe, '\\$1') + '"' : v; + case 'unary': + return me.compileUnary(expr); + case 'binary': + return me.compileBinary(expr); + case 'ternary': + return me.compileTernary(expr); + case 'formatter': + return me.compileFormatter(expr); + } + return this.syntaxError(expr.at, 'Compile error! Unknown symbol'); + }, + /** + * Compiles unary symbol + * + * @param expr + * @return {String} + * @private + */ + compileUnary: function(expr) { + var v = expr.value, + op = expr.operand; + if (v === '!' || v === '-' || v === '+') { + return v + '(' + this.compile(op) + ')'; + } else if (v === '@') { + // @ should be used to prefix global identifiers and nothing else + if (!op.isIdent) { + return this.syntaxError(expr.at, 'Compile error! Unexpected symbol'); + } + return op.value; + } + return ''; + }, + /** + * Compiles binary symbol + * + * @param expr + * @return {String} + * @private + */ + compileBinary: function(expr) { + return '(' + this.compile(expr.lhs) + ' ' + expr.value + ' ' + this.compile(expr.rhs) + ')'; + }, + /** + * Compiles ternary symbol + * + * @param expr + * @return {String} + * @private + */ + compileTernary: function(expr) { + return '(' + this.compile(expr.condition) + ' ? ' + this.compile(expr.tv) + ' : ' + this.compile(expr.fv) + ')'; + }, + /** + * Compiles formatter symbol + * + * @param expr + * @return {String} + * @private + */ + compileFormatter: function(expr) { + var me = this, + fmt = expr.fmt, + length = fmt.length, + body = [ + 'var ret;' + ], + i; + if (fmt.length) { + body.push('ret = ' + me.compileFormatFn(fmt[0], me.compile(expr.operand)) + ';'); + for (i = 1; i < length; i++) { + body.push('ret = ' + me.compileFormatFn(fmt[i], 'ret') + ';'); + } + } + body.push('return ret;'); + return me.addFn(body.join('\n')); + }, + /** + * Compiles a single format symbol using `value` as the first argument + * + * @param expr + * @param value + * @return {String} + * @private + */ + compileFormatFn: function(expr, value) { + var fmt, + args = [], + code = '', + length, i; + if (expr.isIdent) { + // the function has no arguments + fmt = expr.value; + } else if (expr.isInvoke) { + fmt = expr.operand.value; + args = expr.args; + } + if (fmt.substring(0, 5) === 'this.') { + fmt = 'me.' + fmt.substring(5); + } else { + if (!(fmt in Ext.util.Format)) { + return this.syntaxError(expr.at, 'Compile error! Invalid format specified "' + fmt + '"'); + } + fmt = 'fm.' + fmt; + } + code += value; + length = args.length; + for (i = 0; i < length; i++) { + code += ', ' + this.compile(args[i]); + } + return fmt + '(' + code + ')'; + }, + /** + * Adds a new function to the final compiled function + * @param body + * @return {string} Name of the function + * @private + */ + addFn: function(body) { + var defs = this.definitions, + name = 'f' + defs.length; + defs.push('function ' + name + '() {', body, '}'); + return name + '()'; + }, + /** + * Evaluates a function + * @param $ + * @return {Function} + * @private + */ + evalFn: function($) { + eval($); + return $; + }, + /** + * Adds the specified expression token to the internal tokens + * @param token + * @return {string} Name of the variable assigned for this token in the compiled function + * @private + */ + addToken: function(token) { + var tokensMap = this.tokensMap, + tokens = this.tokens, + pos = 0; + // token can be ignored when this function is called via `compileFormatFn` + if (tokensMap && tokens) { + if (token in tokensMap) { + pos = tokensMap[token]; + } else { + tokensMap[token] = pos = tokens.length; + tokens.push(token); + } + } + return 'v' + pos; + } + } +}); + +/** + * This class holds the parsed text for a bind template. The syntax is that of a normal + * `Ext.Template` except that substitution tokens can contain dots to reference property + * names. + * + * The template is parsed and stored in a representation like this: + * + * me.text = 'Hey {foo.bar}! Test {bar} and {foo.bar} with {abc} over {bar:number}' + * + * me.tokens = [ 'foo.bar', 'bar', 'abc' ] + * + * me.buffer = [ me.slots = [ + * 'Hey ', undefined, + * undefined, { token: 'foo.bar', pos: 0 }, + * '! Test ', undefined, + * undefined, { token: 'bar', pos: 1 }, + * ' and ', undefined, + * undefined, { token: 'foo.bar', pos: 0 }, + * ' with ', undefined, + * undefined, { token: 'abc', pos: 2 }, + * ' over ', undefined, + * undefined { token: 'bar', fmt: 'number', pos: 1 } + * ] ] + * + * @private + * @since 5.0.0 + */ +Ext.define('Ext.app.bind.Template', { + requires: [ + 'Ext.util.Format', + 'Ext.app.bind.Parser' + ], + /** + * @cfg {Boolean} escapes + * Set to `true` to process escape characters as part of bind expressions. + * + * The `'\'` character is used to escape the next character, treating it + * as a literal character even if it is a `'{'` or other escape. + * + * The `'~~'` sequence will treat any subsequent characters as a verbatim, + * literal expression and no extra processing will take place. This includes + * escapes and replacement tokens. + * + * @since 6.5.2 + * @private + */ + escapes: false, + /** + * @property {String[]} buffer + * Initially this is just the array of string fragments with `null` between each + * to hold the place of a substitution token. On first use these slots are filled + * with the token's value and this array is joined to form the output. + * @private + */ + buffer: null, + /** + * @property {Object[]} slots + * The elements of this array line up with those of `buffer`. This array holds + * the parsed information for the substitution token that fills a given slot in + * the generated string. Indices that correspond to literal text are `null`. + * + * Consider the following substitution token: + * + * {foo:this.fmt(2,4)} + * + * The object in this array has the following properties to describe this token: + * + * * `fmt` The name of the formatting function ("fmt") or `null` if none. + * * `index` The numeric index if this is not a named substitution or `null`. + * * `not` True if the token has a logical not ("!") at the front. + * * `token` The name of the token ("foo") if not an `index`. + * * `pos` The position of this token in the `tokens` array. + * * `scope` A reference to the object on which the `fmt` method exists. This + * will be `Ext.util.Format` if no "this." is present or `null` if it is (or + * if there is no `fmt`). In the above example, this is `null` to indicate the + * scope is unknown. + * * `args` An array of arguments to `fmt` if the arguments are simple enough + * to parse directly. Otherwise this is `null` and `fn` is used. + * * `fn` A generated function to use to evaluate the arguments to the `fmt`. In + * rare cases these arguments can reference global variables so the expression + * must be evaluated on each call. + * * `format` The method to call to perform the format. This method accepts the + * scope (in case `scope` is unknown) and the value. This function is `null` if + * there is no `fmt`. + * + * @private + */ + slots: null, + /** + * @property {String[]} tokens + * The distinct set of tokens used in the template excluding formatting. This is + * used to ensure that only one bind is performed per unique token. This array is + * passed to {@link Ext.app.ViewModel#bind} to perform a "multi-bind". The result + * is an array of values corresponding these tokens. Each entry in `slots` then + * knows its `pos` in this array from which to pick up its value, apply formats + * and place in `buffer`. + * @private + */ + tokens: null, + /** + * @param {String} text The text of the template. + */ + constructor: function(text) { + var me = this, + initters = me._initters, + name; + me.text = text; + for (name in initters) { + me[name] = initters[name]; + } + }, + /** + * @property {Object} _initters + * Each of the methods contained on this object are placed in new instances to lazily + * parse the template text. + * @private + * @since 5.0.0 + */ + _initters: { + apply: function(values, scope) { + return this.parse().apply(values, scope); + }, + getTokens: function() { + return this.parse().getTokens(); + } + }, + /** + * Applies this template to the given `values`. The `values` must correspond to the + * `tokens` returned by `getTokens`. + * + * @param {Array} values The values of the `tokens`. + * @param {Object} scope The object instance to use for "this." formatter calls in the + * template. + * @return {String} + * @since 5.0.0 + */ + apply: function(values, scope) { + var me = this, + slots = me.slots, + buffer = me.buffer, + length = slots.length, + i, slot; + for (i = 0; i < length; ++i) { + slot = slots[i]; + if (slot) { + buffer[i] = slot(values, scope); + } + } + // If we have only one component and it is a slot (a {} component), then we + // want to evaluate to whatever that expression generated. + if (slot && me.single) { + return buffer[0]; + } + return buffer.join(''); + }, + getText: function() { + return this.buffer.join(''); + }, + /** + * Returns the distinct set of binding tokens for this template. + * @return {String[]} The `tokens` for this template. + */ + getTokens: function() { + return this.tokens; + }, + /** + * Returns true if the expression is static, meaning it has no + * tokens or slots that need to be evaluated. + * + * @private + */ + isStatic: function() { + var tokens = this.getTokens(), + slots = this.slots; + return (tokens.length === 0 && slots.length === 0); + }, + privates: { + literalChar: '~', + escapeChar: '\\', + /** + * Parses the template text into `buffer`, `slots` and `tokens`. This method is called + * automatically when the template is first used. + * @return {Ext.app.bind.Template} this + * @private + */ + parse: function() { + // NOTE: The particulars of what is stored here, while private, are likely to be + // important to Sencha Architect so changes need to be coordinated. + var me = this, + text = me.text, + parser = Ext.app.bind.Parser.fly(), + buffer = (me.buffer = []), + slots = (me.slots = []), + length = text.length, + pos = 0, + escapes = me.escapes, + current = '', + i = 0, + esc = me.escapeChar, + lit = me.literalChar, + escaped, tokens, tokensMap, lastEscaped, c, prev, key; + // Remove the initters so that we don't get called here again. + for (key in me._initters) { + delete me[key]; + } + me.tokens = tokens = []; + me.tokensMap = tokensMap = {}; + // text = 'Hello {foo:this.fmt(2,4)} World {bar} - {1}' + while (i < length) { + c = text[i]; + lastEscaped = escaped; + escaped = escapes && c === esc; + if (escaped) { + c = text[i + 1]; + ++i; + } else if (c === lit && prev === lit && !lastEscaped) { + current = current.slice(0, -1); + current += text.substring(i + 1); + break; + } else if (c === '{') { + if (current) { + buffer[pos++] = current; + current = ''; + } + // parse expression + parser.reset(text, i + 1); + i = me.parseExpression(parser, pos); + ++pos; + + continue; + } + current += c; + ++i; + prev = c; + } + if (current) { + buffer[pos] = current; + } + parser.release(); + me.single = buffer.length === 0 && slots.length === 1; + return me; + }, + parseExpression: function(parser, pos) { + var i; + this.slots[pos] = parser.compileExpression(this.tokens, this.tokensMap); + i = parser.token.at + 1; + // skip over the "}" token + parser.expect('}'); + // ensure the next token is "}" + return i; + } + } +}); + +/** + * This class is created to manage a template against a `ViewModel`. A binding of this + * type uses `{@link Ext.app.bind.Template}` to process the template text so see that + * class for details on template syntax. + * + * The bindings to provide the data needed by the template are managed here. + */ +Ext.define('Ext.app.bind.TemplateBinding', { + extend: 'Ext.app.bind.BaseBinding', + requires: [ + 'Ext.app.bind.Multi', + 'Ext.app.bind.Template' + ], + isTemplateBinding: true, + lastValue: undefined, + value: undefined, + constructor: function(template, owner, callback, scope, options) { + var me = this, + tpl = new Ext.app.bind.Template(template), + tokens = tpl.getTokens(); + me.callParent([ + owner, + callback, + scope, + options + ]); + me.tpl = tpl; + me.tokens = tokens; + tokens.$literal = true; + // If we don't have any tokens, then we've just got a static string. + if (!tpl.isStatic()) { + me.multiBinding = new Ext.app.bind.Multi(tokens, owner, me.onBindData, me); + } else { + me.isStatic = true; + me.onData(tpl.getText()); + } + }, + destroy: function() { + var me = this; + Ext.destroy(me.multiBinding); + me.tpl = me.multiBinding = null; + me.callParent(); + }, + getFullName: function() { + var multi = this.multiBinding; + return this.fullName || (this.fullName = '$' + (multi ? multi.getFullName() : this.callParent())); + }, + getRawValue: function() { + return this.value; + }, + getTemplateScope: function() { + return null; + }, + isAvailable: function() { + var multi = this.multiBinding; + return multi ? multi.isAvailable() : false; + }, + isDescendantOf: function() { + return false; + }, + isLoading: function() { + var multi = this.multiBinding; + return multi ? multi.isLoading() : false; + }, + onBindData: function(data) { + this.onData(this.tpl.apply(data, this.getTemplateScope())); + }, + onData: function(value) { + var me = this, + lastValue = me.value; + if (lastValue !== (me.value = value)) { + me.lastValue = lastValue; + me.schedule(); + } + }, + react: function() { + this.notify(this.value); + }, + refresh: function() { + var multi = this.multiBinding; + if (multi) { + multi.refresh(); + } + }, + privates: { + sort: function() { + var multi = this.multiBinding; + if (multi) { + this.scheduler.sortItem(multi); + } + } + } +}); +// Schedulable#sort === emptyFn +//me.callParent(); + +/** + * A chained store is a store that is a "view" of an existing store. The data comes from the + * {@link #source}, however this view of the store may be sorted & filtered independently without + * having any impact on the {@link #source} store. + */ +Ext.define('Ext.data.ChainedStore', { + extend: 'Ext.data.AbstractStore', + alias: 'store.chained', + /** + * @property {Boolean} isChainedStore + * `true` in this class to identify an object as an instantiated ChainedStore, or subclass thereof. + */ + isChainedStore: true, + config: { + /** + * @cfg {Ext.data.Store/String} source + * The backing data source for this chained store. Either a store instance + * or the id of an existing store. + */ + source: null, + remoteFilter: false, + remoteSort: false + }, + mixins: [ + 'Ext.data.LocalStore' + ], + updateRemoteFilter: function(remoteFilter, oldRemoteFilter) { + if (remoteFilter) { + Ext.raise('Remote filtering cannot be used with chained stores.'); + } + this.callParent([ + remoteFilter, + oldRemoteFilter + ]); + }, + updateRemoteSort: function(remoteSort, oldRemoteSort) { + if (remoteSort) { + Ext.raise('Remote sorting cannot be used with chained stores.'); + } + this.callParent([ + remoteSort, + oldRemoteSort + ]); + }, + remove: function() { + var source = this.getSource(); + if (!source) { + Ext.raise('Cannot remove records with no source.'); + } + return source.remove.apply(source, arguments); + }, + removeAll: function() { + var source = this.getSource(); + if (!source) { + Ext.raise('Cannot remove records with no source.'); + } + return source.removeAll(); + }, + getData: function() { + var me = this, + data = me.data; + if (!data) { + me.data = data = me.constructDataCollection(); + } + return data; + }, + getTotalCount: function() { + return this.getCount(); + }, + getSession: function() { + return this.getSourceValue('getSession', null); + }, + applySource: function(source) { + if (source) { + var original = source, + s; + source = Ext.data.StoreManager.lookup(source); + if (!source) { + s = 'Invalid source {0}specified for Ext.data.ChainedStore'; + s = Ext.String.format(s, typeof original === 'string' ? '"' + original + '" ' : ''); + Ext.raise(s); + } + } + return source; + }, + updateSource: function(source, oldSource) { + var me = this, + data; + if (oldSource && !oldSource.destroyed) { + oldSource.removeObserver(me); + } + if (source) { + data = me.getData(); + data.setSource(source.getData()); + if (!me.isInitializing) { + me.fireEvent('refresh', me); + me.fireEvent('datachanged', me); + } + source.addObserver(me); + } + }, + /** + * Get the model used for this store. + * @return {Ext.data.Model} The model + */ + getModel: function() { + return this.getSourceValue('getModel', null); + }, + getProxy: function() { + return null; + }, + onCollectionAdd: function(collection, info) { + var me = this, + records = info.items, + lastChunk = !info.next; + if (me.ignoreCollectionAdd) { + return; + } + // Collection add changes the items reference of the collection, and that array + // object if directly referenced by Ranges. The ranges have to refresh themselves + // upon add. + if (me.activeRanges) { + me.syncActiveRanges(); + } + me.fireEvent('add', me, records, info.at); + // If there is a next property, that means there is another range that needs + // to be removed after this. Wait until everything is gone before firign datachanged + // since it should be a bulk operation + if (lastChunk) { + me.fireEvent('datachanged', me); + } + }, + // Our collection tells us that an item has changed + onCollectionItemChange: function(collection, info) { + var me = this, + record = info.item, + modifiedFieldNames = info.modified || null, + type = info.meta; + // Inform any interested parties that a record has been mutated. + // This will be invoked on TreeStores in which the invoking record + // is an descendant of a collapsed node, and so *will not be contained by this store + me.onUpdate(record, type, modifiedFieldNames, info); + me.fireEvent('update', me, record, type, modifiedFieldNames, info); + me.fireEvent('datachanged', me); + }, + onCollectionUpdateKey: function(source, details) { + // Must react to upstream Collection key update by firing idchanged event + this.fireEvent('idchanged', this, details.item, details.oldKey, details.newKey); + }, + onUpdate: Ext.emptyFn, + onCollectionRemove: function(collection, info) { + var me = this, + records = info.items, + lastChunk = !info.next; + if (me.ignoreCollectionRemove) { + return; + } + me.fireEvent('remove', me, records, info.at, false); + // If there is a next property, that means there is another range that needs + // to be removed after this. Wait until everything is gone before firign datachanged + // since it should be a bulk operation + if (lastChunk) { + me.fireEvent('datachanged', me); + } + }, + onSourceBeforeLoad: function(source, operation) { + this.fireEvent('beforeload', this, operation); + this.callObservers('BeforeLoad', [ + operation + ]); + }, + onSourceAfterLoad: function(source, records, successful, operation) { + this.fireEvent('load', this, records, successful, operation); + this.callObservers('AfterLoad', [ + records, + successful, + operation + ]); + }, + onFilterEndUpdate: function() { + this.callParent(arguments); + this.callObservers('Filter'); + }, + onSourceBeforePopulate: function() { + this.ignoreCollectionAdd = true; + this.callObservers('BeforePopulate'); + }, + onSourceAfterPopulate: function() { + var me = this; + me.ignoreCollectionAdd = false; + me.fireEvent('datachanged', me); + me.fireEvent('refresh', me); + this.callObservers('AfterPopulate'); + }, + onSourceBeforeClear: function() { + this.ignoreCollectionRemove = true; + this.callObservers('BeforeClear'); + }, + onSourceAfterClear: function() { + this.ignoreCollectionRemove = false; + this.callObservers('AfterClear'); + }, + onSourceBeforeRemoveAll: function() { + this.ignoreCollectionRemove = true; + this.callObservers('BeforeRemoveAll'); + }, + onSourceAfterRemoveAll: function(source, silent) { + var me = this; + me.ignoreCollectionRemove = false; + if (!silent) { + me.fireEvent('clear', me); + me.fireEvent('datachanged', me); + } + this.callObservers('AfterRemoveAll', [ + silent + ]); + }, + onSourceFilter: function() { + var me = this; + me.fireEvent('refresh', me); + me.fireEvent('datachanged', me); + }, + hasPendingLoad: function() { + return this.getSourceValue('hasPendingLoad', false); + }, + isLoaded: function() { + return this.getSourceValue('isLoaded', false); + }, + isLoading: function() { + return this.getSourceValue('isLoading', false); + }, + doDestroy: function() { + var me = this; + me.observers = null; + me.setSource(null); + me.getData().destroy(true); + me.data = null; + me.callParent(); + }, + privates: { + getSourceValue: function(method, defaultValue) { + var source = this.getSource(), + val = defaultValue; + if (source && !source.destroyed) { + val = source[method](); + } + return val; + }, + isMoving: function() { + var source = this.getSource(); + return source.isMoving ? source.isMoving.apply(source, arguments) : false; + }, + loadsSynchronously: function() { + return this.getSource().loadsSynchronously(); + } + } +}); +// Provides docs from the mixin +/** + * @method add + * @inheritdoc Ext.data.LocalStore#add + */ +/** + * @method each + * @inheritdoc Ext.data.LocalStore#each + */ +/** + * @method collect + * @inheritdoc Ext.data.LocalStore#collect + */ +/** + * @method getById + * @inheritdoc Ext.data.LocalStore#getById + */ +/** + * @method getByInternalId + * @inheritdoc Ext.data.LocalStore#getByInternalId + */ +/** + * @method indexOf + * @inheritdoc Ext.data.LocalStore#indexOf + */ +/** + * @method indexOfId + * @inheritdoc Ext.data.LocalStore#indexOfId + */ +/** + * @method insert + * @inheritdoc Ext.data.LocalStore#insert + */ +/** + * @method queryBy + * @inheritdoc Ext.data.LocalStore#queryBy + */ +/** + * @method query + * @inheritdoc Ext.data.LocalStore#query + */ +/** + * @method first + * @inheritdoc Ext.data.LocalStore#first + */ +/** + * @method last + * @inheritdoc Ext.data.LocalStore#last + */ +/** + * @method sum + * @inheritdoc Ext.data.LocalStore#sum + */ +/** + * @method count + * @inheritdoc Ext.data.LocalStore#count + */ +/** + * @method min + * @inheritdoc Ext.data.LocalStore#min + */ +/** + * @method max + * @inheritdoc Ext.data.LocalStore#max + */ +/** + * @method average + * @inheritdoc Ext.data.LocalStore#average + */ +/** + * @method aggregate + * @inheritdoc Ext.data.LocalStore#aggregate + */ + +/** + * This class manages arbitrary data and its relationship to data models. Instances of + * `ViewModel` are associated with some `Component` and then used by their child items + * for the purposes of Data Binding. + * + * # Binding + * + * The most commonly used aspect of a `ViewModel` is the `bind` method. This method takes + * a "bind descriptor" (see below) and a callback to call when the data indicated by the + * bind descriptor either becomes available or changes. + * + * The `bind` method, based on the bind descriptor given, will return different types of + * "binding" objects. These objects maintain the connection between the requested data and + * the callback. Bindings ultimately derive from `{@link Ext.app.bind.BaseBinding}` + * which provides several methods to help manage the binding. + * + * Perhaps the most important method is `destroy`. When the binding is no longer needed + * it is important to remember to `destroy` it. Leaking bindings can cause performance + * problems or worse when callbacks are called at unexpected times. + * + * The types of bindings produced by `bind` are: + * + * * `{@link Ext.app.bind.Binding}` + * * `{@link Ext.app.bind.Multi}` + * * `{@link Ext.app.bind.TemplateBinding}` + * + * ## Bind Descriptors + * + * A "bind descriptor" is a value (a String, an Object or an array of these) that describe + * the desired data. Any piece of data in the `ViewModel` can be described by a bind + * descriptor. + * + * ### Textual Bind Descriptors + * + * The simplest and most common form of bind descriptors are strings that look like an + * `Ext.Template` containing text and tokens surrounded by "{}" with dot notation inside + * to traverse objects and their properties. + * + * For example: + * + * * `'Hello {user.name}!'` + * * `'You have selected "{selectedItem.text}".'` + * * `'{!isDisabled}'` + * * `'{a > b ? "Bigger" : "Smaller"}'` + * * `'{user.groups}'` + * + * All except the last are `{@link Ext.app.bind.TemplateBinding template bindings}` + * which use the familiar `Ext.Template` syntax with some slight differences. For more on + * templates see `{@link Ext.app.bind.Template}`. + * + * The last descriptor is called a "direct bind descriptor". This special form of + * bind maps one-to-one to some piece of data in the `ViewModel` and is managed by the + * `{@link Ext.app.bind.Binding}` class. + * + * #### Two-Way Descriptors + * + * A direct bind descriptor may be able to write back a value to the `ViewModel` as well + * as retrieve one. When this is the case, they are said to be "two-way". For example: + * + * var binding = viewModel.bind('{s}', function(s) { console.log('s=' + s); }); + * + * binding.setValue('abc'); + * + * Direct use of `ViewModel` in this way is not commonly needed because `Ext.Component` + * automates this process. For example, a `textfield` component understands when it is + * given a "two-way" binding and automatically synchronizes its value bidirectionally using + * the above technique. For example: + * + * Ext.widget({ + * items: [{ + * xtype: 'textfield', + * bind: '{s}' // a two-way / direct bind descriptor + * }] + * }); + * + * ### Object and Array Descriptors / Multi-Bind + * + * With two exceptions (see below) an Object is interpreted as a "shape" to produce by + * treating each of its properties as individual bind descriptors. An object of the same + * shape is passed as the value of the bind except that each property is populated with + * the appropriate value. Of course, this definition is recursive, so these properties + * may also be objects. + * + * For example: + * + * viewModel.bind({ + * x: '{x}', + * foo: { + * bar: 'Hello {foo.bar}' + * } + * }, + * function (obj) { + * // obj = { + * // x: 42, + * // foo: { + * // bar: 'Hello foobar' + * // } + * // } + * }); + * + * Arrays are handled in the same way. Each element of the array is considered a bind + * descriptor (recursively) and the value produced for the binding is an array with each + * element set to the bound property. + * + * ### Bind Options + * + * One exception to the "object is a multi-bind" rule is when that object contains a + * `bindTo` property. When an object contains a `bindTo` property the object is understood + * to contain bind options and the value of `bindTo` is considered the actual bind + * descriptor. + * + * For example: + * + * viewModel.bind({ + * bindTo: '{x}', + * single: true + * }, + * function (x) { + * console.log('x: ' + x); // only called once + * }); + * + * The available bind options depend on the type of binding, but since all bindings + * derive from `{@link Ext.app.bind.BaseBinding}` its options are always applicable. + * For a list of the other types of bindings, see above. + * + * #### Deep Binding + * + * When a direct bind is made and the bound property is an object, by default the binding + * callback is only called when that reference changes. This is the most efficient way to + * understand a bind of this type, but sometimes you may need to be notified if any of the + * properties of that object change. + * + * To do this, we create a "deep bind": + * + * viewModel.bind({ + * bindTo: '{someObject}', + * deep: true + * }, + * function (someObject) { + * // called when reference changes or *any* property changes + * }); + * + * #### Binding Timings + * + * The `ViewModel` has a {@link #scheduler} attached that is used to coordinate the firing of bindings. + * It serves 2 main purposes: + * - To coordinate dependencies between bindings. This means bindings will be fired in an order such that + * the any dependencies for a binding are fired before the binding itself. + * - To batch binding firings. The scheduler runs on a short timer, so the following code will only trigger + * a single binding (the last), the changes in between will never be triggered. + * + * Example: + * + * viewModel.bind('{val}', function(v) { + * console.log(v); + * }); + * viewModel.set('val', 1); + * viewModel.set('val', 2); + * viewModel.set('val', 3); + * viewModel.set('val', 4); + * + * The `ViewModel` can be forced to process by calling `{@link #notify}`, which will force the + * scheduler to run immediately in the current state. + * + * viewModel.bind('{val}', function(v) { + * console.log(v); + * }); + * viewModel.set('val', 1); + * viewModel.notify(); + * viewModel.set('val', 2); + * viewModel.notify(); + * viewModel.set('val', 3); + * viewModel.notify(); + * viewModel.set('val', 4); + * viewModel.notify(); + * + * + * #### Models, Stores and Associations + * + * A {@link Ext.data.Session Session} manages model instances and their associations. + * The `ViewModel` may be used with or without a `Session`. When a `Session` is attached, the + * `ViewModel` will always consult the `Session` to ask about records and stores. The `Session` + * ensures that only a single instance of each model Type/Id combination is created. This is + * important when tracking changes in models so that we always have the same reference. + * + * A `ViewModel` provides functionality to easily consume the built in data package types + * {@link Ext.data.Model} and {@link Ext.data.Store}, as well as their associations. + * + * ### Model Links + * + * A model can be described declaratively using {@link #links}. In the example code below, + * We ask the `ViewModel` to construct a record of type `User` with `id: 17`. The model will be loaded + * from the server and the bindings will trigger once the load has completed. Similarly, we could also + * attach a model instance to the `ViewModel` data directly. + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: ['name'] + * }); + * + * var rec = new MyApp.model.User({ + * id: 12, + * name: 'Foo' + * }); + * + * var viewModel = new Ext.app.ViewModel({ + * links: { + * theUser: { + * type: 'User', + * id: 17 + * } + * }, + * data: { + * otherUser: rec + * } + * }); + * viewModel.bind('{theUser.name}', function(v) { + * console.log(v); + * }); + * viewModel.bind('{otherUser.name}', function(v) { + * console.log(v); + * }); + * + * ### Model Fields + * + * Bindings have the functionality to inspect the parent values and resolve the underlying + * value dynamically. This behavior allows model fields to be interrogated as part of a binding. + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: ['name', 'age'] + * }); + * + * var viewModel = new Ext.app.ViewModel({ + * links: { + * theUser: { + * type: 'User', + * id: 22 + * } + * } + * }); + * + * // Server responds with: + * { + * "id": 22, + * "name": "Foo", + * "age": 100 + * } + * + * viewModel.bind('Hello {name}, you are {age} years old', function(v) { + * console.log(v); + * }); + * + * ### Record Properties + * + * It is possible to bind to the certain state properties of a record. The available options are: + * - `{@link Ext.data.Model#property-dirty dirty}` + * - `{@link Ext.data.Model#property-phantom phantom}` + * - `{@link Ext.data.Model#method-isValid valid}` + * + * Example usage: + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: [{ + * name: 'name', + * validators: 'presence' + * }, { + * name: 'age', + * validators: { + * type: 'range', + * min: 0 + * } + * }] + * }); + * + * var rec = new MyApp.model.User(); + * + * var viewModel = new Ext.app.ViewModel({ + * data: { + * theUser: rec + * } + * }); + * + * viewModel.bind({ + * dirty: '{theUser.dirty}', + * phantom: '{theUser.phantom}', + * valid: '{theUser.valid}' + * }, function(v) { + * console.log(v.dirty, v.valid); + * }); + * + * rec.set('name', 'Foo'); + * viewModel.notify(); // dirty, not valid + * rec.set('age', 20); + * viewModel.notify(); // dirty, valid + * rec.reject(); + * viewModel.notify(); // not dirty, not valid + * + * ### Advanced Record Binding + * + * For accessing other record information that is not exposed by the binding API, formulas + * can be used to achieve more advanced operations: + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: ['name', 'age'] + * }); + * + * var rec = new MyApp.model.User(); + * + * var viewModel = new Ext.app.ViewModel({ + * formulas: { + * isNameModified: { + * bind: { + * bindTo: '{theUser}', + * deep: true + * }, + * get: function(rec) { + * return rec.isModified('name'); + * } + * } + * }, + * data: { + * theUser: rec + * } + * }); + * + * viewModel.bind('{isNameModified}', function(modified) { + * console.log(modified); + * }); + * rec.set('name', 'Foo'); + * + * ### Associations + * + * In the same way as fields, the bindings can also traverse associations in a bind statement. + * The `ViewModel` will handle the asynchronous loading of data and only present the value once + * the full path has been loaded. For more information on associations see {@link Ext.data.schema.OneToOne OneToOne} and + * {@link Ext.data.schema.ManyToOne ManyToOne} associations. + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: ['name'] + * }); + * + * Ext.define('Order', { + * extend: 'Ext.data.Model', + * fields: ['date', { + * name: 'userId', + * reference: 'User' + * }] + * }); + * + * Ext.define('OrderItem', { + * extend: 'Ext.data.Model', + * fields: ['price', 'qty', { + * name: 'orderId', + * reference: 'Order' + * }] + * }); + * + * var viewModel = new Ext.app.ViewModel({ + * links: { + * orderItem: { + * type: 'OrderItem', + * id: 13 + * } + * } + * }); + * // The viewmodel will handle both ways of loading the data: + * // a) If the data is loaded inline in a nested fashion it will + * // not make requests for extra data + * // b) Only loading a single model at a time. So the Order will be loaded once + * // the OrderItem returns. The User will be loaded once the Order loads. + * viewModel.bind('{orderItem.order.user.name}', function(name) { + * console.log(name); + * }); + * + * ### Stores + * + * Stores can be created as part of the `ViewModel` definition. The definitions are processed + * like bindings which allows for very powerful dynamic functionality. + * + * It is important to ensure that you name viewModel's data keys uniquely. If data is not named + * uniquely, binds and formulas may receive information from an unintended data source. + * This applies to keys in the viewModel's data block, stores, and links configs. + * + * var viewModel = new Ext.app.ViewModel({ + * stores: { + * users: { + * model: 'User', + * autoLoad: true, + * filters: [{ + * property: 'createdDate', + * value: '{createdFilter}', + * operator: '>' + * }] + * } + * } + * }); + * // Later on in our code, we set the date so that the store is created. + * viewModel.set('createdFilter', Ext.Date.subtract(new Date(), Ext.Date.DAY, 7)); + * + * See {@link #stores} for more detail. + * + * ### Store Properties + * + * It is possible to bind to the certain state properties of the store. The available options are: + * - `{@link Ext.data.Store#method-getCount count}` + * - `{@link Ext.data.Store#method-first}` + * - `{@link Ext.data.Store#method-last}` + * - `{@link Ext.data.Store#method-hasPendingLoad loading}` + * - `{@link Ext.data.Store#method-getTotalCount totalCount}` + * + * Example: + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: ['name'] + * }); + * + * var viewModel = new Ext.app.ViewModel({ + * stores: { + * users: { + * model: 'MyApp.model.User', + * data: [{ + * name: 'Foo' + * }, { + * name: 'Bar' + * }] + * } + * } + * }); + * + * viewModel.bind('{users.first}', function(first) { + * console.log(first ? first.get('name') : 'Nobody'); + * }); + * + * var timer = Ext.interval(function() { + * var store = viewModel.getStore('users'); + * if (store.getCount()) { + * store.removeAt(0); + * } else { + * Ext.uninterval(timer); + * } + * }, 100); + * + * ### Advanced Store Binding + * + * For accessing other store information that is not exposed by the binding API, formulas + * can be used to achieve more advanced operations: + * + * Ext.define('MyApp.model.User', { + * extend: 'Ext.data.Model', + * fields: ['name', 'score'] + * }); + * + * var viewModel = new Ext.app.ViewModel({ + * stores: { + * users: { + * model: 'MyApp.model.User', + * data: [{ + * name: 'Foo', + * score: 100 + * }, { + * name: 'Bar', + * score: 350 + * }] + * } + * }, + * formulas: { + * totalScore: { + * bind: { + * bindTo: '{users}', + * deep: true + * }, + * get: function(store) { + * return store.sum('score'); + * } + * } + * } + * }); + * + * viewModel.bind('{totalScore}', function(score) { + * console.log(score); + * }); + * + * viewModel.notify(); + * viewModel.getStore('users').removeAll(); + * + * #### Formulas + * + * Formulas allow for calculated `ViewModel` data values. The dependencies for these formulas + * are automatically determined so that the formula will not be processed until the required + * data is present. + * + * var viewModel = new Ext.app.ViewModel({ + * formulas: { + * fullName: function(get) { + * return get('firstName') + ' ' + get('lastName'); + * } + * }, + * data: {firstName: 'John', lastName: 'Smith'} + * }); + * + * viewModel.bind('{fullName}', function(v) { + * console.log(v); + * }); + * + * See {@link #formulas} for more detail. + * + * #### Inheriting Data With Nesting + * + * ViewModels can have a {@link #parent} which allows values to be consumed from + * a shared base. These values that are available from the {@link #parent} are not copied, + * rather they are "inherited" in a similar fashion to a javascript closure scope chain. + * This is demonstrated in the example below: + * + * var parent = new Ext.app.ViewModel({ + * data: { + * foo: 3 + * } + * }); + * var child = new Ext.app.ViewModel({ + * parent: parent + * }); + * + * This is analogous to the following javascript closure: + * + * var foo = 3; + * Ext.Ajax.request({ + * success: function() { + * // foo is available here + * } + * }); + * + * ### Climbing/Inheriting + * + * In line with the above, the default behaviour when setting the value of a child ViewModel (either) + * through {@link #set} or {@link Ext.app.bind.Binding#method-setValue} is to climb to where the value + * is "owned" and set the value there: + * + * var parent = new Ext.app.ViewModel({ + * data: { + * foo: 3 + * } + * }); + * var child = new Ext.app.ViewModel({ + * parent: parent + * }); + * + * child.set('foo', 100); // Climbs to set the value on parent + * console.log(parent.get('foo')); // 100 + * parent.set('foo', 200); + * console.log(child.get('foo')); // 200, inherited from the parent + * + * Any subsequent sets are also inherited in the same fashion. The inheriting/climbing behavior + * occurs for any arbitrary depth, climbing/inherting can owned by a parent at any level above. + * + * function log() { + * console.log([a, b, c, d, e].map(function(vm) { + * return vm.get('foo'); + * })); + * } + * + * var a = new Ext.app.ViewModel({data: {foo: 3}}), + * b = new Ext.app.ViewModel({parent: a}), + * c = new Ext.app.ViewModel({parent: b}), + * d = new Ext.app.ViewModel({parent: c}), + * e = new Ext.app.ViewModel({parent: d}); + * + * log(); // [3, 3, 3, 3, 3] + * + * e.set('foo', 100); + * log(); // [100, 100, 100, 100, 100] + * + * This same climbing behavior applies when setting a value on a binding. The climbing begins from + * the ViewModel where the binding was attached: + * + * function log() { + * console.log([a, b, c].map(function(vm) { + * return vm.get('foo'); + * })); + * } + * + * var a = new Ext.app.ViewModel({data: {foo: 3}}), + * b = new Ext.app.ViewModel({parent: a}), + * c = new Ext.app.ViewModel({parent: b}); + * + * var bind = c.bind('{foo}', function() {}); + * + * bind.setValue(100); + * log(); // [100, 100, 100] + * + * The exception to this rule is when there is nothing above to climb to. If a value is set and there + * is no parent above to hold it, then the value is set where it was called: + * + * function log() { + * console.log([a, b, c].map(function(vm) { + * return vm.get('foo'); + * })); + * } + * + * var a = new Ext.app.ViewModel(), + * b = new Ext.app.ViewModel({parent: a}), + * c = new Ext.app.ViewModel({parent: b}); + * + * c.set('foo', 3); + * log(); // [null, null, 3] + * + * b.set('foo', 2); + * log(); // [null, 2, 3] + * + * a.set('foo', 1); + * log(); // [1, 2, 3] + * + * These values are called local values, which are discussed below. + * + * ### Local Values + * + * If the child ViewModel is declared with top level data that also exists in the parent, then that child is + * considered to own that local value, so no value is inherited from the parent, nor does the climbing + * behaviour occur. + * + * var parent = new Ext.app.ViewModel({ + * data: { + * foo: 3 + * } + * }); + * var child = new Ext.app.ViewModel({ + * parent: parent, + * data: { + * foo: 5 + * } + * }); + * + * console.log(parent.get('foo'), child.get('foo')); // 3, 5 + * child.set('foo', 100); + * console.log(parent.get('foo'), child.get('foo')); // 3, 100 + * parent.set('foo', 200); + * console.log(parent.get('foo'), child.get('foo')); // 200, 100 + * + * The inheriting/climbing behavior is limited to local values: + * + * function log() { + * console.log([a, b, c, d, e].map(function(vm) { + * return vm.get('foo'); + * })); + * } + * + * var a = new Ext.app.ViewModel({data: {foo: 1}}), + * b = new Ext.app.ViewModel({parent: a}), + * c = new Ext.app.ViewModel({parent: b, data: {foo: 2}}), + * d = new Ext.app.ViewModel({parent: c}), + * e = new Ext.app.ViewModel({parent: d, data: {foo: 3}}); + * + * log(); // [1, 1, 2, 2, 3] + * + * e.set('foo', 100); + * log(); // [1, 1, 2, 2, 100] + * + * d.set('foo', 200); + * log(); // [1, 1, 200, 200, 100] + * + * c.set('foo', 201); + * log(); // [1, 1, 201, 201, 100] + * + * b.set('foo', 300); + * log(); // [300, 300, 201, 201, 100] + * + * a.set('foo', 301); + * log(); // [301, 301, 201, 201, 100] + * + * ### Attaching/Clearing Local Values Dynamically + * + * To bypass the climbing behaviour and push a value into a particular point + * in the hierarchy, the {@link #setData} method should be used. Once a local value + * is set, it will be used as such in the future. + * + * function log() { + * console.log([a, b, c, d, e].map(function(vm) { + * return vm.get('foo'); + * })); + * } + * + * var a = new Ext.app.ViewModel({data: {foo: 3}}), + * b = new Ext.app.ViewModel({parent: a}), + * c = new Ext.app.ViewModel({parent: b}), + * d = new Ext.app.ViewModel({parent: c}), + * e = new Ext.app.ViewModel({parent: d}); + * + * log(); // [3, 3, 3, 3, 3] + * + * c.setData({ + * foo: 100 + * }); + * + * log(); // [3, 3, 100, 100, 100] + * + * d.set('foo', 200); // Climbs to new local value + * log(); // [3, 3, 200, 200, 200] + * + * Similarly, data can be cleared from being a local value by setting the value to undefined: + * + * function log() { + * console.log([a, b, c, d].map(function(vm) { + * return vm.get('foo'); + * })); + * } + * + * var a = new Ext.app.ViewModel({data: {foo: 3}}), + * b = new Ext.app.ViewModel({parent: a}), + * c = new Ext.app.ViewModel({parent: b, data: {foo: 100}}), + * d = new Ext.app.ViewModel({parent: c}); + * + * log(); // [3, 3, 100, 100] + * + * c.setData({ + * foo: undefined + * }); + * log([3, 3, 3, 3]); + * + */ +Ext.define('Ext.app.ViewModel', { + mixins: [ + 'Ext.mixin.Factoryable', + 'Ext.mixin.Identifiable' + ], + requires: [ + 'Ext.util.Scheduler', + 'Ext.data.Session', + 'Ext.app.bind.RootStub', + 'Ext.app.bind.LinkStub', + 'Ext.app.bind.Multi', + 'Ext.app.bind.Formula', + 'Ext.app.bind.TemplateBinding', + // TODO: this is an injected dependency in onStoreBind, need to define so + // cmd can detect it + 'Ext.data.ChainedStore' + ], + alias: 'viewmodel.default', + // also configures Factoryable + isViewModel: true, + factoryConfig: { + name: 'viewModel' + }, + collectTimeout: 100, + expressionRe: /^(?:\{(?:(\d+)|([a-z_][\w\.]*))\})$/i, + statics: { + /** + * Escape bind strings so they are treated as literals. + * + * @param {Object/String} value The value to escape. If the value is + * an object, any strings will be recursively escaped. + * @return {Object/String} The escaped value. Matches the type of the + * passed value. + * + * @since 6.5.2 + * @private + */ + escape: function(value) { + var ret = value, + key; + if (typeof value === 'string') { + ret = '~~' + value; + } else if (value && value.constructor === Object) { + ret = {}; + for (key in value) { + ret[key] = this.escape(value[key]); + } + } + return ret; + } + }, + $configStrict: false, + // allow "formulas" to be specified on derived class body + config: { + /** + * @cfg {Object} data + * This object holds the arbitrary data that populates the `ViewModel` and is + * then available for binding. + * @since 5.0.0 + */ + data: true, + /** + * @cfg {Object} formulas + * An object that defines named values whose value is managed by function calls. + * The names of the properties of this object are assigned as values in the + * ViewModel. + * + * For example: + * + * formulas: { + * xy: function (get) { return get('x') * get('y'); } + * } + * + * For more details about defining a formula, see `{@link Ext.app.bind.Formula}`. + * @since 5.0.0 + */ + formulas: { + $value: null, + merge: function(newValue, currentValue, target, mixinClass) { + return this.mergeNew(newValue, currentValue, target, mixinClass); + } + }, + /** + * @cfg {Object} links + * Links provide a way to assign a simple name to a more complex bind. The primary + * use for this is to assign names to records in the data model. + * + * links: { + * theUser: { + * type: 'User', + * id: 12 + * } + * } + * + * It is also possible to force a new phantom record to be created by not specifying an + * id but passing `create: true` as part of the descriptor. This is often useful when + * creating a new record for a child session. + * + * links: { + * newUser: { + * type: 'User', + * create: true + * } + * } + * + * `create` can also be an object containing initial data for the record. + * + * links: { + * newUser: { + * type: 'User', + * create: { + * firstName: 'John', + * lastName: 'Smith' + * } + * } + * } + * + * While that is the typical use, the value of each property in `links` may also be + * a bind descriptor (see `{@link #method-bind}` for the various forms of bind + * descriptors). + * @since 5.0.0 + */ + links: null, + /** + * @cfg {Ext.app.ViewModel} parent + * The parent `ViewModel` of this `ViewModel`. Once set, this cannot be changed. + * @readonly + * @since 5.0.0 + */ + parent: null, + /** + * @cfg {Ext.app.bind.RootStub} root + * A reference to the root "stub" (an object that manages bindings). + * @private + * @since 5.0.0 + */ + root: true, + /** + * @cfg {Ext.util.Scheduler} scheduler + * The scheduler used to schedule and manage the delivery of notifications for + * all connections to this `ViewModel` and any other attached to it. The normal + * process to initialize the `scheduler` is to get the scheduler used by the + * `parent` or `session` and failing either of those, create one. + * @readonly + * @private + * @since 5.0.0 + */ + scheduler: null, + /** + * @cfg {String/Ext.data.schema.Schema} schema + * The schema to use for getting information about entities. + */ + schema: 'default', + /** + * @cfg {Ext.data.Session} session + * The session used to manage the data model (records and stores). + * @since 5.0.0 + */ + session: null, + // @cmd-auto-dependency {isKeyedObject: true, aliasPrefix: "store.", defaultType: "store"} + /** + * @cfg {Object} stores + * A declaration of `Ext.data.Store` configurations that are first processed as + * binds to produce an effective store configuration. + * + * A simple store definition. We can reference this in our bind statements using the + * `{users}` as we would with other data values. + * + * new Ext.app.ViewModel({ + * stores: { + * users: { + * model: 'User', + * autoLoad: true + * } + * } + * }); + * + * This store definition contains a dynamic binding. The store will not be created until + * the initial value for groupId is set. Once that occurs, the store is created with the appropriate + * filter configuration. Subsequently, once we change the group value, the old filter will be + * overwritten with the new value. + * + * var viewModel = new Ext.app.ViewModel({ + * stores: { + * users: { + * model: 'User', + * filters: [{ + * property: 'groupId', + * value: '{groupId}' + * }] + * } + * } + * }); + * viewModel.set('groupId', 1); // This will trigger the store creation with the filter. + * viewModel.set('groupId', 2); // The filter value will be changed. + * + * This store uses {@link Ext.data.ChainedStore store chaining} to create a store backed by the + * data in another store. By specifying a string as the store, it will bind our creation and backing + * to the other store. This functionality is especially useful when wanting to display a different "view" + * of a store, for example a different sort order or different filters. + * + * var viewModel = new Ext.app.ViewModel({ + * stores: { + * allUsers: { + * model: 'User', + * autoLoad: true + * }, + * children: { + * source: '{allUsers}', + * filters: [{ + * property: 'age', + * value: 18, + * operator: '<' + * }] + * } + * } + * }); + * + * @since 5.0.0 + */ + stores: null, + /** + * @cfg {Ext.container.Container} view + * The Container that owns this `ViewModel` instance. + * @since 5.0.0 + */ + view: null + }, + constructor: function(config) { + // Used to track non-stub bindings + this.bindings = {}; + /* + * me.data = { + * foo: { + * }, + * + * selectedUser: { + * name: null + * }, + * } + * + * me.root = new Ext.app.bind.RootStub({ + * children: { + * foo: new Ext.app.bind.Stub(), + * selectedUser: new Ext.app.bind.LinkStub({ + * binding: session.bind(...), + * children: { + * name: : new Ext.app.bind.Stub() + * } + * }), + * } + * }) + */ + this.initConfig(config); + }, + destroy: function() { + var me = this, + scheduler = me._scheduler, + stores = me.storeInfo, + parent = me.getParent(), + task = me.collectTask, + children = me.children, + bindings = me.bindings, + key, store, autoDestroy, storeBinding; + me.destroying = true; + if (task) { + task.cancel(); + me.collectTask = null; + } + // When used with components, they are destroyed bottom up + // so this scenario is only likely to happen in the case where + // we're using the VM without any component attachment, in which case + // we need to clean up here. + if (children) { + for (key in children) { + children[key].destroy(); + } + } + if (stores) { + for (key in stores) { + store = stores[key]; + // Cache this property in case store is destroyed; + // Properties are cleared on destroy + storeBinding = store.$binding; + autoDestroy = store.autoDestroy; + if (autoDestroy || (!store.$wasInstance && autoDestroy !== false)) { + store.destroy(); + } + Ext.destroy(storeBinding); + } + } + if (parent) { + parent.unregisterChild(me); + } + me.getRoot().destroy(); + for (key in bindings) { + bindings[key].destroy(); + } + if (scheduler && scheduler.$owner === me) { + scheduler.$owner = null; + scheduler.destroy(); + } + me.children = me.storeInfo = me._session = me._view = me._scheduler = me.bindings = me._root = me._parent = me.formulaFn = me.$formulaData = null; + me.destroying = false; + me.callParent(); + }, + /** + * This method requests that data in this `ViewModel` be delivered to the specified + * `callback`. The data desired is given in a "bind descriptor" which is the first + * argument. + * + * A simple call might look like this: + * + * var binding = vm.bind('{foo}', this.onFoo, this); + * + * binding.destroy(); // when done with the binding + * + * Options for the binding can be provided in the last argument: + * + * var binding = vm.bind('{foo}', this.onFoo, this, { + * deep: true + * }); + * + * Alternatively, bind options can be combined with the bind descriptor using only + * the first argument: + * + * var binding = vm.bind({ + * bindTo: '{foo}', // the presence of bindTo identifies this form + * deep: true + * }, this.onFoo, this); + * + * See the class documentation for more details on Bind Descriptors and options. + * + * @param {String/Object/Array} descriptor The bind descriptor. See class description + * for details. + * @param {Function} callback The function to call with the value of the bound property. + * @param {Object} [scope] The scope (`this` pointer) for the `callback`. + * @param {Object} [options] Additional options to configure the {@link Ext.app.bind.Binding binding}. + * If this parameter is provided, the `bindTo` form of combining options and bind descriptor is not + * recognized. + * @return {Ext.app.bind.BaseBinding/Ext.app.bind.Binding} The binding. + */ + bind: function(descriptor, callback, scope, options) { + var me = this, + track = true, + binding; + scope = scope || me; + if (!options && descriptor.bindTo !== undefined && !Ext.isString(descriptor)) { + options = descriptor; + descriptor = options.bindTo; + } + if (!Ext.isString(descriptor)) { + binding = new Ext.app.bind.Multi(descriptor, me, callback, scope, options); + } else if (me.expressionRe.test(descriptor)) { + // If we have '{foo}' alone it is a literal + descriptor = descriptor.substring(1, descriptor.length - 1); + binding = me.bindExpression(descriptor, callback, scope, options); + track = false; + } else { + binding = new Ext.app.bind.TemplateBinding(descriptor, me, callback, scope, options); + } + if (track) { + me.bindings[binding.id] = binding; + } + return binding; + }, + /** + * Gets the session attached to this (or a parent) ViewModel. See the {@link #session} configuration. + * @return {Ext.data.Session} The session. `null` if no session exists. + */ + getSession: function() { + var me = this, + session = me._session, + parent; + if (!session && (parent = me.getParent())) { + me.setSession(session = parent.getSession()); + } + return session || null; + }, + /** + * Gets a store configured via the {@link #stores} configuration. + * @param {String} key The name of the store. + * @return {Ext.data.Store} The store. `null` if no store exists. + */ + getStore: function(key) { + var storeInfo = this.storeInfo, + store; + if (storeInfo) { + store = storeInfo[key]; + } + return store || null; + }, + /** + * @method getStores + * @hide + */ + /** + * Create a link to a reference. See the {@link #links} configuration. + * @param {String} key The name for the link. + * @param {Object} reference The reference descriptor. + */ + linkTo: function(key, reference) { + var me = this, + stub, create, id, modelType, linkStub, rec; + if (key.indexOf('.') > -1) { + Ext.raise('Links can only be at the top-level: "' + key + '"'); + } + if (reference.isModel) { + reference = { + type: reference.entityName, + id: reference.id + }; + } + // reference is backwards compat, type is preferred. + modelType = reference.type || reference.reference; + create = reference.create; + if (modelType) { + // It's a record + id = reference.id; + if (!reference.create && Ext.isEmpty(id)) { + Ext.raise('No id specified. To create a phantom model, specify "create: true" as part of the reference.'); + } + if (create) { + id = undefined; + } + rec = me.getRecord(modelType, id); + if (Ext.isObject(create)) { + rec.set(create); + rec.commit(); + rec.phantom = true; + } + // Force creation at the root level. If an existing stub is there + // it will be grafted in place here. + stub = me.getRoot().createStubChild(key); + stub.set(rec); + } else { + stub = me.getStub(key); + if (!stub.isLinkStub) { + // Pass parent=null since we will graft in this new stub to replace us: + linkStub = new Ext.app.bind.LinkStub(me, stub.name); + stub.graft(linkStub); + stub = linkStub; + } + stub.link(reference); + } + }, + /** + * Forces all bindings in this ViewModel hierarchy to evaluate immediately. Use this to do a synchronous flush + * of all bindings. + */ + notify: function() { + var scheduler = this.getScheduler(); + if (!scheduler.firing) { + scheduler.notify(); + } + }, + /** + * Get a value from the data for this viewmodel. + * @param {String} path The path of the data to retrieve. + * + * var value = vm.get('theUser.address.city'); + * + * @return {Object} The data stored at the passed path. + */ + get: function(path) { + return this.getStub(path).getValue(); + }, + /** + * Set a value in the data for this viewmodel. This method will climb to set data on + * a parent view model if appropriate. See "Inheriting Data" in the class introduction for + * more information. + * + * @param {Object/String} path The path of the value to set, or an object literal to set + * at the root of the viewmodel. + * @param {Object} value The data to set at the value. If the value is an object literal, + * any required paths will be created. + * + * // Set a single property at the root level + * viewModel.set('expiry', Ext.Date.add(new Date(), Ext.Date.DAY, 7)); + * console.log(viewModel.get('expiry')); + * // Sets a single property in user.address, does not overwrite any hierarchy. + * viewModel.set('user.address.city', 'London'); + * console.log(viewModel.get('user.address.city')); + * // Sets 2 properties of "user". Overwrites any existing hierarchy. + * viewModel.set('user', {firstName: 'Foo', lastName: 'Bar'}); + * console.log(viewModel.get('user.firstName')); + * // Sets a single property at the root level. Overwrites any existing hierarchy. + * viewModel.set({rootKey: 1}); + * console.log(viewModel.get('rootKey')); + */ + set: function(path, value) { + var me = this, + obj, stub; + // Force data creation + me.getData(); + if (value === undefined && path && path.constructor === Object) { + stub = me.getRoot(); + value = path; + } else if (path && path.indexOf('.') < 0) { + obj = {}; + obj[path] = value; + value = obj; + stub = me.getRoot(); + } else { + stub = me.getStub(path); + } + stub.set(value); + }, + /** + * Sets data directly at the level of this viewmodel. This method does not climb + * to set data on parent view models. Passing `undefined` will clear the value + * in this viewmodel, which means that this viewmodel is free to inherit data + * from a parent. See "Inheriting Data" in the class introduction for more information. + * @param {Object} data The new data to set. + * @method setData + */ + //========================================================================= + privates: { + registerChild: function(child) { + var children = this.children; + if (!children) { + this.children = children = {}; + } + children[child.getId()] = child; + }, + unregisterChild: function(child) { + var children = this.children; + // If we're destroying we'll be wiping this collection shortly, so + // just ignore it here + if (!this.destroying && children) { + delete children[child.getId()]; + } + }, + /** + * Get a record instance given a reference descriptor. Will ask + * the session if one exists. + * @param {String/Ext.Class} type The model type. + * @param {Object} id The model id. + * @return {Ext.data.Model} The model instance. + * @private + */ + getRecord: function(type, id) { + var session = this.getSession(), + Model = type, + hasId = id !== undefined, + record; + if (session) { + if (hasId) { + record = session.getRecord(type, id); + } else { + record = session.createRecord(type); + } + } else { + if (!Model.$isClass) { + Model = this.getSchema().getEntity(Model); + if (!Model) { + Ext.raise('Invalid model name: ' + type); + } + } + if (hasId) { + record = Model.createWithId(id); + record.load(); + } else { + record = new Model(); + } + } + return record; + }, + bindExpression: function(descriptor, callback, scope, options) { + var stub = this.getStub(descriptor); + return stub.bind(callback, scope, options); + }, + applyScheduler: function(scheduler) { + if (scheduler && !scheduler.isInstance) { + if (scheduler === true) { + scheduler = {}; + } + if (!('preSort' in scheduler)) { + scheduler = Ext.apply({ + preSort: 'kind,-depth' + }, scheduler); + } + scheduler = new Ext.util.Scheduler(scheduler); + scheduler.$owner = this; + } + return scheduler; + }, + getScheduler: function() { + var me = this, + scheduler = me._scheduler, + parent; + if (!scheduler) { + if (!(parent = me.getParent())) { + scheduler = new Ext.util.Scheduler({ + // See Session#scheduler + preSort: 'kind,-depth' + }); + scheduler.$owner = me; + } else { + scheduler = parent.getScheduler(); + } + me.setScheduler(scheduler); + } + return scheduler; + }, + /** + * This method looks up the `Stub` for a single bind descriptor. + * @param {String/Object} bindDescr The bind descriptor. + * @return {Ext.app.bind.AbstractStub} The `Stub` associated to the bind descriptor. + * @private + */ + getStub: function(bindDescr) { + var root = this.getRoot(); + return bindDescr ? root.getChild(bindDescr) : root; + }, + collect: function() { + var me = this, + parent = me.getParent(), + task = me.collectTask; + if (parent) { + parent.collect(); + return; + } + if (!task) { + task = me.collectTask = new Ext.util.DelayedTask(me.doCollect, me); + } + // Useful for testing + if (me.collectTimeout === 0) { + me.doCollect(); + } else { + task.delay(me.collectTimeout); + } + }, + doCollect: function() { + var children = this.children, + key; + // We need to loop over the children first, since they may have link stubs + // that create bindings inside our VM. Attempt to clean them up first. + if (children) { + for (key in children) { + children[key].doCollect(); + } + } + this.getRoot().collect(); + }, + invalidateChildLinks: function(name, clear) { + var children = this.children, + key; + if (children) { + for (key in children) { + children[key].getRoot().invalidateChildLink(name, clear); + } + } + }, + onBindDestroy: function(binding, fromChild) { + var me = this, + parent; + if (me.destroying) { + return; + } + if (!fromChild) { + delete me.bindings[binding.id]; + } + parent = me.getParent(); + if (parent) { + parent.onBindDestroy(binding, true); + } else { + me.collect(); + } + }, + //------------------------------------------------------------------------- + // Config + // + applyData: function(newData, data) { + var me = this, + linkData, parent; + // Force any session to be invoked so we can access it + me.getSession(); + if (!data) { + parent = me.getParent(); + /** + * @property {Object} linkData + * This object is used to hold the result of a linked value. This is done + * so that the data object hasOwnProperty equates to whether or not this + * property is owned by this instance or inherited. + * @private + * @readonly + * @since 5.0.0 + */ + me.linkData = linkData = parent ? Ext.Object.chain(parent.getData()) : {}; + /** + * @property {Object} data + * This object holds all of the properties of this `ViewModel`. It is + * prototype chained to the `linkData` which is, in turn, prototype chained + * to (if present) the `data` object of the parent `ViewModel`. + * @private + * @readonly + * @since 5.0.0 + */ + me.data = me._data = Ext.Object.chain(linkData); + } + if (newData && newData.constructor === Object) { + me.getRoot().set(newData, true); + } + }, + applyParent: function(parent) { + if (parent) { + parent.registerChild(this); + } + return parent; + }, + applyStores: function(stores) { + var me = this, + root = me.getRoot(), + key, cfg, storeBind, stub, listeners; + me.storeInfo = {}; + me.listenerScopeFn = function() { + return me.getView().getInheritedConfig('defaultListenerScope'); + }; + for (key in stores) { + cfg = stores[key]; + if (cfg.isStore) { + cfg.$wasInstance = true; + me.setupStore(cfg, key); + + continue; + } else if (Ext.isString(cfg)) { + cfg = { + source: cfg + }; + } else { + cfg = Ext.apply({}, cfg); + } + // Get rid of listeners so they don't get considered as a bind + listeners = cfg.listeners; + delete cfg.listeners; + storeBind = me.bind(cfg, me.onStoreBind, me, { + trackStatics: true + }); + if (storeBind.isStatic()) { + // Everything is static, we don't need to wait, so remove the + // binding because it will only fire the first time. + storeBind.destroy(); + me.createStore(key, cfg, listeners); + } else { + storeBind.$storeKey = key; + storeBind.$listeners = listeners; + stub = root.createStubChild(key); + stub.setStore(storeBind); + } + } + }, + onStoreBind: function(cfg, oldValue, binding) { + var info = this.storeInfo, + key = binding.$storeKey, + store = info[key], + proxy; + if (!store) { + this.createStore(key, cfg, binding.$listeners, binding); + } else { + cfg = Ext.merge({}, binding.pruneStaticKeys()); + proxy = cfg.proxy; + delete cfg.type; + delete cfg.model; + delete cfg.fields; + delete cfg.proxy; + delete cfg.listeners; + // TODO: possibly optimize this so we can figure out what has changed + // instead of smashing the whole lot + if (proxy) { + delete proxy.reader; + delete proxy.writer; + store.getProxy().setConfig(proxy); + } + store.setConfig(cfg); + } + }, + createStore: function(key, cfg, listeners, binding) { + var session = this.getSession(), + store; + cfg = Ext.apply({}, cfg); + if (cfg.session) { + cfg.session = session; + } + if (cfg.source) { + cfg.type = cfg.type || 'chained'; + } + // Restore the listeners from applyStores here + cfg.listeners = listeners; + // Ensure events fired by ctor can find their target: + cfg.resolveListenerScope = this.listenerScopeFn; + store = Ext.Factory.store(cfg); + store.$binding = binding; + this.setupStore(store, key); + }, + setupStore: function(store, key) { + // May have been given a store instance + store.resolveListenerScope = this.listenerScopeFn; + this.storeInfo[key] = store; + this.set(key, store); + }, + applyFormulas: function(formulas) { + var me = this, + root = me.getRoot(), + name, stub; + me.getData(); + // make sure our data is setup first + for (name in formulas) { + if (name.indexOf('.') >= 0) { + Ext.raise('Formula names cannot contain dots: ' + name); + } + // Force a stub to be created + root.createStubChild(name); + stub = me.getStub(name); + stub.setFormula(formulas[name]); + } + return formulas; + }, + applyLinks: function(links) { + for (var link in links) { + this.linkTo(link, links[link]); + } + }, + applySchema: function(schema) { + return Ext.data.schema.Schema.get(schema); + }, + applyRoot: function() { + var root = new Ext.app.bind.RootStub(this), + parent = this.getParent(); + if (parent) { + // We are assigning the root of a child VM such that its bindings will be + // pre-sorted after the bindings of the parent VM. + root.depth = parent.getRoot().depth - 1000; + } + return root; + }, + getFormulaFn: function(data) { + var me = this, + fn = me.formulaFn; + if (!fn) { + fn = me.formulaFn = function(name) { + // Note that the `this` pointer here is the view model because + // the VM calls it in the VM scope. + return me.$formulaData[name]; + }; + } + me.$formulaData = data; + return fn; + } + } +}); +// + +/** + * This class implements the controller event domain. All classes extending from + * {@link Ext.app.Controller} are included in this domain. The selectors are simply id, + * alias, or the wildcard "*" to match any controller. + * + * @private + */ +Ext.define('Ext.app.domain.Controller', { + extend: 'Ext.app.EventDomain', + singleton: true, + requires: [ + 'Ext.app.Controller' + ], + type: 'controller', + prefix: 'controller.', + idMatchRe: /^\#/, + constructor: function() { + var me = this; + me.callParent(); + me.monitor(Ext.app.BaseController); + }, + match: function(target, selector) { + var result = false, + alias = target.alias; + if (selector === '*') { + result = true; + } else if (selector === '#') { + result = !!target.isApplication; + } else if (this.idMatchRe.test(selector)) { + result = target.getId() === selector.substring(1); + } else if (alias) { + result = Ext.Array.indexOf(alias, this.prefix + selector) > -1; + } + return result; + } +}); + +/** + * Ext Direct aims to streamline communication between the client and server + * by providing a single interface that reduces the amount of common code + * typically required to validate data and handle returned data packets + * (reading data, error conditions, etc). + * + * The `Ext.direct` namespace includes several classes for a closer integration + * with the server-side. The Ext.data namespace also includes classes for working + * with Ext.data.Stores which are backed by data from an Ext Direct method. + * + * # Specification + * + * For additional information consult the [Ext Direct Specification][1]. + * + * # Providers + * + * Ext Direct uses a provider architecture, where one or more providers are used + * to transport data to and from the server. There are several providers that exist + * in the core at the moment: + * + * - {@link Ext.direct.JsonProvider JsonProvider} for simple JSON operations + * - {@link Ext.direct.PollingProvider PollingProvider} for repeated requests + * - {@link Ext.direct.RemotingProvider RemotingProvider} exposes server side to the client. + * + * A provider does not need to be invoked directly, providers are added via + * {@link Ext.direct.Manager #addProvider}. RemotingProviders' API declarations + * can also be loaded with {@link Ext.direct.Manager #loadProvider}, with + * Provider instance created automatically after successful retrieval. + * + * # Router + * + * Ext Direct RemotingProviders utilize a "router" on the server to direct + * requests from the client to the appropriate server-side method. Because + * the Ext Direct API is platform-agnostic, you could completely swap out + * a Java based server solution and replace it with one that uses C# + * without changing the client side JavaScript at all, or vice versa. + * + * # Server side events + * + * Custom events from the server may be handled by the client by adding listeners, for example: + * + * {"type":"event","name":"message","data":"Successfully polled at: 11:19:30 am"} + * + * // add a handler for a 'message' event sent by the server + * Ext.direct.Manager.on('message', function(e){ + * out.append(String.format('

{0}

', e.data)); + * out.el.scrollTo('t', 100000, true); + * }); + * + * [1]: http://sencha.com/products/extjs/extdirect + * + * @singleton + * @alternateClassName Ext.Direct + */ +Ext.define('Ext.direct.Manager', { + singleton: true, + requires: [ + 'Ext.util.MixedCollection' + ], + mixins: [ + 'Ext.mixin.Observable' + ], + /** + * Exception types. + */ + exceptions: { + TRANSPORT: 'xhr', + PARSE: 'parse', + DATA: 'data', + LOGIN: 'login', + SERVER: 'exception' + }, + // Classes of Providers available to the application + providerClasses: {}, + // Remoting Methods registered with the Manager + remotingMethods: {}, + config: { + /** + * @cfg {String} [varName="Ext.REMOTING_API"] + * Default variable name to use for Ext Direct API declaration. + */ + varName: 'Ext.REMOTING_API' + }, + apiNotFoundError: 'Ext Direct API was not found at {0}', + /** + * @event event + * + * Fires after an event. + * + * @param {Ext.direct.Event} event The {@link Ext.direct.Event Event} that occurred. + * @param {Ext.direct.Provider} provider The {@link Ext.direct.Provider Provider} + * that provided the event. + */ + /** + * @event exception + * + * Fires after an event exception. + * + * @param {Ext.direct.Event} event The {@link Ext.direct.Event Event} that occurred. + * @param {Ext.direct.Provider} provider The {@link Ext.direct.Provider Provider} + * that provided the event. + */ + /** + * @event providerload + * + * Fired by {@link #loadProvider} after successfully loading RemotingProvider API + * declaration and creating a new Provider instance. + * + * @param {String} url The URL used to retrieve remoting API. + * @param {Ext.direct.Provider} provider The {@link Ext.direct.Provider Provider} + * instance that was created. + */ + /** + * @event providerloaderror + * + * Fired by {@link #loadProvider} when remoting API could not be loaded, or + * Provider instance could not be created. + * + * @param {String} url The URL used to retrieve remoting API. + * @param {String} error The error that occured. + */ + /** + * @private + */ + constructor: function() { + var me = this; + me.mixins.observable.constructor.call(me); + me.transactions = new Ext.util.MixedCollection(); + me.providers = new Ext.util.MixedCollection(); + }, + /** + * Adds an Ext Direct Provider and creates the proxy or stub methods to execute + * server-side methods for RemotingProviders. If the provider is not already connected, + * it will auto-connect. + * + * var pollProv = new Ext.direct.PollingProvider({ + * id: 'polling1', + * url: 'php/poll2.php' + * }); + * + * Ext.direct.Manager.addProvider({ + * id: 'remoting1', + * type: 'remoting', // create a Ext.direct.RemotingProvider + * url: 'php/router.php', // url to connect to the Ext Direct server-side router. + * actions: { // each property within the actions object represents an Action + * TestAction: [{ // array of Methods within each server side Action + * name: 'doEcho', // name of method + * len: 1 + * }, { + * name: 'multiply', + * len: 1 + * }, { + * name: 'doForm', + * formHandler: true // handle form on server with Ext.direct.Transaction + * }] + * }, + * namespace: 'myApplication', // namespace to create the Remoting Provider in + * }, { + * id: 'polling2', + * type: 'polling', // create an Ext.direct.PollingProvider + * url: 'php/poll.php' + * }, + * pollProv); // reference to previously created instance + * + * @param {Ext.direct.Provider/Object...} provider + * + * Accepts any number of Provider descriptions (an instance or config object for + * a Provider). Each Provider description instructs Ext Direct how to create + * client-side stub methods. + */ + addProvider: function(provider) { + var me = this, + args = arguments, + relayers = me.relayers || (me.relayers = {}), + i, len; + if (args.length > 1) { + for (i = 0 , len = args.length; i < len; ++i) { + me.addProvider(args[i]); + } + return; + } + // if provider has not already been instantiated + if (!provider.isProvider) { + provider = Ext.create('direct.' + provider.type + 'provider', provider); + } + me.providers.add(provider); + provider.on('data', me.onProviderData, me); + if (provider.relayedEvents) { + relayers[provider.id] = me.relayEvents(provider, provider.relayedEvents); + } + if (!provider.isConnected()) { + provider.connect(); + } + return provider; + }, + /** + * Load Ext Direct Provider API declaration from the server and construct + * a new Provider instance. The new Provider will then auto-connect and + * create stub functions for the methods exposed by the server side. See + * {@link #addProvider}. + * + * Ext.direct.Manager.loadProvider({ + * url: 'php/api.php', + * varName: 'MY_REMOTING_API' // defaults to 'Ext.REMOTING_API' + * }); + * + * @param {Object} config Remoting API configuration. + * @param {String} config.url URL to retrieve remoting API declaration from. + * @param {String} config.varName Name of the variable that will hold + * RemotingProvider configuration block, including its Actions. + * @param {Function} [callback] Optional callback to execute when + * Provider is created, or when an error has occured. + * @param {Object} [scope] Optional scope to execute callback function in. + * + * For additional information see the [Ext Direct specification][1]. + */ + loadProvider: function(config, callback, scope) { + var me = this, + classes = me.providerClasses, + type, url, varName, provider, i, len; + if (Ext.isArray(config)) { + for (i = 0 , len = config.length; i < len; i++) { + me.loadProvider(config[i], callback, scope); + } + return; + } + // We may have been passed config object containing enough + // information to create a Provider without further ado. + type = config.type; + url = config.url; + if (classes[type] && classes[type].checkConfig(config)) { + provider = me.addProvider(config); + me.fireEventArgs('providerload', [ + url, + provider + ]); + Ext.callback(callback, scope, [ + url, + provider + ]); + // We're deliberately not returning the provider here + // to make way for the future Promises based implementation + // that should be consistent with the remote API declaration + // retrieval below. + return; + } + // For remote API declaration retrieval we need to know the + // service discovery URL and variable name, at the minimum. + // We have a default for the variable name but not for URL. + varName = config.varName || me.getVarName(); + delete config.varName; + if (!url) { + Ext.raise("Need API discovery URL to load a Remoting provider!"); + } + // The URL we are requesting API from is not the same as the + // service URL, and we don't need them to mix. + delete config.url; + // Have to use closures here as Loader does not allow passing + // options object from caller to callback. + Ext.Loader.loadScript({ + url: url, + scope: me, + onLoad: function() { + this.onApiLoadSuccess({ + url: url, + varName: varName, + config: config, + callback: callback, + scope: scope + }); + }, + onError: function() { + this.onApiLoadFailure({ + url: url, + callback: callback, + scope: scope + }); + } + }); + }, + /** + * Retrieves a {@link Ext.direct.Provider provider} by the id specified when the + * provider is added. + * + * @param {String/Ext.direct.Provider} id The id of the provider, or the provider instance. + */ + getProvider: function(id) { + return id.isProvider ? id : this.providers.get(id); + }, + /** + * Removes the provider. + * + * @param {String/Ext.direct.Provider} provider The provider instance or the id of the provider. + * + * @return {Ext.direct.Provider} The provider, null if not found. + */ + removeProvider: function(provider) { + var me = this, + providers = me.providers, + relayers = me.relayers, + id; + provider = provider.isProvider ? provider : providers.get(provider); + if (provider) { + provider.un('data', me.onProviderData, me); + id = provider.id; + if (relayers[id]) { + relayers[id].destroy(); + delete relayers[id]; + } + providers.remove(provider); + return provider; + } + return null; + }, + /** + * Adds a transaction to the manager. + * + * @param {Ext.direct.Transaction} transaction The transaction to add + * + * @return {Ext.direct.Transaction} transaction + * + * @private + */ + addTransaction: function(transaction) { + this.transactions.add(transaction); + return transaction; + }, + /** + * Removes a transaction from the manager. + * + * @param {String/Ext.direct.Transaction} transaction The transaction/id of transaction to remove + * + * @return {Ext.direct.Transaction} transaction + * + * @private + */ + removeTransaction: function(transaction) { + var me = this; + transaction = me.getTransaction(transaction); + me.transactions.remove(transaction); + return transaction; + }, + /** + * Gets a transaction + * + * @param {String/Ext.direct.Transaction} transaction The transaction/id of transaction to get + * + * @return {Ext.direct.Transaction} + * + * @private + */ + getTransaction: function(transaction) { + return typeof transaction === 'object' ? transaction : this.transactions.get(transaction); + }, + onProviderData: function(provider, event) { + var me = this, + i, len; + if (Ext.isArray(event)) { + for (i = 0 , len = event.length; i < len; ++i) { + me.onProviderData(provider, event[i]); + } + return; + } + if (event.name && event.name !== 'event' && event.name !== 'exception') { + me.fireEvent(event.name, event); + } else if (event.status === false) { + me.fireEvent('exception', event); + } + me.fireEvent('event', event, provider); + }, + /** + * Parses a direct function. It may be passed in a string format, for example: + * "MyApp.Person.read". + * + * @param {String/Function} fn The direct function + * + * @return {Function} The function to use in the direct call. Null if not found + */ + parseMethod: function(fn) { + var current = Ext.global, + i = 0, + resolved, parts, len; + if (Ext.isFunction(fn)) { + resolved = fn; + } else if (Ext.isString(fn)) { + resolved = this.remotingMethods[fn]; + // Support legacy resolution as top-down lookup + // from the window scope + if (!resolved) { + parts = fn.split('.'); + len = parts.length; + while (current && i < len) { + current = current[parts[i]]; + ++i; + } + resolved = Ext.isFunction(current) ? current : null; + } + } + return resolved || null; + }, + /** + * @private + * Iterate over an API object containing function names and resolve Direct functions. + * + * @param {Object} api API object + * @param {Ext.Base} caller The object calling + * + * @return {Object} The API object with each property resolved to a Direct function. + */ + resolveApi: function(api, caller) { + var prefix, action, method, fullName, fn; + prefix = api && api.prefix; + if (prefix && prefix.substr(prefix.length - 1) !== '.') { + prefix += '.'; + } + for (action in api) { + method = api[action]; + if (action !== 'prefix' && typeof method !== 'function') { + fullName = (prefix || '') + method; + fn = this.parseMethod(fullName); + if (typeof fn === 'function') { + api[action] = fn; + } else { + Ext.raise("Cannot resolve Direct API method '" + fullName + "' for " + action + " action in " + caller.$className + " instance with id: " + (caller.id != null ? caller.id : 'unknown')); + } + } + } + return api; + }, + privates: { + addProviderClass: function(type, cls) { + this.providerClasses[type] = cls; + }, + onApiLoadSuccess: function(options) { + var me = this, + url = options.url, + varName = options.varName, + api, provider, error; + try { + // Variable name could be nested (default is Ext.REMOTING_API), + // so we use eval() to get the actual value. + api = Ext.apply(options.config, eval(varName)); + provider = me.addProvider(api); + } catch (e) { + error = e + ''; + } + if (error) { + me.fireEventArgs('providerloaderror', [ + url, + error + ]); + Ext.callback(options.callback, options.scope, [ + url, + error + ]); + } else { + me.fireEventArgs('providerload', [ + url, + provider + ]); + Ext.callback(options.callback, options.scope, [ + url, + provider + ]); + } + }, + onApiLoadFailure: function(options) { + var url = options.url, + error; + error = Ext.String.format(this.apiNotFoundError, url); + this.fireEventArgs('providerloaderror', [ + url, + error + ]); + Ext.callback(options.callback, options.scope, [ + url, + error + ]); + }, + registerMethod: function(name, method) { + this.remotingMethods[name] = method; + }, + // Used for testing + clearAllMethods: function() { + this.remotingMethods = {}; + } + } +}, function() { + // Backwards compatibility + Ext.Direct = Ext.direct.Manager; +}); + +/** + * Ext.direct.Provider is an abstract class meant to be extended. + * + * For example Ext JS implements the following subclasses: + * + * Provider + * | + * +---JsonProvider + * | + * +---PollingProvider + * | + * +---RemotingProvider + * + * @abstract + */ +Ext.define('Ext.direct.Provider', { + alias: 'direct.provider', + mixins: [ + 'Ext.mixin.Observable' + ], + requires: [ + 'Ext.direct.Manager' + ], + isProvider: true, + $configPrefixed: false, + $configStrict: false, + /** + * @cfg {String} id + * The unique id of the provider (defaults to an {@link Ext#id auto-assigned id}). + * You should assign an id if you need to be able to access the provider later and you do + * not have an object reference available, for example: + * + * Ext.direct.Manager.addProvider({ + * type: 'polling', + * url: 'php/poll.php', + * id: 'poll-provider' + * }); + * var p = {@link Ext.direct.Manager}.{@link Ext.direct.Manager#getProvider getProvider}('poll-provider'); + * p.disconnect(); + * + */ + /** + * @cfg {String[]} relayedEvents + * List of Provider events that should be relayed by {@link Ext.direct.Manager}. + * 'data' event is always relayed. + */ + config: { + /** + * @cfg {Object} [headers] + * An object containing default headers for every Ajax request made by this Provider. + */ + headers: undefined + }, + /** + * @event connect + * Fires when the Provider connects to the server-side + * + * @param {Ext.direct.Provider} provider The {@link Ext.direct.Provider Provider}. + */ + /** + * @event disconnect + * Fires when the Provider disconnects from the server-side + * + * @param {Ext.direct.Provider} provider The {@link Ext.direct.Provider Provider}. + */ + /** + * @event data + * Fires when the Provider receives data from the server-side. This event is fired + * for valid responses as well as for exceptions. + * + * @param {Ext.direct.Provider} provider The {@link Ext.direct.Provider Provider} instance. + * @param {Ext.direct.Event} e The {@link Ext.direct.Event} that occurred. + */ + /** + * @event exception + * Fires when the Provider receives an exception from the server-side. This event is *not* + * fired for valid responses. + * + * @param {Ext.direct.Provider} provider The {@link Ext.direct.Provider Provider} instance. + * @param {Ext.direct.Event} e The {@link Ext.direct.Event Exception event} that occured. + */ + subscribers: 0, + constructor: function(config) { + var me = this; + me.mixins.observable.constructor.call(me, config); + me.requests = {}; + Ext.applyIf(me, { + id: Ext.id(null, 'provider-') + }); + }, + destroy: function() { + var me = this; + me.disconnect(true); + me.callParent(); + }, + /** + * Returns whether or not the server-side is currently connected. + */ + isConnected: function() { + return this.subscribers > 0; + }, + /** + * Connect the provider and start its service. + * Provider will fire `connect` event upon successful connection. + */ + connect: function() { + var me = this; + if (me.subscribers === 0) { + me.doConnect(); + me.fireEventArgs('connect', [ + me + ]); + } + me.subscribers++; + }, + /** + * @method + * + * Do connection setup. This is a template method. + * @template + * @protected + */ + doConnect: Ext.emptyFn, + /** + * Disconnect the provider and stop its service. + * Provider will fire `disconnect` event upon successful disconnect. + */ + disconnect: function(/* */ + force) { + var me = this; + if (me.subscribers > 0 || force) { + if (force) { + me.subscribers = 0; + } else { + me.subscribers--; + } + if (me.subscribers === 0) { + me.doDisconnect(); + me.fireEventArgs('disconnect', [ + me + ]); + } + } + }, + /** + * @method + * + * Do connection teardown. This is a template method. + * @template + * @protected + */ + doDisconnect: function() { + var requests = this.requests, + request, id; + for (id in requests) { + request = requests[id]; + request.abort(); + } + this.requests = {}; + }, + /** + * Send the Ajax request + * + * @param {Object} params Ajax request parameters + * + * @private + */ + sendAjaxRequest: function(params) { + var request = Ext.Ajax.request(params); + if (request && request.id) { + this.requests[request.id] = request; + } + return request; + }, + /** + * Ajax request callback + * + * @private + */ + onData: function(options, success, response) { + if (response && response.request) { + delete this.requests[response.request.id]; + } + }, + inheritableStatics: { + /** + * @method + * + * Check if the passed configuration object contains enough + * information to construct a Provider. + * + * @param {Object} config + * + * @return {Boolean} `true` if config is sufficient, `false` otherwise. + * @static + * @inheritable + */ + checkConfig: Ext.returnFalse + }, + onClassExtended: function(cls, data, hooks) { + if (data.type) { + Ext.direct.Manager.addProviderClass(data.type, cls); + } + } +}); + +/** + * This class implements the Ext Direct event domain. All classes extending from + * {@link Ext.direct.Provider} are included in this domain. The selectors are simply provider + * id's or the wildcard "*" to match any provider. + * + * @private + */ +Ext.define('Ext.app.domain.Direct', { + extend: 'Ext.app.EventDomain', + singleton: true, + requires: [ + 'Ext.direct.Provider' + ], + type: 'direct', + idProperty: 'id', + constructor: function() { + var me = this; + me.callParent(); + me.monitor(Ext.direct.Provider); + } +}); + +/** + * @class Ext.data.PageMap + * @extends Ext.util.LruCache + * Private class for use by only Store when configured `buffered: true`. + * @private + */ +Ext.define('Ext.data.PageMap', { + extend: 'Ext.util.LruCache', + config: { + store: null, + /** + * @cfg {Number} pageSize + * The size of pages in this map. + */ + pageSize: 0, + /** + * @cfg {String} rootProperty + * The root property to use for aggregation, filtering and sorting. By default + * this is `null` but when containing things like {@link Ext.data.Model records} + * this config would likely be set to "data" so that property names are applied + * to the fields of each record. + */ + rootProperty: '' + }, + // Maintain a generation counter, so that the Store can reject incoming pages destined for the previous generation + clear: function(initial) { + var me = this; + me.pageMapGeneration = (me.pageMapGeneration || 0) + 1; + // Map of internalId to recordIndex + me.indexMap = {}; + me.callParent([ + initial + ]); + }, + updatePageSize: function(value, oldValue) { + if (oldValue != null) { + throw "pageMap page size may not be changed"; + } + }, + forEach: function(fn, scope) { + var me = this, + pageNumbers = Ext.Object.getKeys(me.map), + pageCount = pageNumbers.length, + pageSize = me.getPageSize(), + i, j, pageNumber, page, len; + for (i = 0; i < pageCount; i++) { + pageNumbers[i] = +pageNumbers[i]; + } + Ext.Array.sort(pageNumbers, Ext.Array.numericSortFn); + scope = scope || me; + for (i = 0; i < pageCount; i++) { + pageNumber = pageNumbers[i]; + page = me.getPage(pageNumber); + len = page.length; + for (j = 0; j < len; j++) { + if (fn.call(scope, page[j], (pageNumber - 1) * pageSize + j) === false) { + return; + } + } + } + }, + /** + * Returns the first record in this page map which elicits a true return value from the + * passed selection function. + * + * **IMPORTANT + * This can ONLY find records which happen to be cached in the page cache. This will be parts of the dataset around the currently + * visible zone, or recently visited zones if the pages have not yet been purged from the cache. + * + * This CAN NOT find records which have not been loaded into the cache.** + * + * If full client side searching is required, do not use a buffered store, instead use a regular, fully loaded store and + * use the {@link Ext.grid.plugin.BufferedRenderer BufferedRenderer} plugin to minimize DOM footprint. + * @param {Function} fn The selection function to execute for each item. + * @param {Mixed} fn.rec The record. + * @param {Mixed} fn.index The index in the total dataset of the record. + * @param {Object} [scope] The scope (`this` reference) in which the function is executed. Defaults to this PageMap. + * @return {Object} The first record in this page map which returned true from the selection + * function, or null if none was found. + */ + findBy: function(fn, scope) { + var me = this, + result = null; + scope = scope || me; + me.forEach(function(rec, index) { + if (fn.call(scope, rec, index)) { + result = rec; + return false; + } + }); + return result; + }, + /** + * Returns the index *in the whole dataset* of the first record in this page map which elicits a true return value from the + * passed selection function. + * + * **IMPORTANT + * This can ONLY find records which happen to be cached in the page cache. This will be parts of the dataset around the currently + * visible zone, or recently visited zones if the pages have not yet been purged from the cache. + * + * This CAN NOT find records which have not been loaded into the cache.** + * + * If full client side searching is required, do not use a buffered store, instead use a regular, fully loaded store and + * use the {@link Ext.grid.plugin.BufferedRenderer BufferedRenderer} plugin to minimize DOM footprint. + * @param {Function} fn The selection function to execute for each item. + * @param {Mixed} fn.rec The record. + * @param {Mixed} fn.index The index in the total dataset of the record. + * @param {Object} [scope] The scope (`this` reference) in which the function is executed. Defaults to this PageMap. + * @return {Number} The index first record in this page map which returned true from the selection + * function, or -1 if none was found. + */ + findIndexBy: function(fn, scope) { + var me = this, + result = -1; + scope = scope || me; + me.forEach(function(rec, index) { + if (fn.call(scope, rec)) { + result = index; + return false; + } + }); + return result; + }, + find: function(property, value, start, startsWith, endsWith, ignoreCase) { + if (Ext.isEmpty(value, false)) { + return null; + } + var regex = Ext.String.createRegex(value, startsWith, endsWith, ignoreCase), + root = this.getRootProperty(); + return this.findBy(function(item) { + return item && regex.test((root ? item[root] : item)[property]); + }, null, start); + }, + findIndex: function(property, value, start, startsWith, endsWith, ignoreCase) { + if (Ext.isEmpty(value, false)) { + return null; + } + var regex = Ext.String.createRegex(value, startsWith, endsWith, ignoreCase), + root = this.getRootProperty(); + return this.findIndexBy(function(item) { + return item && regex.test((root ? item[root] : item)[property]); + }, null, start); + }, + getPageFromRecordIndex: function(index) { + return Math.floor(index / this.getPageSize()) + 1; + }, + addAll: function(records) { + if (this.getCount()) { + Ext.raise('Cannot addAll to a non-empty PageMap'); + } + this.addPage(1, records); + }, + addPage: function(pageNumber, records) { + var me = this, + pageSize = me.getPageSize(), + lastPage = pageNumber + Math.floor((records.length - 1) / pageSize), + storeIndex = (pageNumber - 1) * pageSize, + indexMap = me.indexMap, + page, i, len, startIdx; + // Account for being handed a block of records spanning several pages. + // This can happen when loading from a MemoryProxy before a viewSize has been determined. + for (startIdx = 0; pageNumber <= lastPage; pageNumber++ , startIdx += pageSize) { + page = Ext.Array.slice(records, startIdx, startIdx + pageSize); + // Maintain the indexMap so that we can implement indexOf(record) + for (i = 0 , len = page.length; i < len; i++) { + indexMap[page[i].internalId] = storeIndex++; + } + me.add(pageNumber, page); + me.fireEvent('pageadd', me, pageNumber, page); + } + }, + getCount: function() { + var result = this.callParent(); + if (result) { + result = (result - 1) * this.getPageSize() + this.last.value.length; + } + return result; + }, + getByInternalId: function(internalId) { + var index = this.indexMap[internalId]; + if (index != null) { + return this.getAt(index); + } + }, + indexOf: function(record) { + var result = -1; + if (record) { + result = this.indexMap[record.internalId]; + if (result == null) { + result = -1; + } + } + return result; + }, + insert: function() { + Ext.raise('insert operation not suppported into buffered Store'); + }, + remove: function() { + Ext.raise('remove operation not suppported from buffered Store'); + }, + removeAt: function() { + Ext.raise('removeAt operation not suppported from buffered Store'); + }, + removeAtKey: function(page) { + // Allow observers to veto + var me = this, + thePage = me.getPage(page), + len, i, result; + if (thePage) { + if (me.fireEvent('beforepageremove', me, page, thePage) !== false) { + len = thePage.length; + for (i = 0; i < len; i++) { + delete me.indexMap[thePage[i].internalId]; + } + result = me.callParent(arguments); + me.fireEvent('pageremove', me, page, thePage); + // Empty the page array *after* informing observers that the records have exited. + thePage.length = 0; + } + } + return result; + }, + getPage: function(pageNumber) { + return this.get(pageNumber); + }, + hasRange: function(start, end) { + var me = this, + pageNumber = me.getPageFromRecordIndex(start), + endPageNumber = me.getPageFromRecordIndex(end); + for (; pageNumber <= endPageNumber; pageNumber++) { + if (!me.hasPage(pageNumber)) { + return false; + } + } + // Check that the last page is filled enough to encapsulate the range. + return (endPageNumber - 1) * me._pageSize + me.getPage(endPageNumber).length > end; + }, + hasPage: function(pageNumber) { + // We must use this.get to trigger an access so that the page which is checked for presence is not eligible for pruning + return !!this.get(pageNumber); + }, + peekPage: function(pageNumber) { + return this.map[pageNumber]; + }, + getAt: function(index) { + return this.getRange(index, index + 1)[0]; + }, + getRange: function(start, end) { + // Store's backing Collection now uses EXCLUSIVE endIndex + // So store will always pass the endIndex+1 unless it's 0 + if (end) { + end--; + } + if (!this.hasRange(start, end)) { + Ext.raise('PageMap asked for range which it does not have'); + } + var me = this, + Array = Ext.Array, + pageSize = me.getPageSize(), + startPageNumber = me.getPageFromRecordIndex(start), + endPageNumber = me.getPageFromRecordIndex(end), + dataStart = (startPageNumber - 1) * pageSize, + dataEnd = (endPageNumber * pageSize) - 1, + pageNumber = startPageNumber, + result = [], + sliceBegin, sliceEnd, doSlice; + for (; pageNumber <= endPageNumber; pageNumber++) { + // First and last pages *may* need slicing to cut into the actual wanted records + if (pageNumber === startPageNumber) { + sliceBegin = start - dataStart; + doSlice = sliceBegin > 0; + } else { + sliceBegin = 0; + doSlice = false; + } + if (pageNumber === endPageNumber) { + sliceEnd = pageSize - (dataEnd - end); + doSlice = doSlice || sliceEnd < pageSize; + } + // First and last pages will need slicing + if (doSlice) { + Array.push(result, Array.slice(me.getPage(pageNumber), sliceBegin, sliceEnd)); + } else { + Array.push(result, me.getPage(pageNumber)); + } + } + return result; + } +}); + +/** + * A BufferedStore maintains a sparsely populated map of pages corresponding to an extremely large server-side dataset. + * + * **Note:** Buffered Stores are not available in the modern toolkit. Instead use + * `Ext.data.virtual.Store`. + * + * Use a BufferedStore when the dataset size is so large that the database and network latency, and client memory requirements + * preclude caching the entire dataset in a regular {@link Ext.data.Store Store}. + * + * When using a BufferedStore *not all of the dataset is present in the client*. Only pages which have been + * requested by the UI (usually a {@link Ext.grid.Panel GridPanel}) and surrounding pages will be present. Retention + * of viewed pages in the BufferedStore after they have been scrolled out of view is configurable. See {@link #leadingBufferZone}, + * {@link #trailingBufferZone} and {@link #purgePageCount}. + * + * To use a BufferedStore, initiate the loading process by loading the first page. The number of rows rendered are + * determined automatically, and the range of pages needed to keep the cache primed for scrolling is + * requested and cached. + * Example: + * + * myBufferedStore.loadPage(1); // Load page 1 + * + * A {@link Ext.grid.plugin.BufferedRenderer BufferedRenderer} is instantiated which will monitor the scrolling in the grid, and + * refresh the view's rows from the page cache as needed. It will also pull new data into the page + * cache when scrolling of the view draws upon data near either end of the prefetched data. + * + * The margins which trigger view refreshing from the prefetched data are {@link Ext.grid.plugin.BufferedRenderer#numFromEdge}, + * {@link Ext.grid.plugin.BufferedRenderer#leadingBufferZone} and {@link Ext.grid.plugin.BufferedRenderer#trailingBufferZone}. + * + * The margins which trigger loading more data into the page cache are, {@link #leadingBufferZone} and + * {@link #trailingBufferZone}. + * + * By default, only 5 pages of data (in addition to the pages which over the visible region) are cached in the page cache, + * with old pages being evicted from the cache as the view moves down through the dataset. This is controlled by the + * {@link #purgePageCount} setting. + * + * Setting this value to zero means that no pages are *ever* scrolled out of the page cache, and + * that eventually the whole dataset may become present in the page cache. This is sometimes desirable + * as long as datasets do not reach astronomical proportions. + * + * Selection state may be maintained across page boundaries by configuring the SelectionModel not to discard + * records from its collection when those Records cycle out of the Store's primary collection. This is done + * by configuring the SelectionModel like this: + * + * selModel: { + * pruneRemoved: false + * } + * + */ +Ext.define('Ext.data.BufferedStore', { + extend: 'Ext.data.ProxyStore', + alias: 'store.buffered', + requires: [ + 'Ext.data.PageMap', + 'Ext.util.Filter', + 'Ext.util.Sorter', + 'Ext.util.Grouper' + ], + uses: [ + 'Ext.util.SorterCollection', + 'Ext.util.FilterCollection', + 'Ext.util.GroupCollection' + ], + /** + * @property {Boolean} isBufferedStore + * `true` in this class to identify an object as an instantiated BufferedStore, or subclass thereof. + */ + isBufferedStore: true, + // For backward compatibility with user code. + buffered: true, + config: { + data: 0, + pageSize: 25, + /** + * @cfg remoteSort + * @inheritdoc + */ + remoteSort: true, + /** + * @cfg remoteFilter + * @inheritdoc + */ + remoteFilter: true, + /** + * @cfg sortOnLoad + * @inheritdoc + */ + sortOnLoad: false, + /** + * @cfg {Number} purgePageCount + * + * The number of pages *in addition to twice the required buffered range* to keep + * in the prefetch cache before purging least recently used records. + * + * For example, if the height of the view area and the configured + * {@link #trailingBufferZone} and {@link #leadingBufferZone} require that there + * are three pages in the cache, then a `purgePageCount` of 5 ensures that up to + * 11 pages can be in the page cache any any one time. This is enough to allow + * the user to scroll rapidly between different areas of the dataset without + * evicting pages which are still needed. + * + * A value of 0 indicates to never purge the prefetched data. + */ + purgePageCount: 5, + /** + * @cfg {Number} trailingBufferZone + * The number of extra records to keep cached on the trailing side of scrolling + * buffer as scrolling proceeds. A larger number means fewer replenishments from + * the server. + */ + trailingBufferZone: 25, + /** + * @cfg {Number} leadingBufferZone + * The number of extra rows to keep cached on the leading side of scrolling + * buffer as scrolling proceeds. A larger number means fewer replenishments from + * the server. + */ + leadingBufferZone: 200, + /** + * @cfg {Number} defaultViewSize + * The default view size to use until the + * {@link #viewSize} has been configured. + * @private + */ + defaultViewSize: 100, + /** + * @cfg {Number} viewSize The view size needed to fill the current view. Defaults + * to the {@link #defaultViewSize}. + * This will typically be set by the underlying view. + * @private + */ + viewSize: 0, + /** + * @cfg {Boolean} trackRemoved + * The {@link Ext.data.ProxyStore#cfg!trackRemoved trackRemoved} config is not + * supported by buffered stores. + */ + trackRemoved: false + }, + /** + * We are using applyData so that we can return nothing and prevent the `this.data` + * property to be overridden. + * @param {Array/Object} data + */ + applyData: function(data) { + var dataCollection = this.data || (this.data = this.createDataCollection()); + if (data && data !== true) { + Ext.raise('Cannot load a buffered store with local data - the store is a map of remote data'); + } + return dataCollection; + }, + applyProxy: function(proxy) { + proxy = this.callParent([ + proxy + ]); + // This store asks for pages. + // If used with a MemoryProxy, it must work + if (proxy && proxy.setEnablePaging) { + proxy.setEnablePaging(true); + } + return proxy; + }, + applyAutoSort: function() {}, + // Return undefined so that applier does not run. + // BufferedStore/PageMap cannot sort. + createFiltersCollection: function() { + return new Ext.util.FilterCollection(); + }, + createSortersCollection: function() { + return new Ext.util.SorterCollection(); + }, + updateRemoteFilter: function(remoteFilter, oldRemoteFilter) { + if (remoteFilter === false) { + Ext.raise('Buffered stores are always remotely filtered.'); + } + this.callParent([ + remoteFilter, + oldRemoteFilter + ]); + }, + updateRemoteSort: function(remoteSort, oldRemoteSort) { + if (remoteSort === false) { + Ext.raise('Buffered stores are always remotely sorted.'); + } + this.callParent([ + remoteSort, + oldRemoteSort + ]); + }, + updateTrackRemoved: function(value) { + if (value !== false) { + Ext.raise('Cannot use trackRemoved with a buffered store.'); + } + this.callParent(arguments); + }, + updateGroupField: function(field) { + this.group(field); + }, + getGrouper: function() { + return this.grouper; + }, + isGrouped: function() { + return !!this.grouper; + }, + createDataCollection: function() { + var me = this, + result = new Ext.data.PageMap({ + store: me, + rootProperty: 'data', + pageSize: me.getPageSize(), + maxSize: me.getPurgePageCount(), + listeners: { + // Whenever PageMap gets cleared, it means we re no longer interested in + // any outstanding page prefetches, so cancel them all + clear: me.onPageMapClear, + scope: me + } + }); + // Allow view to veto prune if the old page is still in use by the view + me.relayEvents(result, [ + 'beforepageremove', + 'pageadd', + 'pageremove' + ]); + me.pageRequests = {}; + return result; + }, + add: function() { + Ext.raise('add method may not be called on a buffered store - the store is a map of remote data'); + }, + insert: function() { + Ext.raise('insert method may not be called on a buffered store - the store is a map of remote data'); + }, + removeAll: function(silent) { + var me = this, + data = me.getData(); + if (data) { + if (silent) { + me.suspendEvent('clear'); + } + data.clear(); + if (silent) { + me.resumeEvent('clear'); + } + } + }, + flushLoad: function() { + var me = this, + options = me.pendingLoadOptions; + // If it gets called programmatically, the listener will need cancelling + me.clearLoadTask(); + if (!options) { + return; + } + // Buffered stores, a load operation means kick off a clean load from page 1 + // unless it's specified to preserve the options + if (!options.preserveOnFlush) { + me.getData().clear(); + options.page = 1; + options.start = 0; + options.limit = me.getViewSize() || me.getDefaultViewSize(); + } + // If we're prefetching, the arguments on the callback for getting the range is different + // So we indicate that we need to fire a special "load" style callback + options.loadCallback = options.callback; + // options might be chained, with callback on a prototype; delete won't clear it. + options.callback = null; + return me.loadToPrefetch(options); + }, + reload: function(options) { + var me = this, + data = me.getData(), + // If we don't have a known totalCount, use a huge value + lastTotal = Number.MAX_VALUE, + startIdx, endIdx, startPage, endPage, i, waitForReload, bufferZone, records; + if (!options) { + options = {}; + } + // Prevent re-entering the load process if we are already in a wait state for a batch of pages. + if (me.loading || me.fireEvent('beforeload', me, options) === false) { + return; + } + waitForReload = function() { + var newCount = me.totalCount, + oldRequestSize = endIdx - startIdx; + // If the dataset has now shrunk leaving the calculated request zone unavailable, + // re-evaluate the request zone. Start as close to the end as possible. + if (endIdx >= newCount) { + endIdx = newCount - 1; + startIdx = Math.max(endIdx - oldRequestSize, 0); + } + if (me.rangeCached(startIdx, endIdx, false)) { + me.loadCount = (me.loadCount || 0) + 1; + me.loading = false; + data.un('pageadd', waitForReload); + records = data.getRange(startIdx, endIdx); + me.fireEvent('refresh', me); + me.fireEvent('load', me, records, true); + } + }; + bufferZone = Math.ceil((me.getLeadingBufferZone() + me.getTrailingBufferZone()) / 2); + // Decide what reload means. + // If the View was configured preserveScrollOnReload, then it will + // inject that setting here. This means that reload means + // load the last requested range. + if (me.lastRequestStart && me.preserveScrollOnReload) { + startIdx = me.lastRequestStart; + endIdx = me.lastRequestEnd; + lastTotal = me.getTotalCount(); + } else // Otherwise, reload means start from page 1 + { + startIdx = options.start || 0; + endIdx = startIdx + (options.count || me.getPageSize()) - 1; + } + // Clear page cache + data.clear(true); + // So that prefetchPage does not consider the store to be fully loaded if the local count is equal to the total count + delete me.totalCount; + // Calculate a page range which encompasses the Store's loaded range plus both buffer zones + startIdx = Math.max(startIdx - bufferZone, 0); + endIdx = Math.min(endIdx + bufferZone, lastTotal); + // We must wait for a slightly wider range to be cached. + // This is to allow grouping features to peek at the two surrounding records + // when rendering a *range* of records to see whether the start of the range + // really is a group start and the end of the range really is a group end. + startIdx = startIdx === 0 ? 0 : startIdx - 1; + endIdx = endIdx === lastTotal ? endIdx : endIdx + 1; + startPage = me.getPageFromRecordIndex(startIdx); + endPage = me.getPageFromRecordIndex(endIdx); + me.loading = true; + options.waitForReload = waitForReload; + // Wait for the requested range to become available in the page map + // Load the range as soon as the whole range is available + data.on('pageadd', waitForReload); + // Recache the page range which encapsulates our visible records + for (i = startPage; i <= endPage; i++) { + me.prefetchPage(i, options); + } + }, + filter: function() { + if (!this.getRemoteFilter()) { + Ext.raise('Local filtering may not be used on a buffered store - the store is a map of remote data'); + } + // Remote filtering forces a load. load clears the store's contents. + this.callParent(arguments); + }, + filterBy: function(fn, scope) { + Ext.raise('Local filtering may not be used on a buffered store - the store is a map of remote data'); + }, + loadData: function(data, append) { + Ext.raise('LoadData may not be used on a buffered store - the store is a map of remote data'); + }, + loadPage: function(page, options) { + var me = this; + options = options || {}; + options.page = me.currentPage = page; + options.start = (page - 1) * me.getPageSize(); + options.limit = me.getViewSize() || me.getDefaultViewSize(); + options.loadCallback = options.callback; + // options might be chained, with callback on a prototype; delete won't clear it. + options.callback = null; + // Since we're deferring these to flushLoad, we need to preserve the options. + // Otherwise, they will be reset. + options.preserveOnFlush = true; + return me.load(options); + }, + clearData: function(isLoad) { + var me = this, + data = me.getData(); + if (data) { + data.clear(); + } + }, + /** + * @private + * A BufferedStore always reports that it contains the full dataset. + * The number of records that happen to be cached at any one time is never useful. + */ + getCount: function() { + return this.totalCount || 0; + }, + getRange: function(start, end, options) { + var me = this, + maxIndex = me.totalCount - 1, + lastRequestStart = me.lastRequestStart, + result = [], + data = me.getData(), + pageAddHandler, requiredStart, requiredEnd, requiredStartPage, requiredEndPage; + options = Ext.apply({ + prefetchStart: start, + prefetchEnd: end + }, options); + // Sanity check end point to be within dataset range + end = (end >= me.totalCount) ? maxIndex : end; + // If this is being called in the default manner, to fetch data + // for rendering, then we must wait for a slightly wider range to be cached. + // This is to allow grouping features to peek at the two surrounding records + // when rendering a *range* of records to see whether the start of the range + // really is a group start and the end of the range really is a group end. + if (options.forRender !== false) { + requiredStart = start === 0 ? 0 : start - 1; + requiredEnd = end === maxIndex ? end : end + 1; + } else { + requiredStart = start; + requiredEnd = end; + } + // Keep track of range we are being asked for so we can track direction of movement through the dataset + me.lastRequestStart = start; + me.lastRequestEnd = end; + // If data request can be satisfied from the page cache + if (me.rangeCached(start, end, options.forRender)) { + me.onRangeAvailable(options); + result = data.getRange(start, end + 1); + } else // At least some of the requested range needs loading from server + { + // Private event used by the LoadMask class to perform masking when the range required for rendering is not found in the cache + me.fireEvent('cachemiss', me, start, end); + requiredStartPage = me.getPageFromRecordIndex(requiredStart); + requiredEndPage = me.getPageFromRecordIndex(requiredEnd); + // Add a pageadd listener, and as soon as the requested range is loaded, call onRangeAvailable to call the callback. + pageAddHandler = function(pageMap, page, records) { + if (page >= requiredStartPage && page <= requiredEndPage && me.rangeCached(start, end)) { + // Private event used by the LoadMask class to unmask when the range required for rendering has been loaded into the cache + me.fireEvent('cachefilled', me, start, end); + data.un('pageadd', pageAddHandler); + me.onRangeAvailable(options); + } + }; + data.on('pageadd', pageAddHandler); + // Prioritize the request for the *exact range that the UI is asking for*. + // When a page request is in flight, it will not be requested again by checking the me.pageRequests hash, + // so the request after this will only request the *remaining* unrequested pages . + me.prefetchRange(start, end); + } + // Load the pages around the requested range required by the leadingBufferZone and trailingBufferZone. + me.primeCache(start, end, start < lastRequestStart ? -1 : 1); + return result; + }, + /** + * Get the Record with the specified id. + * + * This method is not affected by filtering, lookup will be performed from all records + * inside the store, filtered or not. + * + * @param {Mixed} id The id of the Record to find. + * @return {Ext.data.Model} The Record with the passed id. Returns null if not found. + */ + getById: function(id) { + var result = this.data.findBy(function(record) { + return record.getId() === id; + }); + return result; + }, + /** + * @method getAt + * @inheritdoc + */ + getAt: function(index) { + var data = this.getData(); + if (data.hasRange(index, index)) { + return data.getAt(index); + } + }, + /** + * @private + * Get the Record with the specified internalId. + * + * This method is not effected by filtering, lookup will be performed from all records + * inside the store, filtered or not. + * + * @param {Mixed} internalId The id of the Record to find. + * @return {Ext.data.Model} The Record with the passed internalId. Returns null if not found. + */ + getByInternalId: function(internalId) { + return this.data.getByInternalId(internalId); + }, + /** + * @method contains + * @inheritdoc + */ + contains: function(record) { + return this.indexOf(record) > -1; + }, + /** + * Get the index of the record within the store. + * + * When store is filtered, records outside of filter will not be found. + * + * @param {Ext.data.Model} record The Ext.data.Model object to find. + * @return {Number} The index of the passed Record. Returns -1 if not found. + */ + indexOf: function(record) { + return this.getData().indexOf(record); + }, + /** + * Get the index within the store of the Record with the passed id. + * + * Like #indexOf, this method is effected by filtering. + * + * @param {String} id The id of the Record to find. + * @return {Number} The index of the Record. Returns -1 if not found. + */ + indexOfId: function(id) { + return this.indexOf(this.getById(id)); + }, + group: function(grouper, direction) { + var me = this, + oldGrouper; + if (grouper && typeof grouper === 'string') { + oldGrouper = me.grouper; + if (oldGrouper && direction !== undefined) { + oldGrouper.setDirection(direction); + } else { + me.grouper = new Ext.util.Grouper({ + property: grouper, + direction: direction || 'ASC', + root: 'data' + }); + } + } else { + me.grouper = grouper ? me.getSorters().decodeSorter(grouper, Ext.util.Grouper) : null; + } + me.getData().clear(); + me.loadPage(1, { + callback: function() { + me.fireEvent('groupchange', me, me.getGrouper()); + } + }); + }, + /** + * Determines the page from a record index + * @param {Number} index The record index + * @return {Number} The page the record belongs to + */ + getPageFromRecordIndex: function(index) { + return Math.floor(index / this.getPageSize()) + 1; + }, + calculatePageCacheSize: function(rangeSizeRequested) { + var me = this, + purgePageCount = me.getPurgePageCount(); + // Calculate the number of pages that the cache will keep before purging as follows: + // TWO full rendering zones (in case of rapid teleporting by dragging the scroller) plus configured purgePageCount. + // Ensure we never reduce the count. It always uses the largest requested block as the basis for the calculated size. + return purgePageCount ? Math.max(me.getData().getMaxSize() || 0, Math.ceil((rangeSizeRequested + me.getTrailingBufferZone() + me.getLeadingBufferZone()) / me.getPageSize()) * 2 + purgePageCount) : 0; + }, + loadToPrefetch: function(options) { + var me = this, + prefetchOptions = options, + i, records, dataSetSize, + // Get the requested record index range in the dataset + startIdx = options.start, + endIdx = options.start + options.limit - 1, + rangeSizeRequested = (me.getViewSize() || options.limit), + // The end index to load into the store's live record collection + loadEndIdx = Math.min(endIdx, options.start + rangeSizeRequested - 1), + // Calculate a page range which encompasses the requested range plus both buffer zones. + // The endPage will be adjusted to be in the dataset size range as soon as the first data block returns. + startPage = me.getPageFromRecordIndex(Math.max(startIdx - me.getTrailingBufferZone(), 0)), + endPage = me.getPageFromRecordIndex(endIdx + me.getLeadingBufferZone()), + data = me.getData(), + callbackFn = function() { + // See comments in load() for why we need this. + records = records || []; + if (options.loadCallback) { + options.loadCallback.call(options.scope || me, records, operation, true); + } + if (options.callback) { + options.callback.call(options.scope || me, records, startIdx || 0, endIdx || 0, options); + } + }, + fireEventsFn = function() { + me.loadCount = (me.loadCount || 0) + 1; + me.fireEvent('datachanged', me); + me.fireEvent('refresh', me); + me.fireEvent('load', me, records, true); + }, + // Wait for the viewable range to be available. + waitForRequestedRange = function() { + if (me.rangeCached(startIdx, loadEndIdx)) { + me.loading = false; + records = data.getRange(startIdx, loadEndIdx + 1); + data.un('pageadd', waitForRequestedRange); + // If there is a listener for guaranteedrange then fire that event + if (me.hasListeners.guaranteedrange) { + me.guaranteeRange(startIdx, loadEndIdx, options.callback, options.scope); + } + callbackFn(); + fireEventsFn(); + } + }, + operation; + if (isNaN(me.pageSize) || !me.pageSize) { + Ext.raise('Buffered store configured without a pageSize', me); + } + // Ensure that the purgePageCount allows enough pages to be kept cached to cover the + // requested range. If the pageSize is very small we might need a lot of pages. + data.setMaxSize(me.calculatePageCacheSize(rangeSizeRequested)); + if (me.fireEvent('beforeload', me, options) !== false) { + // So that prefetchPage does not consider the store to be fully loaded if the local count is equal to the total count + delete me.totalCount; + me.loading = true; + // Any configured callback is handled in waitForRequestedRange above. + // It should not be processed by onProxyPrefetch. + if (options.callback) { + prefetchOptions = Ext.apply({}, options); + delete prefetchOptions.callback; + } + // Load the first page in the range, which will give us the initial total count. + // Once it is loaded, go ahead and prefetch any subsequent pages, if necessary. + // The prefetchPage has a check to prevent us loading more than the totalCount, + // so we don't want to blindly load up pages where it isn't required. + me.on('prefetch', function(store, records, successful, op) { + // Capture operation here so it can be used in the loadCallback above + operation = op; + if (successful) { + // If there is data in the dataset, we can go ahead and add the pageadd listener which waits for the visible range + // and we can also issue the requests to fill the surrounding buffer zones. + if ((dataSetSize = me.getTotalCount())) { + // Wait for the requested range to become available in the page map + data.on('pageadd', waitForRequestedRange); + // As soon as we have the size of the dataset, ensure we are not waiting for more than can ever arrive, + loadEndIdx = Math.min(loadEndIdx, dataSetSize - 1); + // And make sure we never ask for pages beyond the end of the dataset. + endPage = me.getPageFromRecordIndex(Math.min(loadEndIdx + me.getLeadingBufferZone(), dataSetSize - 1)); + for (i = startPage + 1; i <= endPage; ++i) { + me.prefetchPage(i, prefetchOptions); + } + } else { + callbackFn(); + fireEventsFn(); + } + } else // Unsuccessful prefetch: fire a load event with success false. + { + me.loading = false; + callbackFn(); + me.fireEvent('load', me, records, false); + } + }, null, { + single: true + }); + me.prefetchPage(startPage, prefetchOptions); + } + }, + // Buffering + /** + * Prefetches data into the store using its configured {@link #proxy}. + * @param {Object} options (Optional) config object, passed into the Ext.data.operation.Operation object before loading. + * See {@link #method-load} + */ + prefetch: function(options) { + var me = this, + pageSize = me.getPageSize(), + data = me.getData(), + operation, existingPageRequest; + // Check pageSize has not been tampered with. That would break page caching + if (pageSize) { + if (me.lastPageSize && pageSize != me.lastPageSize) { + Ext.raise("pageSize cannot be dynamically altered"); + } + if (!data.getPageSize()) { + data.setPageSize(pageSize); + } + } else // Allow first prefetch call to imply the required page size. + { + me.pageSize = data.setPageSize(pageSize = options.limit); + } + // So that we can check for tampering next time through + me.lastPageSize = pageSize; + // Always get whole pages. + if (!options.page) { + options.page = me.getPageFromRecordIndex(options.start); + options.start = (options.page - 1) * pageSize; + options.limit = Math.ceil(options.limit / pageSize) * pageSize; + } + // Currently not requesting this page, or the request was for the last + // generation of the data cache (clearing it changes generations) + // then request it... + existingPageRequest = me.pageRequests[options.page]; + if (!existingPageRequest || existingPageRequest.getOperation().pageMapGeneration !== data.pageMapGeneration) { + // Copy options into a new object so as not to mutate passed in objects + options = Ext.apply({ + action: 'read', + filters: me.getFilters().items, + sorters: me.getSorters().items, + grouper: me.getGrouper(), + internalCallback: me.onProxyPrefetch, + internalScope: me + }, options); + operation = me.createOperation('read', options); + // Generation # of the page map to which the requested records belong. + // If page map is cleared while this request is in flight, the pageMapGeneration will increment and the payload will be rejected + operation.pageMapGeneration = data.pageMapGeneration; + if (me.fireEvent('beforeprefetch', me, operation) !== false) { + me.pageRequests[options.page] = operation.execute(); + if (me.getProxy().isSynchronous) { + delete me.pageRequests[options.page]; + } + } + } + return me; + }, + /** + * @private + * Cancels all pending prefetch requests. + * + * This is called when the page map is cleared. + * + * Any requests which still make it through will be for the previous pageMapGeneration + * (pageMapGeneration is incremented upon clear), and so will be rejected upon arrival. + */ + onPageMapClear: function() { + var me = this, + loadingFlag = me.wasLoading, + reqs = me.pageRequests, + data = me.getData(), + page; + // If any requests return, we no longer respond to them. + data.clearListeners(); + // replace the listeners we need. + data.on('clear', me.onPageMapClear, me); + me.relayEvents(data, [ + 'beforepageremove', + 'pageadd', + 'pageremove' + ]); + // If the page cache gets cleared it's because a full reload is in progress. + // Setting the loading flag prevents linked Views from displaying the empty text + // during a load... we don't know whether their dataset is empty or not. + me.loading = true; + me.totalCount = 0; + // Abort all outstanding requests. + // onProxyPrefetch will reject them as being for the previous data generation + // anyway, if they do return. + // because of the pageMapGeneration mismatch. + for (page in reqs) { + if (reqs.hasOwnProperty(page)) { + reqs[page].getOperation().abort(); + } + } + // This will update any views. + me.fireEvent('clear', me); + // Restore loading flag. The beforeload event could still veto the process. + // The flag does not get set for real until we pass the beforeload event. + me.loading = loadingFlag; + }, + /** + * Prefetches a page of data. + * @param {Number} page The page to prefetch + * @param {Object} options (Optional) config object, passed into the Ext.data.operation.Operation object before loading. + * See {@link #method-load} + */ + prefetchPage: function(page, options) { + var me = this, + pageSize = me.getPageSize(), + start = (page - 1) * pageSize, + total = me.totalCount; + // No more data to prefetch. + if (total !== undefined && me.data.getCount() === total) { + return; + } + // Copy options into a new object so as not to mutate passed in objects + me.prefetch(Ext.applyIf({ + page: page, + start: start, + limit: pageSize + }, options)); + }, + /** + * Called after the configured proxy completes a prefetch operation. + * @private + * @param {Ext.data.operation.Operation} operation The operation that completed + */ + onProxyPrefetch: function(operation) { + if (this.destroying || this.destroyed) { + return; + } + var me = this, + resultSet = operation.getResultSet(), + records = operation.getRecords(), + successful = operation.wasSuccessful(), + page = operation.getPage(), + waitForReload = operation.waitForReload, + oldTotal = me.totalCount, + requests = me.pageRequests, + key, op; + // Only cache the data if the operation was invoked for the current pageMapGeneration. + // If the pageMapGeneration has changed since the request was fired off, it will have been cancelled. + if (operation.pageMapGeneration === me.getData().pageMapGeneration) { + if (resultSet) { + me.totalCount = resultSet.getTotal(); + if (me.totalCount !== oldTotal) { + me.fireEvent('totalcountchange', me.totalCount); + } + } + // Remove the loaded page from the outstanding pages hash + if (page !== undefined) { + delete me.pageRequests[page]; + } + // Prefetch is broadcast before the page is cached + me.loading = false; + me.fireEvent('prefetch', me, records, successful, operation); + // Add the page into the page map. + // pageadd event may trigger the onRangeAvailable + if (successful) { + if (me.totalCount === 0) { + if (waitForReload) { + for (key in requests) { + op = requests[key].getOperation(); + // Created in the same batch, clear the waitForReload so this + // won't be run again + if (op.waitForReload === waitForReload) { + delete op.waitForReload; + } + } + me.getData().un('pageadd', waitForReload); + me.fireEvent('refresh', me); + me.fireEvent('load', me, [], true); + } + } else { + me.cachePage(records, operation.getPage()); + } + } + //this is a callback that would have been passed to the 'read' function and is optional + Ext.callback(operation.getCallback(), operation.getScope() || me, [ + records, + operation, + successful + ]); + } + }, + /** + * Caches the records in the prefetch and stripes them with their server-side + * index. + * @private + * @param {Ext.data.Model[]} records The records to cache + * @param {Ext.data.operation.Operation} page The associated operation + */ + cachePage: function(records, page) { + var me = this, + len = records.length, + i; + if (!Ext.isDefined(me.totalCount)) { + me.totalCount = records.length; + me.fireEvent('totalcountchange', me.totalCount); + } + // Add the fetched page into the pageCache + for (i = 0; i < len; i++) { + records[i].join(me); + } + me.getData().addPage(page, records); + }, + /** + * Determines if the passed range is available in the page cache. + * @private + * @param {Number} start The start index + * @param {Number} end The end index in the range + * @param {Boolean} [forRender] (private) Passed by the BufferedRenderer to + * indicate that it's going to need extra rows to peek at to determine + * group start/end status for the rendered block. + */ + rangeCached: function(start, end, forRender) { + var requiredStart = start, + requiredEnd = end; + // If this is for getting data to render, we must wait for a slightly wider range to be cached. + // This is to allow grouping features to peek at the two surrounding records + // when rendering a *range* of records to see whether the start of the range + // really is a group start and the end of the range really is a group end. + if (forRender !== false) { + requiredStart = start === 0 ? 0 : start - 1 , requiredEnd = end === this.totalCount - 1 ? end : end + 1; + } + return this.getData().hasRange(requiredStart, requiredEnd); + }, + /** + * Determines if the passed page is available in the page cache. + * @private + * @param {Number} page The page to find in the page cache. + */ + pageCached: function(page) { + return this.getData().hasPage(page); + }, + /** + * Determines if a request for a page is currently running + * @private + * @param {Number} page The page to check for + */ + pagePending: function(page) { + return !!this.pageRequests[page]; + }, + /** + * Determines if the passed range is available in the page cache. + * @private + * @deprecated 4.1.0 use {@link #rangeCached} instead + * @param {Number} start The start index + * @param {Number} end The end index in the range + * @return {Boolean} + */ + rangeSatisfied: function(start, end) { + return this.rangeCached(start, end); + }, + /** + * Handles the availability of a requested range that was not previously available + * @private + */ + onRangeAvailable: function(options) { + var me = this, + totalCount = me.getTotalCount(), + start = options.prefetchStart, + end = (options.prefetchEnd > totalCount - 1) ? totalCount - 1 : options.prefetchEnd, + range; + end = Math.max(0, end); + if (start > end) { + Ext.log({ + level: 'warn', + msg: 'Start (' + start + ') was greater than end (' + end + ') for the range of records requested (' + start + '-' + options.prefetchEnd + ')' + (this.storeId ? ' from store "' + this.storeId + '"' : '') + }); + } + range = me.getData().getRange(start, end + 1); + if (options.fireEvent !== false) { + me.fireEvent('guaranteedrange', range, start, end, options); + } + if (options.callback) { + options.callback.call(options.scope || me, range, start, end, options); + } + }, + /** + * Guarantee a specific range, this will load the store with a range (that + * must be the `pageSize` or smaller) and take care of any loading that may + * be necessary. + * @param {Number} start The starting index. Defaults to zero. + * @param {Number} end The ending index. Defaults to the last record. The end index + * **is included**. + * @param {Function} callback Function to call with the results + * @param {Object} [scope] The `this` pointer for the `callback`. + * @param {Object} [options] (private) + * @deprecated 4.2 Use {@link #getRange} + */ + guaranteeRange: function(start, end, callback, scope, options) { + options = Ext.apply({ + callback: callback, + scope: scope + }, options); + this.getRange(start, end + 1, options); + }, + /** + * Ensures that the specified range of rows is present in the cache. + * + * Converts the row range to a page range and then only load pages which are not already + * present in the page cache. + */ + prefetchRange: function(start, end) { + var me = this, + startPage, endPage, page, + data = me.getData(); + if (!me.rangeCached(start, end)) { + startPage = me.getPageFromRecordIndex(start); + endPage = me.getPageFromRecordIndex(end); + // Ensure that the page cache's max size is correct. + // Our purgePageCount is the number of additional pages *outside of the required range* which + // may be kept in the cache. A purgePageCount of zero means unlimited. + data.setMaxSize(me.calculatePageCacheSize(end - start + 1)); + // We have the range, but ensure that we have a "buffer" of pages around it. + for (page = startPage; page <= endPage; page++) { + if (!me.pageCached(page)) { + me.prefetchPage(page); + } + } + } + }, + primeCache: function(start, end, direction) { + var me = this, + leadingBufferZone = me.getLeadingBufferZone(), + trailingBufferZone = me.getTrailingBufferZone(), + pageSize = me.getPageSize(), + totalCount = me.totalCount; + // Scrolling up + if (direction === -1) { + start = Math.max(start - leadingBufferZone, 0); + end = Math.min(end + trailingBufferZone, totalCount - 1); + } + // Scrolling down + else if (direction === 1) { + start = Math.max(Math.min(start - trailingBufferZone, totalCount - pageSize), 0); + end = Math.min(end + leadingBufferZone, totalCount - 1); + } else // Teleporting + { + start = Math.min(Math.max(Math.floor(start - ((leadingBufferZone + trailingBufferZone) / 2)), 0), totalCount - me.pageSize); + end = Math.min(Math.max(Math.ceil(end + ((leadingBufferZone + trailingBufferZone) / 2)), 0), totalCount - 1); + } + me.prefetchRange(start, end); + }, + sort: function(field, direction, mode) { + if (arguments.length === 0) { + this.clearAndLoad(); + } else { + this.getSorters().addSort(field, direction, mode); + } + }, + onSorterEndUpdate: function() { + var me = this, + sorters = me.getSorters().getRange(); + // Only load or sort if there are sorters + if (sorters.length) { + me.fireEvent('beforesort', me, sorters); + me.clearAndLoad({ + callback: function() { + me.fireEvent('sort', me, sorters); + } + }); + } else { + // Sort event must fire when sorters collection is updated to empty. + me.fireEvent('sort', me, sorters); + } + }, + clearAndLoad: function(options) { + var me = this; + me.clearing = true; + me.getData().clear(); + me.clearing = false; + me.loadPage(1, options); + }, + privates: { + isLast: function(record) { + return this.indexOf(record) === this.getTotalCount() - 1; + }, + isMoving: function() { + return false; + } + } +}); + +/** + * This class is used to send requests to the server using {@link Ext.direct.Manager Ext Direct}. + * When a request is made, the transport mechanism is handed off to the appropriate + * {@link Ext.direct.RemotingProvider Provider} to complete the call. + * + * # Specifying the functions + * + * This proxy expects Direct remoting method to be passed in order to be able to complete requests, + * one Direct function per CRUD method. This is done via {@link #api} configuration: + * + * api: { + * read: 'MyApp.readRecords', + * create: 'MyApp.createRecords', + * update: 'MyApp.updateRecords', + * destroy: 'MyApp.destroyRecords' + * } + * + * You can also use a `prefix` config to avoid duplicating full namespaces for Direct functions: + * + * api: { + * prefix: 'MyApp', + * read: 'readRecords', + * create: 'createRecords', + * update: 'updateRecords', + * destroy: 'destroyRecords' + * } + * + * The preferred way is to specify function names to allow late resolution, however you can + * pass function references instead if desired: + * + * api: { + * read: MyApp.readRecords, + * create: MyApp.createRecords, + * update: MyApp.updateRecords, + * destroy: MyApp.destroyRecords + * } + * + * This method of configuring API is not recommended because this way the Direct functions + * need to be created very early in the application lifecycle, long before {@link Ext.app.Application} + * instance is initialized. + * + * You can also use the {@link #directFn} configuration instead of {@link #api}. This will use + * the same Direct function for all types of requests. + * + * # Server API + * + * The server side methods are expected to conform to the following calling conventions: + * + * ## `read` + * + * Accept one argument which is either named arguments in an object (default), or an array + * of values depending on the {@link #paramsAsHash} configuration. Return an array of records + * or an object with format recognizable by the configured {@link Ext.data.reader.Reader} + * instance. + * + * Example {@link Ext.direct.RemotingProvider#cfg-actions Direct API declaration}: + * + * actions: { + * MyApp: [{ + * name: 'readRecords', + * params: [], + * strict: false + * }] + * } + * + * Example function invocation: + * + * MyApp.readRecords( + * { + * start: 0, + * limit: 10 + * }, + * // Results are passed to the callback function + * function(records) { + * console.log(records); + * // Logs: [{ id: 'r0', text: 'foo' }, { id: 'r1', text: 'bar' }] + * } + * ); + * + * ## `create` + * + * Accept one ordered argument which is either an object with data for the new record, + * or an array of objects for multiple records. Return an array of identifiers for actually + * created records. See {@link Ext.data.Model#clientIdProperty} for more information. + * + * Example {@link Ext.direct.RemotingProvider#cfg-actions Direct API declaration}: + * + * actions: [ + * MyApp: [{ + * name: 'createRecords', + * len: 1 + * }] + * } + * + * Example function invocation: + * + * MyApp.createRecords( + * [ + * { id: 0, text: 'foo' }, + * { id: 1, text: 'bar' } + * ], + * // Results are passed to the callback function + * function(records) { + * console.log(records); + * // Logs: [{ clientId: 0, id: 'r0' }, { clientId: 1, id: 'r1' }] + * } + * ); + * + * ## `update` + * + * Accept one ordered argument which is either an object with updated data and valid + * record identifier, or an array of objects for multiple records. Return an array of + * objects with updated record data. + * + * Example {@link Ext.direct.RemotingProvider#cfg-actions Direct API declaration}: + * + * actions: [ + * MyApp: [{ + * name: 'updateRecords', + * len: 1 + * }] + * } + * + * Example function invocation: + * + * MyApp.updateRecords( + * [ + * { id: 'r0', text: 'blerg' }, + * { id: 'r1', text: 'throbbe' } + * ], + * // Results are passed to the callback function + * function(records) { + * console.log(records); + * // Logs: [{ id: 'r0', text: 'blerg' }, { id: 'r1', text: 'throbbe }] + * } + * ); + * + * ## `destroy` + * + * Accept one ordered argument which is an array of record identifiers to be deleted. + * Return an object with at least one {@link Ext.data.reader.Json#successProperty} + * property set to `true` or `false`, with more optional properties recognizable by configured + * {@link Ext.data.reader.Reader} instance. + * + * Example {@link Ext.direct.RemotingProvider#cfg-actions Direct API declaration}: + * + * actions: [ + * MyApp: [{ + * name: 'destroyRecords', + * len: 1 + * }] + * } + * + * Example function invocation: + * + * MyApp.destroyRecords( + * [ + * { id: 'r0' }, + * { id: 'r1' } + * ], + * // Results are passed to the callback function + * function(result) { + * // Default successProperty is `success` + * if (!result.success) { + * // Handle the error + * } + * } + * ); + * + * ## Read method parameters + * + * Direct proxy provides options to help configure which parameters will be sent to the server + * for Read operations. By setting the {@link #paramsAsHash} option to `true`, the proxy will + * send an object literal containing each of the passed parameters. This is the default. When + * {@link #paramsAsHash} is set to `false`, Proxy will pass the Read function an array of values + * instead of an object, with the order determined by {@link #paramOrder} value. + * + * Setting {@link #paramOrder} to any value other than `undefined` will automatically reset + * {@link #paramsAsHash} to `false`. + * + * # Example Usage + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: ['firstName', 'lastName'] + * }); + * + * Ext.define('Users', { + * extend: 'Ext.data.Store', + * model: 'User', + * proxy: { + * type: 'direct', + * directFn: 'MyApp.getUsers', + * // Tells the proxy to pass `start` and `limit` as two by-position arguments: + * paramOrder: 'start,limit' + * } + * }); + * + * var store = new Users(); + * store.load(); + */ +Ext.define('Ext.data.proxy.Direct', { + /* Begin Definitions */ + extend: 'Ext.data.proxy.Server', + alternateClassName: 'Ext.data.DirectProxy', + alias: 'proxy.direct', + requires: [ + 'Ext.direct.Manager' + ], + /* End Definitions */ + /** + * @cfg url + * @hide + */ + config: { + /** + * @cfg {String/String[]} paramOrder + * A list of params to be passed to server side Read function. Specify the params + * in the order in which they must be executed on the server-side as either (1) + * an Array of String values, or (2) a String of params delimited by either + * whitespace, comma, or pipe. For example, any of the following would be + * acceptable: + * + * paramOrder: ['param1','param2','param3'] + * paramOrder: 'param1 param2 param3' + * paramOrder: 'param1,param2,param3' + * paramOrder: 'param1|param2|param' + */ + paramOrder: undefined, + /** + * @cfg {Boolean} paramsAsHash + * Send Read function parameters as a collection of named arguments. Providing a + * {@link #paramOrder} nullifies this configuration. + */ + paramsAsHash: true, + /** + * @cfg {Function/String} directFn + * Function to call when executing a request. `directFn` is a simple alternative + * to defining the api configuration parameter for Stores which will not + * implement a full CRUD api. The `directFn` may also be a string reference to + * the fully qualified name of the function, for example: + * `'MyApp.company.GetProfile'`. This can be useful when using dynamic loading. + * The string will be resolved before calling the function for the first time. + */ + directFn: undefined, + /** + * @cfg {Object} api + * The same as {@link Ext.data.proxy.Server#api}, however instead of providing + * urls you should provide a Direct function name for each CRUD method. + * + * Instead of providing fully qualified names for each function, you can use + * `prefix` property to provide a common prefix for all functions: + * + * api: { + * prefix: 'MyApp', + * read: 'readRecords', + * create: 'createRecords', + * update: 'updateRecords', + * destroy: 'destroyRecords' + * } + * + * This way function names will be resolved to `'MyApp.readRecords'`, + * `'MyApp.createRecords'`, etc. Note that using `prefix` and fully qualified + * function names is **not** supported, and prefix will be used for every + * function name when configured. + * + * See also {@link #directFn}. + */ + api: undefined, + /** + * @cfg {Object/Array} metadata + * Optional set of fixed parameters to send with every Proxy request, similar to + * {@link #extraParams} but available with all CRUD requests. Also unlike + * {@link #extraParams}, metadata is not mixed with the ordinary data but sent + * separately in the data packet. + * You may need to update your server side Ext Direct stack to use this feature. + */ + metadata: undefined + }, + /** + * @private + */ + paramOrderRe: /[\s,|]/, + constructor: function(config) { + this.callParent([ + config + ]); + this.canceledOperations = {}; + }, + applyParamOrder: function(paramOrder) { + if (Ext.isString(paramOrder)) { + paramOrder = paramOrder.split(this.paramOrderRe); + } + return paramOrder; + }, + updateApi: function() { + this.methodsResolved = false; + }, + updateDirectFn: function() { + this.methodsResolved = false; + }, + resolveMethods: function() { + var me = this, + fn = me.getDirectFn(), + api = me.getApi(), + method; + if (fn) { + me.setDirectFn(method = Ext.direct.Manager.parseMethod(fn)); + if (!Ext.isFunction(method)) { + Ext.raise('Cannot resolve directFn ' + fn); + } + } + if (api) { + api = Ext.direct.Manager.resolveApi(api, me); + me.setApi(api); + } + me.methodsResolved = true; + }, + doRequest: function(operation) { + var me = this, + writer, request, action, params, args, api, fn, callback; + if (!me.methodsResolved) { + me.resolveMethods(); + } + request = me.buildRequest(operation); + action = request.getAction(); + api = me.getApi(); + if (api) { + fn = api[action]; + } + fn = fn || me.getDirectFn(); + if (!fn || !fn.directCfg) { + Ext.raise({ + msg: 'No Ext Direct function specified for Direct proxy "' + action + '" operation', + proxy: me + }); + } + // This might lead to exceptions so bail out early + if (!me.paramOrder && fn.directCfg.method.len > 1) { + Ext.raise({ + msg: 'Incorrect parameters for Direct proxy "' + action + '" operation', + proxy: me + }); + } + writer = me.getWriter(); + if (writer && operation.allowWrite()) { + request = writer.write(request); + } + // The weird construct below is due to historical way of handling extraParams; + // they were mixed in with request data in ServerProxy.buildRequest() and were + // inseparable after that point. This does not work well with CUD operations + // so instead of using potentially poisoned request params we took the raw + // JSON data as Direct function argument payload (but only for CUD!). A side + // effect of that was that the request metadata (extraParams) was only available + // for read operations. + // We keep this craziness for backwards compatibility. + if (action === 'read') { + params = request.getParams(); + } else { + params = request.getJsonData(); + } + args = fn.directCfg.method.getArgs({ + params: params, + allowSingle: writer.getAllowSingle(), + paramOrder: me.getParamOrder(), + paramsAsHash: me.getParamsAsHash(), + paramsAsArray: true, + metadata: me.getMetadata(), + callback: me.createRequestCallback(request, operation), + scope: me + }); + request.setConfig({ + args: args, + directFn: fn + }); + fn.apply(window, args); + // Store expects us to return something to indicate that the request + // is pending; not doing so will make a buffered Store repeat the + // requests over and over. + return request; + }, + /** + * Aborts a running request by operation. + * + * @param {Ext.data.Operation} operation The operation to abort. This parameter + * is mandatory. + */ + abort: function(operation) { + var id; + // Assume this can be called with request instead of operation, a la Ajax proxy + if (operation && operation.isDataRequest) { + operation = operation.getOperation(); + } + // Check definedness again, the above could have returned null + if (operation && operation.isOperation) { + id = operation.id; + } + // We cannot abort a running request but we can ignore the data when it comes back. + if (id != null) { + this.canceledOperations[id] = true; + } + }, + /** + * @method applyEncoding + * @inheritdoc + */ + applyEncoding: Ext.identityFn, + createRequestCallback: function(request, operation) { + var me = this; + return function(data, event) { + if (!me.canceledOperations[operation.id]) { + me.processResponse(event.status, operation, request, event); + } + delete me.canceledOperations[operation.id]; + }; + }, + /** + * @method extractResponseData + * @inheritdoc + */ + extractResponseData: function(response) { + return Ext.isDefined(response.result) ? response.result : response.data; + }, + /** + * @method setException + * @inheritdoc + */ + setException: function(operation, response) { + operation.setException(response.message); + }, + /** + * @method buildUrl + * @inheritdoc + */ + buildUrl: function() { + return ''; + } +}); + +/** + * Small helper class to create an {@link Ext.data.Store} configured with an {@link Ext.data.proxy.Direct} + * and {@link Ext.data.reader.Json} to make interacting with an {@link Ext.direct.Manager} server-side + * {@link Ext.direct.Provider Provider} easier. To create a different proxy/reader combination create a basic + * {@link Ext.data.Store} configured as needed. + * + * **Note:** Although they are not listed, this class inherits all of the config options of: + * + * - **{@link Ext.data.Store Store}** + * + * - **{@link Ext.data.reader.Json JsonReader}** + * + * - **{@link Ext.data.reader.Json#cfg-rootProperty rootProperty}** + * - **{@link Ext.data.reader.Json#totalProperty totalProperty}** + * + * - **{@link Ext.data.proxy.Direct DirectProxy}** + * + * - **{@link Ext.data.proxy.Direct#directFn directFn}** + * - **{@link Ext.data.proxy.Direct#paramOrder paramOrder}** + * - **{@link Ext.data.proxy.Direct#paramsAsHash paramsAsHash}** + * + */ +Ext.define('Ext.data.DirectStore', { + /* Begin Definitions */ + extend: 'Ext.data.Store', + alias: 'store.direct', + requires: [ + 'Ext.data.proxy.Direct' + ], + /* End Definitions */ + constructor: function(config) { + config = Ext.apply({}, config); + if (!config.proxy) { + var proxy = { + type: 'direct', + reader: { + type: 'json' + } + }; + Ext.copyTo(proxy, config, 'paramOrder,paramsAsHash,directFn,api,simpleSortMode,extraParams'); + Ext.copyTo(proxy.reader, config, 'totalProperty,root,rootProperty,idProperty'); + config.proxy = proxy; + } + this.callParent([ + config + ]); + } +}); + +/** + * This class is used to create JSONP requests. JSONP is a mechanism that allows for making + * requests for data cross domain. JSONP is basically a ` + * + * When we inject the tag above, the browser makes a request to that url and includes the response as if it was any + * other type of JavaScript include. By passing a callback in the url above, we're telling domainB's server that we want + * to be notified when the result comes in and that it should call our callback function with the data it sends back. So + * long as the server formats the response to look like this, everything will work: + * + * someCallback({ + * users: [ + * { + * id: 1, + * name: "Ed Spencer", + * email: "ed@sencha.com" + * } + * ] + * }); + * + * As soon as the script finishes loading, the 'someCallback' function that we passed in the url is called with the JSON + * object that the server returned. + * + * JsonP proxy takes care of all of this automatically. It formats the url you pass, adding the callback parameter + * automatically. It even creates a temporary callback function, waits for it to be called and then puts the data into + * the Proxy making it look just like you loaded it through a normal {@link Ext.data.proxy.Ajax AjaxProxy}. Here's how + * we might set that up: + * + * Ext.define('User', { + * extend: 'Ext.data.Model', + * fields: ['id', 'name', 'email'] + * }); + * + * var store = Ext.create('Ext.data.Store', { + * model: 'User', + * proxy: { + * type: 'jsonp', + * url : 'http://domainB.com/users' + * } + * }); + * + * store.load(); + * + * That's all we need to do - JsonP proxy takes care of the rest. In this case the Proxy will have injected a script tag + * like this: + * + * + * + * # Customization + * + * This script tag can be customized using the {@link #callbackKey} configuration. For example: + * + * var store = Ext.create('Ext.data.Store', { + * model: 'User', + * proxy: { + * type: 'jsonp', + * url : 'http://domainB.com/users', + * callbackKey: 'theCallbackFunction' + * } + * }); + * + * store.load(); + * + * Would inject a script tag like this: + * + * + * + * # Implementing on the server side + * + * The remote server side needs to be configured to return data in this format. Here are suggestions for how you might + * achieve this using Java, PHP and ASP.net: + * + * Java: + * + * boolean jsonP = false; + * String cb = request.getParameter("callback"); + * if (cb != null) { + * jsonP = true; + * response.setContentType("text/javascript"); + * } else { + * response.setContentType("application/x-json"); + * } + * Writer out = response.getWriter(); + * if (jsonP) { + * out.write(cb + "("); + * } + * out.print(dataBlock.toJsonString()); + * if (jsonP) { + * out.write(");"); + * } + * + * PHP: + * + * $callback = $_REQUEST['callback']; + * + * // Create the output object. + * $output = array('a' => 'Apple', 'b' => 'Banana'); + * + * //start output + * if ($callback) { + * header('Content-Type: text/javascript'); + * echo $callback . '(' . json_encode($output) . ');'; + * } else { + * header('Content-Type: application/x-json'); + * echo json_encode($output); + * } + * + * ASP.net: + * + * String jsonString = "{"success": true}"; + * String cb = Request.Params.Get("callback"); + * String responseString = ""; + * if (!String.IsNullOrEmpty(cb)) { + * responseString = cb + "(" + jsonString + ")"; + * } else { + * responseString = jsonString; + * } + * Response.Write(responseString); + */ +Ext.define('Ext.data.proxy.JsonP', { + extend: 'Ext.data.proxy.Server', + alternateClassName: 'Ext.data.ScriptTagProxy', + alias: [ + 'proxy.jsonp', + 'proxy.scripttag' + ], + requires: [ + 'Ext.data.JsonP' + ], + config: { + /** + * @cfg {String} callbackKey + * See {@link Ext.data.JsonP#callbackKey}. + */ + callbackKey: 'callback', + /** + * @cfg {String} [recordParam] + * The HTTP parameter name to use when passing records to the server and the {@link #writer Json writer} is not configured + * to {@link Ext.data.writer.Json#encode encode} records into a parameter. + * + * The {@link #encodeRecords} method is used to encode the records to create this parameter's value. + */ + recordParam: 'records', + /** + * @cfg {Boolean} autoAppendParams + * True to automatically append the request's params to the generated url. Defaults to true + */ + autoAppendParams: true + }, + /** + * @private + * Performs the read request to the remote domain. JsonP proxy does not actually create an Ajax request, + * instead we write out a ` + * + * ## Configuration + * + * This component allows several options for configuring how the target Flash movie is embedded. The most + * important is the required {@link #url} which points to the location of the Flash movie to load. Other + * configurations include: + * + * - {@link #backgroundColor} + * - {@link #wmode} + * - {@link #flashVars} + * - {@link #flashParams} + * - {@link #flashAttributes} + * + * ## Example usage: + * + * var win = Ext.widget('window', { + * title: "It's a tiger!", + * layout: 'fit', + * width: 300, + * height: 300, + * x: 20, + * y: 20, + * resizable: true, + * items: { + * xtype: 'flash', + * url: 'tiger.swf' + * } + * }); + * win.show(); + * + * ## Express Install + * + * Adobe provides a tool called [Express Install](http://www.adobe.com/devnet/flashplayer/articles/express_install.html) + * that offers users an easy way to upgrade their Flash player. If you wish to make use of this, you should set + * the static EXPRESS\_INSTALL\_URL property to the location of your Express Install SWF file: + * + * Ext.flash.Component.EXPRESS_INSTALL_URL = 'path/to/local/expressInstall.swf'; + */ +Ext.define('Ext.flash.Component', { + extend: 'Ext.Component', + alternateClassName: 'Ext.FlashComponent', + alias: 'widget.flash', + /** + * @cfg {String} [flashVersion="9.0.115"] + * Indicates the version the flash content was published for. + */ + flashVersion: '9.0.115', + /** + * @cfg {String} [backgroundColor="#ffffff"] + * The background color of the SWF movie. + */ + backgroundColor: '#ffffff', + /** + * @cfg {String} [wmode="opaque"] + * The wmode of the flash object. This can be used to control layering. + * Set to 'transparent' to ignore the {@link #backgroundColor} and make the background of the Flash + * movie transparent. + */ + wmode: 'opaque', + /** + * @cfg {Object} flashVars + * A set of key value pairs to be passed to the flash object as flash variables. + */ + /** + * @cfg {Object} flashParams + * A set of key value pairs to be passed to the flash object as parameters. Possible parameters can be found here: + * http://kb2.adobe.com/cps/127/tn_12701.html + */ + /** + * @cfg {Object} flashAttributes + * A set of key value pairs to be passed to the flash object as attributes. + */ + /** + * @cfg {String} url (required) + * The URL of the SWF file to include. + */ + /** + * @cfg {String/Number} [swfWidth="100%"] + * The width of the embedded SWF movie inside the component. + * + * Defaults to "100%" so that the movie matches the width of the component. + */ + swfWidth: '100%', + /** + * @cfg {String/Number} [swfHeight="100%"] + * The height of the embedded SWF movie inside the component. + * + * Defaults to "100%" so that the movie matches the height of the component. + */ + swfHeight: '100%', + /** + * @cfg {Boolean} [expressInstall=false] + * True to prompt the user to install flash if not installed. Note that this uses + * Ext.FlashComponent.EXPRESS_INSTALL_URL, which should be set to the local resource. + */ + expressInstall: false, + /** + * @property {Ext.dom.Element} swf + * A reference to the object or embed element into which the SWF file is loaded. Only + * populated after the component is rendered and the SWF has been successfully embedded. + */ + // Have to create a placeholder div with the swfId, which SWFObject will replace with the object/embed element. + renderTpl: [ + '
' + ], + /** + * @event success + * Fired when the Flash movie has been successfully embedded + * @param {Ext.flash.Component} this + */ + /** + * @event failure + * Fired when the Flash movie embedding fails + * @param {Ext.flash.Component} this + */ + initComponent: function() { + if (!('swfobject' in window)) { + Ext.raise('The SWFObject library is not loaded. Ext.flash.Component requires SWFObject version 2.2 or later: http://code.google.com/p/swfobject/'); + } + if (!this.url) { + Ext.raise('The "url" config is required for Ext.flash.Component'); + } + this.callParent(); + }, + beforeRender: function() { + this.callParent(); + Ext.applyIf(this.renderData, { + swfId: this.getSwfId() + }); + }, + afterRender: function() { + var me = this, + flashParams = Ext.apply({}, me.flashParams), + flashVars = Ext.apply({}, me.flashVars); + me.callParent(); + flashParams = Ext.apply({ + allowScriptAccess: 'always', + bgcolor: me.backgroundColor, + wmode: me.wmode + }, flashParams); + flashVars = Ext.apply({ + allowedDomain: document.location.hostname + }, flashVars); + new swfobject.embedSWF(// jshint ignore:line + me.url, me.getSwfId(), me.swfWidth, me.swfHeight, me.flashVersion, me.expressInstall ? me.statics.EXPRESS_INSTALL_URL : undefined, flashVars, flashParams, me.flashAttributes, me.swfCallback.bind(me)); + }, + /** + * @private + * The callback method for handling an embedding success or failure by SWFObject + * @param {Object} e The event object passed by SWFObject - see http://code.google.com/p/swfobject/wiki/api + */ + swfCallback: function(e) { + var me = this; + if (e.success) { + me.swf = Ext.get(e.ref); + me.onSuccess(); + me.fireEvent('success', me); + } else { + me.onFailure(); + me.fireEvent('failure', me); + } + }, + /** + * Retrieves the id of the SWF object/embed element. + */ + getSwfId: function() { + return this.swfId || (this.swfId = "extswf" + this.getAutoId()); + }, + onSuccess: function() { + // swfobject forces visiblity:visible on the swf element, which prevents it + // from getting hidden when an ancestor is given visibility:hidden. + this.swf.setStyle('visibility', 'inherit'); + }, + onFailure: Ext.emptyFn, + doDestroy: function() { + var me = this, + swf = me.swf; + if (swf) { + swfobject.removeSWF(me.getSwfId()); + // jshint ignore:line + me.swf = Ext.destroy(swf); + } + me.callParent(); + }, + statics: { + /** + * @property {String} + * The url for installing flash if it doesn't exist. This should be set to a local resource. + * See [http://get.adobe.com/flashplayer/](http://get.adobe.com/flashplayer/) for details. + * @static + */ + EXPRESS_INSTALL_URL: 'http:/' + '/swfobject.googlecode.com/svn/trunk/swfobject/expressInstall.swf' + } +}); + +/** + * The subclasses of this class provide actions to perform upon {@link Ext.form.Basic Form}s. + * + * Instances of this class are only created by a {@link Ext.form.Basic Form} when the Form needs to perform an action + * such as submit or load. The Configuration options listed for this class are set through the Form's action methods: + * {@link Ext.form.Basic#submit submit}, {@link Ext.form.Basic#load load} and {@link Ext.form.Basic#doAction doAction} + * + * The instance of Action which performed the action is passed to the success and failure callbacks of the Form's action + * methods ({@link Ext.form.Basic#submit submit}, {@link Ext.form.Basic#load load} and + * {@link Ext.form.Basic#doAction doAction}), and to the {@link Ext.form.Basic#actioncomplete actioncomplete} and + * {@link Ext.form.Basic#actionfailed actionfailed} event handlers. + */ +Ext.define('Ext.form.action.Action', { + alternateClassName: 'Ext.form.Action', + /** + * @cfg {Ext.form.Basic} form + * The {@link Ext.form.Basic BasicForm} instance that is invoking this Action. Required. + */ + /** + * @cfg {String} url + * The URL that the Action is to invoke. Will default to the {@link Ext.form.Basic#url url} configured on the + * {@link #form}. + */ + /** + * @cfg {Boolean} reset + * When set to **true**, causes the Form to be {@link Ext.form.Basic#reset reset} on Action success. If specified, + * this happens before the {@link #success} callback is called and before the Form's + * {@link Ext.form.Basic#actioncomplete actioncomplete} event fires. + */ + /** + * @cfg {String} method + * The HTTP method to use to access the requested URL. + * Defaults to the {@link Ext.form.Basic#method BasicForm's method}, or 'POST' if not specified. + */ + /** + * @cfg {Object/String} params + * Extra parameter values to pass. These are added to the Form's {@link Ext.form.Basic#baseParams} and passed to the + * specified URL along with the Form's input fields. + * + * Parameters are encoded as standard HTTP parameters using {@link Ext#urlEncode Ext.Object.toQueryString}. + */ + /** + * @cfg {Object} headers + * Extra headers to be sent in the AJAX request for submit and load actions. + * See {@link Ext.data.proxy.Ajax#headers}. + * + * **Note:** Headers are not sent during file upload. + */ + /** + * @cfg {Number} timeout + * The number of seconds to wait for a server response before failing with the {@link #failureType} as + * {@link Ext.form.action.Action#CONNECT_FAILURE}. If not specified, defaults to the configured + * {@link Ext.form.Basic#timeout timeout} of the {@link #form}. + */ + /** + * @cfg {Function/String} success + * The function to call when a valid success return packet is received. + * @cfg {Ext.form.Basic} success.form The form that requested the action + * @cfg {Ext.form.action.Action} success.action The Action class. The {@link #result} property of this object may + * be examined to perform custom post-processing. + * + * @controllable + */ + /** + * @cfg {Function/String} failure + * The function to call when a failure packet was received, or when an error + * occurred in the Ajax communication. + * @cfg {Ext.form.Basic} failure.form The form that requested the action + * @cfg {Ext.form.action.Action} failure.action The Action class. If an Ajax error + * occurred, the failure type will be in {@link #failureType}. The {@link #result} + * property of this object may be examined to perform custom post-processing. + * + * @controllable + */ + /** + * @cfg {Object} scope + * The scope in which to call the configured #success and #failure callback functions + * (the `this` reference for the callback functions). + */ + /** + * @cfg {String} waitMsg + * The message to be displayed by a call to {@link Ext.window.MessageBox#wait} during the time the action is being + * processed. + */ + /** + * @cfg {String} waitTitle + * The title to be displayed by a call to {@link Ext.window.MessageBox#wait} during the time the action is being + * processed. + */ + /** + * @cfg {Boolean} submitEmptyText + * If set to true, the emptyText value will be sent with the form when it is submitted. + */ + submitEmptyText: true, + /** + * @property {String} type + * The type of action this Action instance performs. Currently only "submit" and "load" are supported. + */ + /** + * @property {String} failureType + * The type of failure detected will be one of these: + * {@link #CLIENT_INVALID}, {@link #SERVER_INVALID}, {@link #CONNECT_FAILURE}, or {@link #LOAD_FAILURE}. + * + * Usage: + * + * var fp = new Ext.form.Panel({ + * ... + * buttons: [{ + * text: 'Save', + * formBind: true, + * handler: function(){ + * if(fp.getForm().isValid()){ + * fp.getForm().submit({ + * url: 'form-submit.php', + * waitMsg: 'Submitting your data...', + * success: function(form, action){ + * // server responded with success = true + * var result = action.result; + * }, + * failure: function(form, action){ + * if (action.{@link #failureType} === Ext.form.action.Action.CONNECT_FAILURE) { + * Ext.Msg.alert('Error', + * 'Status:'+action.response.status+': '+ + * action.response.statusText); + * } + * if (action.failureType === Ext.form.action.Action.SERVER_INVALID){ + * // server responded with success = false + * Ext.Msg.alert('Invalid', action.result.errormsg); + * } + * } + * }); + * } + * } + * },{ + * text: 'Reset', + * handler: function(){ + * fp.getForm().reset(); + * } + * }] + */ + /** + * @property {Object} response + * The raw XMLHttpRequest object used to perform the action. + */ + /** + * @property {Object} result + * The decoded response object containing a boolean `success` property and other, action-specific properties. + */ + /** + * Creates new Action. + * @param {Object} [config] Config object. + */ + constructor: function(config) { + if (config) { + Ext.apply(this, config); + } + // Normalize the params option to an Object + var params = config.params; + if (Ext.isString(params)) { + this.params = Ext.Object.fromQueryString(params); + } + }, + /** + * @method + * Invokes this action using the current configuration. + */ + run: Ext.emptyFn, + /** + * @private + * @method onSuccess + * Callback method that gets invoked when the action completes successfully. Must be implemented by subclasses. + * @param {Object} response + */ + /** + * @private + * @method handleResponse + * Handles the raw response and builds a result object from it. Must be implemented by subclasses. + * @param {Object} response + */ + /** + * @private + * Handles a failure response. + * @param {Object} response + */ + onFailure: function(response) { + var form = this.form, + formActive = form && !form.destroying && !form.destroyed; + this.response = response; + this.failureType = Ext.form.action.Action.CONNECT_FAILURE; + if (formActive) { + form.afterAction(this, false); + } + }, + /** + * @private + * Validates that a response contains either responseText or responseXML and invokes + * {@link #handleResponse} to build the result object. + * @param {Object} response The raw response object. + * @return {Object/Boolean} The result object as built by handleResponse, or `true` if + * the response had empty responseText and responseXML. + */ + processResponse: function(response) { + this.response = response; + if (!response.responseText && !response.responseXML) { + return true; + } + return (this.result = this.handleResponse(response)); + }, + /** + * @private + * Build the URL for the AJAX request. Used by the standard AJAX submit and load actions. + * @return {String} The URL. + */ + getUrl: function() { + return this.url || this.form.url; + }, + /** + * @private + * Determine the HTTP method to be used for the request. + * @return {String} The HTTP method + */ + getMethod: function() { + return (this.method || this.form.method || 'POST').toUpperCase(); + }, + /** + * @private + * Get the set of parameters specified in the BasicForm's baseParams and/or the params option. + * Items in params override items of the same name in baseParams. + * @return {Object} the full set of parameters + */ + getParams: function() { + return Ext.apply({}, this.params, this.form.baseParams); + }, + /** + * @private + * Creates a callback object. + */ + createCallback: function() { + var me = this; + return { + success: me.onSuccess, + failure: me.onFailure, + scope: me, + timeout: (me.timeout || me.form.timeout) * 1000 + }; + }, + statics: { + /** + * @property + * Failure type returned when client side validation of the Form fails thus aborting a submit action. Client + * side validation is performed unless {@link Ext.form.action.Submit#clientValidation} is explicitly set to + * false. + * @static + */ + CLIENT_INVALID: 'client', + /** + * @property + * Failure type returned when server side processing fails and the {@link #result}'s `success` property is set to + * false. + * + * In the case of a form submission, field-specific error messages may be returned in the {@link #result}'s + * errors property. + * @static + */ + SERVER_INVALID: 'server', + /** + * @property + * Failure type returned when a communication error happens when attempting to send a request to the remote + * server. The {@link #response} may be examined to provide further information. + * @static + */ + CONNECT_FAILURE: 'connect', + /** + * @property + * Failure type returned when the response's `success` property is set to false, or no field values are returned + * in the response's data property. + * @static + */ + LOAD_FAILURE: 'load' + } +}); + +/** + * A class which handles loading of data from a server into the Fields of an {@link Ext.form.Basic}. + * + * Instances of this class are only created by a {@link Ext.form.Basic Form} when {@link Ext.form.Basic#load load}ing. + * + * ## Response Packet Criteria + * + * A response packet **must** contain: + * + * - **`success`** property : Boolean + * - **`data`** property : Object + * + * The `data` property contains the values of Fields to load. The individual value object for each Field is passed to + * the Field's {@link Ext.form.field.Field#setValue setValue} method. + * + * ## JSON Packets + * + * By default, response packets are assumed to be JSON, so for the following form load call: + * + * var myFormPanel = new Ext.form.Panel({ + * title: 'Client and routing info', + * renderTo: Ext.getBody(), + * defaults: { + * xtype: 'textfield' + * }, + * items: [{ + * fieldLabel: 'Client', + * name: 'clientName' + * }, { + * fieldLabel: 'Port of loading', + * name: 'portOfLoading' + * }, { + * fieldLabel: 'Port of discharge', + * name: 'portOfDischarge' + * }] + * }); + * myFormPanel.getForm().load({ + * url: '/getRoutingInfo.php', + * params: { + * consignmentRef: myConsignmentRef + * }, + * failure: function(form, action) { + * Ext.Msg.alert("Load failed", action.result.errorMessage); + * } + * }); + * + * a **success response** packet may look like this: + * + * { + * success: true, + * data: { + * clientName: "Fred. Olsen Lines", + * portOfLoading: "FXT", + * portOfDischarge: "OSL" + * } + * } + * + * while a **failure response** packet may look like this: + * + * { + * success: false, + * errorMessage: "Consignment reference not found" + * } + * + * Other data may be placed into the response for processing the {@link Ext.form.Basic Form}'s callback or event handler + * methods. The object decoded from this JSON is available in the {@link Ext.form.action.Action#result result} property. + */ +Ext.define('Ext.form.action.Load', { + extend: 'Ext.form.action.Action', + requires: [ + 'Ext.data.Connection' + ], + alternateClassName: 'Ext.form.Action.Load', + alias: 'formaction.load', + type: 'load', + /** + * @private + */ + run: function() { + Ext.Ajax.request(Ext.apply(this.createCallback(), { + method: this.getMethod(), + url: this.getUrl(), + headers: this.headers, + params: this.getParams() + })); + }, + /** + * @private + */ + onSuccess: function(response) { + var result = this.processResponse(response), + form = this.form, + formActive = form && !form.destroying && !form.destroyed; + if (result === true || !result.success || !result.data) { + this.failureType = Ext.form.action.Action.LOAD_FAILURE; + if (formActive) { + form.afterAction(this, false); + } + return; + } + if (formActive) { + form.clearInvalid(); + form.setValues(result.data); + form.afterAction(this, true); + } + }, + /** + * @private + */ + handleResponse: function(response) { + var reader = this.form.reader, + rs, data; + if (reader) { + rs = reader.read(response); + data = rs.records && rs.records[0] ? rs.records[0].data : null; + return { + success: rs.success, + data: data + }; + } + return Ext.decode(response.responseText); + } +}); + +/** + * A class which handles submission of data from {@link Ext.form.Basic Form}s and processes the returned response. + * + * Instances of this class are only created by a {@link Ext.form.Basic Form} when + * {@link Ext.form.Basic#submit submit}ting. + * + * # Response Packet Criteria + * + * A response packet may contain: + * + * - **`success`** property : Boolean - required. + * + * - **`errors`** property : Object - optional, contains error messages for invalid fields. + * + * # JSON Packets + * + * By default, response packets are assumed to be JSON, so a typical response packet may look like this: + * + * { + * success: false, + * errors: { + * clientCode: "Client not found", + * portOfLoading: "This field must not be null" + * } + * } + * + * Other data may be placed into the response for processing by the {@link Ext.form.Basic}'s callback or event handler + * methods. The object decoded from this JSON is available in the {@link Ext.form.action.Action#result result} property. + * + * Alternatively, if an {@link Ext.form.Basic#errorReader errorReader} is specified as an + * {@link Ext.data.reader.Xml XmlReader}: + * + * errorReader: new Ext.data.reader.Xml({ + * record : 'field', + * success: '@success' + * }, [ + * 'id', 'msg' + * ] + * ) + * + * then the results may be sent back in XML format: + * + * + * + * + * + * clientCode + * This is a test validation message from the server ]]> + * + * + * portOfLoading + * This is a test validation message from the server ]]> + * + * + * + * + * Other elements may be placed into the response XML for processing by the {@link Ext.form.Basic}'s callback or event + * handler methods. The XML document is available in the {@link Ext.form.Basic#errorReader errorReader}'s + * {@link Ext.data.reader.Xml#xmlData xmlData} property. + */ +Ext.define('Ext.form.action.Submit', { + extend: 'Ext.form.action.Action', + alternateClassName: 'Ext.form.Action.Submit', + alias: 'formaction.submit', + type: 'submit', + /** + * @cfg {Boolean} [clientValidation=true] + * Determines whether a Form's fields are validated in a final call to {@link Ext.form.Basic#isValid isValid} prior + * to submission. Pass false in the Form's submit options to prevent this. + */ + run: function() { + var me = this, + form = me.form; + if (me.clientValidation === false || form.isValid()) { + me.doSubmit(); + } else { + // client validation failed + me.failureType = Ext.form.action.Action.CLIENT_INVALID; + form.afterAction(me, false); + } + }, + /** + * @private + * Performs the submit of the form data. + */ + doSubmit: function() { + var me = this, + ajaxOptions = Ext.apply(me.createCallback(), { + url: me.getUrl(), + method: me.getMethod(), + headers: me.headers + }), + form = me.form, + jsonSubmit = me.jsonSubmit || form.jsonSubmit, + paramsProp = jsonSubmit ? 'jsonData' : 'params', + formInfo; + // For uploads we need to create an actual form that contains the file upload fields, + // and pass that to the ajax call so it can do its iframe-based submit method. + if (form.hasUpload()) { + formInfo = me.buildForm(); + ajaxOptions.form = formInfo.formEl; + ajaxOptions.isUpload = true; + } else { + ajaxOptions[paramsProp] = me.getParams(jsonSubmit); + } + Ext.Ajax.request(ajaxOptions); + if (formInfo) { + me.cleanup(formInfo); + } + }, + cleanup: function(formInfo) { + var formEl = formInfo.formEl, + uploadEls = formInfo.uploadEls, + uploadFields = formInfo.uploadFields, + len = uploadFields.length, + i, field; + for (i = 0; i < len; ++i) { + field = uploadFields[i]; + if (!field.clearOnSubmit) { + field.restoreInput(uploadEls[i]); + } + } + if (formEl) { + Ext.removeNode(formEl); + } + }, + /** + * @private + * Builds the full set of parameters from the field values plus any additional configured params. + */ + getParams: function(useModelValues) { + var falseVal = false, + configParams = this.callParent(), + fieldParams = this.form.getValues(falseVal, falseVal, this.submitEmptyText !== falseVal, useModelValues, /*isSubmitting*/ + true); + return Ext.apply({}, fieldParams, configParams); + }, + /** + * @private + * Builds a form element containing fields corresponding to all the parameters to be + * submitted (everything returned by {@link #getParams}. + * + * NOTE: the form element is automatically added to the DOM, so any code that uses + * it must remove it from the DOM after finishing with it. + * + * @return {HTMLElement} + */ + buildForm: function() { + var me = this, + fieldsSpec = [], + formSpec, formEl, + basicForm = me.form, + params = me.getParams(), + uploadFields = [], + uploadEls = [], + fields = basicForm.getFields().items, + i, + len = fields.length, + field, key, value, v, vLen, el; + for (i = 0; i < len; ++i) { + field = fields[i]; + if (field.isFileUpload()) { + uploadFields.push(field); + } + } + for (key in params) { + if (params.hasOwnProperty(key)) { + value = params[key]; + if (Ext.isArray(value)) { + vLen = value.length; + for (v = 0; v < vLen; v++) { + fieldsSpec.push(me.getFieldConfig(key, value[v])); + } + } else { + fieldsSpec.push(me.getFieldConfig(key, value)); + } + } + } + formSpec = { + tag: 'form', + role: 'presentation', + action: me.getUrl(), + method: me.getMethod(), + target: me.target ? (Ext.isString(me.target) ? me.target : Ext.fly(me.target).dom.name) : '_self', + style: 'display:none', + cn: fieldsSpec + }; + if (!formSpec.target) { + Ext.raise('Invalid form target.'); + } + // Set the proper encoding for file uploads + if (uploadFields.length) { + formSpec.encoding = formSpec.enctype = 'multipart/form-data'; + } + // Create the form + formEl = Ext.DomHelper.append(Ext.getBody(), formSpec); + // Special handling for file upload fields: since browser security measures prevent setting + // their values programatically, and prevent carrying their selected values over when cloning, + // we have to move the actual field instances out of their components and into the form. + len = uploadFields.length; + for (i = 0; i < len; ++i) { + el = uploadFields[i].extractFileInput(); + formEl.appendChild(el); + uploadEls.push(el); + } + return { + formEl: formEl, + uploadFields: uploadFields, + uploadEls: uploadEls + }; + }, + getFieldConfig: function(name, value) { + return { + tag: 'input', + type: 'hidden', + name: name, + value: Ext.String.htmlEncode(value) + }; + }, + /** + * @private + */ + onSuccess: function(response) { + var form = this.form, + formActive = form && !form.destroying && !form.destroyed, + success = true, + result = this.processResponse(response); + if (result !== true && !result.success) { + if (result.errors && formActive) { + form.markInvalid(result.errors); + } + this.failureType = Ext.form.action.Action.SERVER_INVALID; + success = false; + } + if (formActive) { + form.afterAction(this, success); + } + }, + /** + * @private + */ + handleResponse: function(response) { + var form = this.form, + errorReader = form.errorReader, + rs, errors, i, len, records, result; + if (errorReader) { + rs = errorReader.read(response); + records = rs.records; + errors = []; + if (records) { + for (i = 0 , len = records.length; i < len; i++) { + errors[i] = records[i].data; + } + } + if (errors.length < 1) { + errors = null; + } + result = { + success: rs.success, + errors: errors + }; + } else { + try { + result = Ext.decode(response.responseText); + } catch (e) { + result = { + success: false, + errors: [] + }; + } + } + return result; + } +}); + +/** + * A class which handles submission of data from {@link Ext.form.Basic Form}s using a standard `` element submit. + * It does not handle the response from the submit. + * + * If validation of the form fields fails, the Form's afterAction method will be called. Otherwise, afterAction will not + * be called. + * + * Instances of this class are only created by a {@link Ext.form.Basic Form} when + * {@link Ext.form.Basic#submit submit}ting, when the form's {@link Ext.form.Basic#standardSubmit} config option is true. + */ +Ext.define('Ext.form.action.StandardSubmit', { + extend: 'Ext.form.action.Submit', + alias: 'formaction.standardsubmit', + /** + * @cfg {String} target + * Optional target attribute to be used for the form when submitting. + * + * Defaults to the current window/frame. + */ + /** + * @private + * Perform the form submit. Creates and submits a temporary form element containing an input element for each + * field value returned by {@link Ext.form.Basic#getValues}, plus any configured {@link #params params} or + * {@link Ext.form.Basic#baseParams baseParams}. + */ + doSubmit: function() { + var formInfo = this.buildForm(); + formInfo.formEl.submit(); + this.cleanup(formInfo); + } +}); + +/** + * A subclass of Ext.dd.DragTracker which handles dragging any Component. + * + * This is configured with a Component to be made draggable, and a config object for the {@link Ext.dd.DragTracker} + * class. + * + * A {@link #delegate} may be provided which may be either the element to use as the mousedown target or a + * CSS selector to activate multiple mousedown targets. + * + * When the Component begins to be dragged, its `beginDrag` method will be called if implemented. + * + * When the drag ends, its `endDrag` method will be called if implemented. + */ +Ext.define('Ext.util.ComponentDragger', { + extend: 'Ext.dd.DragTracker', + /** + * @cfg {Boolean} constrain + * Specify as `true` to constrain the Component to within the bounds of the {@link #constrainTo} region. + */ + /** + * @cfg {String/Ext.dom.Element} delegate + * A CSS selector which identifies child elements within the Component's encapsulating + * Element which are the drag handles. This limits dragging to only begin when the matching elements are + * mousedowned. + * + * This may also be a specific child element within the Component's encapsulating element to use as the drag handle. + */ + /** + * @cfg {Boolean} constrainDelegate + * Specify as `true` to constrain the drag handles within the {@link #constrainTo} region. + */ + /** + * @cfg {Boolean} [liveDrag=false] + * @member Ext.Component + * True to drag the component itself. Else a lightweight version of the component + * will be shown (_using the component's ghost() method_). + * + * **Note:** This config is only relevant when used with dragging implemented via + * {@link Ext.util.ComponentDragger}. + */ + autoStart: 500, + /** + * Creates new ComponentDragger. + * @param {Object} comp The Component to provide dragging for. + * @param {Object} [config] Config object + */ + constructor: function(comp, config) { + this.comp = comp; + this.initialConstrainTo = config.constrainTo; + this.callParent([ + config + ]); + }, + onStart: function(e) { + var me = this, + comp = me.comp; + // ComponentDragger is always dragging the component. + // The superclass uses the delegated handle as the + // drag target and the target's start region. + me.dragTarget = me.el; + me.startRegion = me.el.getRegion(); + // Cache the start [X, Y] array + me.startPosition = comp.getXY(); + // If client Component has a ghost method to show a lightweight version of itself + // then use that as a drag proxy unless configured to liveDrag. + if (comp.ghost && !comp.liveDrag) { + me.proxy = comp.ghost(); + } + // Set the constrainTo Region before we start dragging. + if (me.constrain || me.constrainDelegate) { + me.constrainTo = me.calculateConstrainRegion(); + } + if (comp.beginDrag) { + comp.beginDrag(); + } + // We should cover all iframes to avoid them stealing our current drag event + Ext.dom.Element.maskIframes(); + }, + calculateConstrainRegion: function() { + var me = this, + comp = me.comp, + constrainTo = me.initialConstrainTo || me.comp.el.dom.parentNode, + constraintInsets = comp.constraintInsets, + constrainEl, delegateRegion, elRegion, + dragEl = me.proxy ? me.proxy.el : comp.el, + shadow = dragEl.shadow, + shadowSize = (shadow && !me.constrainDelegate && comp.constrainShadow && !shadow.disabled) ? shadow.getShadowSize() : 0; + // The configured constrainTo might be a Region or an element + if (!(constrainTo instanceof Ext.util.Region)) { + constrainEl = Ext.fly(constrainTo); + // draggable components are constrained to the area inside the borders of + // their floatParent, but not inside the padding + constrainTo = constrainEl.getConstrainRegion(); + } else { + // Create a clone so we don't modify the original + constrainTo = constrainTo.copy(); + } + // Apply constraintInsets + if (constraintInsets) { + constraintInsets = Ext.isObject(constraintInsets) ? constraintInsets : Ext.Element.parseBox(constraintInsets); + constrainTo.adjust(constraintInsets.top, constraintInsets.right, constraintInsets.bottom, constraintInsets.left); + } + // Reduce the constrain region to allow for shadow + if (shadowSize) { + constrainTo.adjust(shadowSize[0], -shadowSize[1], -shadowSize[2], shadowSize[3]); + } + // If they only want to constrain the *delegate* to within the constrain region, + // adjust the region to be larger based on the insets of the delegate from the outer + // edges of the Component. + if (me.constrainDelegate) { + delegateRegion = Ext.fly(me.handle).getRegion(); + elRegion = dragEl.getRegion(); + constrainTo.adjust(elRegion.top - delegateRegion.top, elRegion.right - delegateRegion.right, elRegion.bottom - delegateRegion.bottom, elRegion.left - delegateRegion.left); + } + return constrainTo; + }, + // Move either the ghost Component or the target Component to its new position on drag + onDrag: function(e) { + var me = this, + comp = (me.proxy && !me.comp.liveDrag) ? me.proxy : me.comp, + offset = me.getOffset(me.constrain || me.constrainDelegate ? 'dragTarget' : null); + comp.setPagePosition(me.startPosition[0] + offset[0], me.startPosition[1] + offset[1]); + }, + onEnd: function(e) { + var comp = this.comp; + if (comp.destroyed || comp.destroying) { + return; + } + if (this.proxy && !comp.liveDrag) { + comp.unghost(); + } + if (comp.endDrag) { + comp.endDrag(); + } + // We should uncover all iframes + Ext.dom.Element.unmaskIframes(); + } +}); + +/** + * A specialized panel intended for use as an application window. Windows are floated, {@link #resizable}, and + * {@link #cfg-draggable} by default. Windows can be {@link #maximizable maximized} to fill the viewport, restored to + * their prior size, and can be {@link #method-minimize}d. + * + * Windows can also be linked to a {@link Ext.ZIndexManager} or managed by the {@link Ext.WindowManager} to provide + * grouping, activation, to front, to back and other application-specific behavior. + * + * By default, Windows will be rendered to document.body. To {@link #constrain} a Window to another element specify + * {@link Ext.Component#renderTo renderTo}. + * + * **As with all {@link Ext.container.Container Container}s, it is important to consider how you want the Window to size + * and arrange any child Components. Choose an appropriate {@link #layout} configuration which lays out child Components + * in the required manner.** + * + * @example + * Ext.create('Ext.window.Window', { + * title: 'Hello', + * height: 200, + * width: 400, + * layout: 'fit', + * items: { // Let's put an empty grid in just to illustrate fit layout + * xtype: 'grid', + * border: false, + * columns: [{header: 'World'}], // One header just for show. There's no data, + * store: Ext.create('Ext.data.ArrayStore', {}) // A dummy empty data store + * } + * }).show(); + */ +Ext.define('Ext.window.Window', { + extend: 'Ext.panel.Panel', + alternateClassName: 'Ext.Window', + requires: [ + 'Ext.util.ComponentDragger', + 'Ext.util.Region' + ], + alias: 'widget.window', + /** + * @cfg {Number} x + * The X position of the left edge of the window on initial showing. Defaults to centering the Window within the + * width of the Window's container {@link Ext.dom.Element Element} (The Element that the Window is rendered to). + */ + /** + * @cfg {Number} y + * The Y position of the top edge of the window on initial showing. Defaults to centering the Window within the + * height of the Window's container {@link Ext.dom.Element Element} (The Element that the Window is rendered to). + */ + /** + * @cfg {String/Ext.dom.Element/Ext.Component/Boolean} [animateTarget=null] + * Id, Component element, or Component from which the window should animate when + * shown or hidden. + * + * You may also pass true to have the Window animate when maximizing and restoring + * using the maximize / restore tools created via the {@link #maximizable} config. + * + * var btn, win; + * + * btn = Ext.create({ + * xtype: 'button', + * renderTo: Ext.getBody(), + * text: 'Show Window', + * handler: function() { + * win.show(); + * } + * }); + * + * win = Ext.create({ + * xtype: 'window', + * title: 'Animate from the Show Window Button', + * height: 300, + * width: 400, + * modal: true, + * closeAction: 'hide', + * animateTarget: btn + * // or btn.getId() + * // or btn.getEl() + * // or true (when maximizable is true) + * }); + */ + /** + * @cfg {Boolean/Function} ghost + * Set to false to disable the ghost panel during dragging the window. + * Do note that you should not set this to true, by default it is a function. + */ + /** + * @cfg {String/Number/Ext.Component} defaultFocus + * Specifies a Component to receive focus when this Window is focused. + * + * If a String is provided, the Component will be resolved using the {@link #down} method which uses {@link Ext.ComponentQuery}. + * If the string begins with an alphanumeric value, it will first attempt to find the Component based on the {@link Ext.Component#id} or {@link Ext.Component#itemId}. + * If a matching component is not found via id, then an attempt to do a query to find a matching component. + * + * An example of finding the Component with an id/itemId: + * + * Ext.create('Ext.window.Window', { + * autoShow : true, + * width : 300, + * title : 'Login', + * defaultFocus : 'username', + * items : [ + * { + * xtype : 'textfield', + * fieldLabel : 'Username', + * itemId : 'username', + * name : 'username' + * }, + * { + * xtype : 'textfield', + * inputType : 'password', + * fieldLabel : 'Password', + * itemId : 'password', + * name : 'password' + * } + * ] + * }); + * + * If a Number is provided, this will resolve an {@link Ext.button.Button} at that index. This is very useful if + * the window has buttons in the {@link #buttons} config and you want to provide default focus to one of them. + * + * An example of this would be: + * + * Ext.create('Ext.window.Window', { + * autoShow : true, + * width : 300, + * title : 'Login', + * defaultFocus : 1, + * items : [ + * { + * xtype : 'textfield', + * fieldLabel : 'Username', + * name : 'username' + * }, + * { + * xtype : 'textfield', + * inputType : 'password', + * fieldLabel : 'Password', + * name : 'password' + * } + * ], + * buttons : [ + * { + * text : 'Cancel' + * }, + * { + * text : 'Login' + * } + * ] + * }); + * + * In summary, defaultFocus may be one of: + * + * - The index of a footer Button. + * - The id or {@link Ext.Component#itemId} of a descendant Component. + * - A {@link Ext.ComponentQuery query} to find a {@link Ext.Component}. + * - A descendant {@link Ext.Component}. + */ + /** + * @cfg {Function} onEsc + * Allows override of the built-in processing for the escape key. Default action is to close the Window (performing + * whatever action is specified in {@link #closeAction}. To prevent the Window closing when the escape key is + * pressed, specify this as {@link Ext#emptyFn Ext.emptyFn}. + */ + /** + * @cfg {Boolean} [collapsed=false] + * True to render the window collapsed, false to render it expanded. Note that if {@link #expandOnShow} + * is true (the default) it will override the `collapsed` config and the window will always be + * expanded when shown. + */ + /** + * @cfg {Boolean} [maximized=false] + * True to initially display the window in a maximized state. + */ + /** + * @cfg {Boolean} [hideShadowOnDeactivate=false] + * True to hide this Window's shadow when another floating item in the same z-index stack is activated. + */ + /** + * @cfg {String} baseCls + * The base CSS class to apply to this panel's element. + */ + baseCls: Ext.baseCSSPrefix + 'window', + /** + * @cfg {Boolean/Object} resizable + * Specify as `true` to allow user resizing at each edge and corner of the window, false to disable resizing. + * + * This may also be specified as a config object to Ext.resizer.Resizer + */ + resizable: true, + /** + * @cfg {Boolean} draggable + * True to allow the window to be dragged by the header bar, false to disable dragging. Note that + * by default the window will be centered in the viewport, so if dragging is disabled the window may need to be + * positioned programmatically after render (e.g., `myWindow.setPosition(100, 100);`). + */ + draggable: true, + /** + * @cfg {Boolean} constrain + * True to constrain the window within its containing element, false to allow it to fall outside of its containing + * element. By default the window will be rendered to `document.body`. To render and constrain the window within + * another element specify {@link #renderTo}. Optionally the header only can be constrained + * using {@link #constrainHeader}. + */ + constrain: false, + /** + * @cfg {Boolean} constrainHeader + * True to constrain the window header within its containing element (allowing the window body to fall outside of + * its containing element) or false to allow the header to fall outside its containing element. + * Optionally the entire window can be constrained using {@link #constrain}. + */ + constrainHeader: false, + /** + * @cfg simpleDrag + * @hide + */ + /** + * @cfg {Boolean} plain + * True to render the window body with a transparent background so that it will blend into the framing elements, + * false to add a lighter background color to visually highlight the body element and separate it more distinctly + * from the surrounding frame. + */ + plain: false, + /** + * @cfg {Boolean} minimizable + * True to display the 'minimize' tool button and allow the user to minimize the window, false to hide the button + * and disallow minimizing the window. Note that this button provides no implementation -- the + * behavior of minimizing a window is implementation-specific, so the minimize event must be handled and a custom + * minimize behavior implemented for this option to be useful. + */ + minimizable: false, + /** + * @cfg {Boolean} maximizable + * True to display the 'maximize' tool button and allow the user to maximize the window, false to hide the button + * and disallow maximizing the window. Note that when a window is maximized, the tool button + * will automatically change to a 'restore' button with the appropriate behavior already built-in that will restore + * the window to its previous size. + */ + maximizable: false, + /** + * @cfg minHeight + * @inheritdoc + */ + minHeight: 50, + /** + * @cfg minWidth + * @inheritdoc + */ + minWidth: 50, + /** + * @cfg {Boolean} expandOnShow + * True to always expand the window when it is displayed, false to keep it in its current state (which may be + * {@link #collapsed}) when displayed. + */ + expandOnShow: true, + /** + * @cfg collapsible + * @inheritdoc + */ + collapsible: false, + /** + * @cfg {Boolean} closable + * True to display the 'close' tool button and allow the user to close the window, false to hide the button and + * disallow closing the window. + * + * By default, when close is requested by either clicking the close button in the header or pressing ESC when the + * Window has focus, the {@link #method-close} method will be called. This will _{@link Ext.Component#method-destroy destroy}_ the + * Window and its content meaning that it may not be reused. + * + * To make closing a Window _hide_ the Window so that it may be reused, set {@link #closeAction} to 'hide'. + */ + closable: true, + /** + * @cfg {Boolean} monitorResize + * `true` to listen to the viewport resize event and perform any layout updating if necessary. + * This is useful if using sizes as percentages for the window. + */ + /** + * @cfg {Boolean} hidden + * Render this Window hidden. If `true`, the {@link #method-hide} method will be called internally. + */ + hidden: true, + /** + * @cfg autoRender + * @inheritdoc + * Windows render to the body on first show. + */ + autoRender: true, + /** + * @cfg hideMode + * @inheritdoc + * Windows hide using offsets in order to preserve the scroll positions of their descendants. You may review + * other configuration options here: {@link Ext.Component#hideMode}. + */ + hideMode: 'offsets', + /** + * @cfg floating + * @inheritdoc Ext.Component#cfg!floating + */ + floating: true, + /** + * @cfg alignOnScroll + * @inheritdoc + */ + alignOnScroll: false, + /** + * @cfg stateEvents + * @inheritdoc Ext.state.Stateful#cfg-stateEvents + * @localdoc By default the following stateEvents are added: + * + * - {@link #event-resize} - _(added by Ext.Component)_ + * - {@link #event-collapse} - _(added by Ext.panel.Panel)_ + * - {@link #event-expand} - _(added by Ext.panel.Panel)_ + * - {@link #event-maximize} + * - {@link #event-restore} + * - {@link #event-resize} + * - {@link #event-dragend} + */ + itemCls: Ext.baseCSSPrefix + 'window-item', + /** + * @cfg overlapHeader + * @inheritdoc + */ + overlapHeader: true, + ignoreHeaderBorderManagement: true, + // Flag to Renderable to always look up the framing styles for this Component + alwaysFramed: true, + // Buffer this so we don't recreate the same object + isRootCfg: { + isRoot: true + }, + /** + * @property {Boolean} isWindow + * `true` in this class to identify an object as an instantiated Window, or subclass thereof. + */ + isWindow: true, + /** + * @property ariaRole + * @inheritdoc + */ + ariaRole: 'dialog', + /** + * @property focusable + * @inheritdoc + */ + focusable: true, + /** + * @cfg tabGuard + * @inheritdoc + */ + tabGuard: true, + /** + * @cfg closeToolText + * @inheritdoc + */ + closeToolText: 'Close dialog', + /** + * @cfg keyMap + * @inheritdoc + */ + keyMap: { + scope: 'this', + ESC: 'onEsc' + }, + /** + * @cfg {String} maskClickAction + * The method to call when the window's modal mask is clicked or tapped: + * + * - **`'{@link #method-focus}'`** : + * + * The default. Focus the window, which will then pass focus into its {@link #cfg-defaultFocus} delegate. + * + * - **`'{@link #method-destroy}'`** : + * + * Remove the window from the DOM and {@link Ext.Component#method-destroy destroy} it and all descendant + * Components. The window will **not** be available to be redisplayed via the {@link #method-show} method. + * + * - **`'{@link #method-hide}'`** : + * + * {@link #method-hide} the window by setting visibility to hidden and applying negative offsets. The window will be + * available to be redisplayed via the {@link #method-show} method. + * @since 6.2.0 + */ + maskClickAction: 'focus', + /** + * @event activate + * Fires after the window has been visually activated via {@link #setActive}. + * @param {Ext.window.Window} this + */ + /** + * @event deactivate + * Fires after the window has been visually deactivated via {@link #setActive}. + * @param {Ext.window.Window} this + */ + /** + * @event maskclick + * Fires when this Window's modal mask is clicked or tapped. Returning `false` from + * a handler will veto the subsequent preocessing of the {@link #cfg-maskClickAction}.. + * @param {Ext.window.Window} this + */ + /** + * @event resize + * Fires after the window has been resized. + * @param {Ext.window.Window} this + * @param {Number} width The window's new width + * @param {Number} height The window's new height + */ + /** + * @event maximize + * Fires after the window has been maximized. + * @param {Ext.window.Window} this + */ + /** + * @event minimize + * Fires after the window has been minimized. + * @param {Ext.window.Window} this + */ + /** + * @event restore + * Fires after the window has been restored to its original size after being maximized. + * @param {Ext.window.Window} this + */ + disableCloseToolFocus: true, + /** + * @private + */ + initComponent: function() { + var me = this; + // Explicitly set frame to false, since alwaysFramed is + // true, we only want to lookup framing in a specific instance + me.frame = false; + me.callParent(); + if (me.plain) { + me.addClsWithUI('plain'); + } + me.addStateEvents([ + 'maximize', + 'restore', + 'resize', + 'dragend' + ]); + }, + getElConfig: function() { + var me = this, + elConfig; + elConfig = me.callParent(); + elConfig.tabIndex = -1; + return elConfig; + }, + /** + * @protected + * Returns the focus holder element associated with this Window. + * By default, this is the Window's element; this can be overridden + * by setting {@link #defaultFocus} property. + * + * @return {Ext.dom.Element/Ext.Component} the focus holding element or Component. + */ + getFocusEl: function() { + return this.getDefaultFocus() || this.el; + }, + // State Management + /** + * @private + */ + getState: function() { + var me = this, + state = me.callParent() || {}, + maximized = !!me.maximized, + ghostBox = me.ghostBox, + pos; + state.maximized = maximized; + if (maximized) { + pos = me.restorePos; + } else if (ghostBox) { + // If we're animating a show, it will be from offscreen, so + // grab the position from the final box + pos = [ + ghostBox.x, + ghostBox.y + ]; + } else { + pos = me.getPosition(true); + } + Ext.apply(state, { + size: maximized ? me.restoreSize : me.getSize(), + pos: pos + }); + return state; + }, + applyState: function(state) { + var me = this; + if (state) { + me.maximized = state.maximized; + if (me.maximized) { + me.hasSavedRestore = true; + me.restoreSize = state.size; + me.restorePos = state.pos; + } else { + Ext.apply(me, { + width: state.size.width, + height: state.size.height, + x: state.pos[0], + y: state.pos[1] + }); + } + } + }, + onRender: function(ct, position) { + var me = this; + me.callParent(arguments); + // Single clicking a header will focus the defaultFocus child + if (me.header) { + me.header.on({ + scope: me, + click: me.onHeaderClick + }); + } + // Double clicking a header will toggleMaximize + if (me.maximizable) { + me.header.on({ + scope: me, + dblclick: me.toggleMaximize + }); + } + }, + afterRender: function() { + var me = this, + header = me.header; + // Initialize + if (me.maximized) { + me.maximized = false; + me.maximize(null, true); + if (header) { + header.removeCls(header.indicateDragCls); + } + } + me.callParent(); + me.initTabGuards(); + }, + /** + * @private + */ + onEsc: function(e) { + if (this.closable) { + e.stopEvent(); + this.close(); + return false; + } + }, + doDestroy: function() { + var me = this; + if (me.rendered) { + Ext.un('resize', me.onWindowResize, me); + delete me.animateTarget; + me.hide(); + } + me.callParent(); + }, + /** + * @private + * Contribute class-specific tools to the header. + * + * Called by Panel's initTools at initialization time. + * + * Implementations should jst add new tool config objects to `this.tools` + */ + addTools: function() { + var me = this, + tools = []; + // Call Panel's addTools + me.callParent(); + if (me.minimizable) { + tools.push({ + type: 'minimize', + handler: 'minimize', + scope: me + }); + } + if (me.maximizable) { + tools.push({ + type: 'maximize', + handler: 'toggleMaximize', + scope: me + }); + } + if (tools.length) { + me.addTool(tools); + } + }, + addTool: function(tools) { + var me = this; + me.callParent([ + tools + ]); + if (me.rendered && me.tabGuard) { + me.initTabGuards(); + } + }, + add: function() { + var me = this, + ret; + ret = me.callParent(arguments); + if (me.rendered && me.tabGuard) { + me.initTabGuards(); + } + return ret; + }, + remove: function() { + var me = this, + ret; + ret = me.callParent(arguments); + if (me.rendered && me.tabGuard) { + me.initTabGuards(); + } + return ret; + }, + addDocked: function() { + var me = this, + ret; + ret = me.callParent(arguments); + if (me.rendered && me.tabGuard) { + me.initTabGuards(); + } + return ret; + }, + removeDocked: function() { + var me = this, + ret; + ret = me.callParent(arguments); + if (me.rendered && me.tabGuard) { + me.initTabGuards(); + } + return ret; + }, + onShow: function() { + var me = this; + me.callParent(arguments); + if (me.expandOnShow) { + me.expand(false); + } + me.syncMonitorWindowResize(); + if (me.rendered && me.tabGuard) { + me.initTabGuards(); + } + }, + /** + * @private + */ + doClose: function() { + var me = this; + // Being called as callback after going through the hide call below + if (me.hidden) { + me.fireEvent('close', me); + // This method can be called from hide() which in turn can be called + // from destroy() + if (me.closeAction === 'destroy' && !me.destroying && !me.destroyed) { + me.destroy(); + } + } else { + // close after hiding + me.hide(me.animateTarget, me.doClose, me); + } + }, + /** + * @private + */ + afterHide: function() { + var me = this; + // No longer subscribe to resizing now that we're hidden + me.syncMonitorWindowResize(); + // Perform superclass's afterHide tasks. + me.callParent(arguments); + // Hide may have destroyed a Window. + if (!me.destroyed && me.rendered && me.tabGuard) { + me.initTabGuards(); + } + }, + /** + * @private + */ + onWindowResize: function() { + var me = this, + sizeModel; + // This is called on a timer. Window may have been destroyed in the interval. + if (!me.destroyed) { + if (me.maximized) { + me.fitContainer(); + } else { + sizeModel = me.getSizeModel(); + if (sizeModel.width.natural || sizeModel.height.natural) { + me.updateLayout(); + } + me.doConstrain(); + } + } + }, + /** + * Placeholder method for minimizing the window. By default, this method simply fires the {@link #event-minimize} event + * since the behavior of minimizing a window is application-specific. To implement custom minimize behavior, either + * the minimize event can be handled or this method can be overridden. + * @return {Ext.window.Window} this + */ + minimize: function() { + this.fireEvent('minimize', this); + return this; + }, + resumeHeaderLayout: function(changed) { + this.header.resumeLayouts(changed ? this.isRootCfg : null); + }, + afterCollapse: function() { + var me = this, + header = me.header, + tools = me.tools; + if (header && me.maximizable) { + header.suspendLayouts(); + tools.maximize.hide(); + this.resumeHeaderLayout(true); + } + if (me.resizer) { + me.resizer.disable(); + } + me.callParent(arguments); + }, + afterExpand: function() { + var me = this, + header = me.header, + tools = me.tools, + changed; + if (header) { + header.suspendLayouts(); + if (me.maximizable) { + tools.maximize.show(); + changed = true; + } + this.resumeHeaderLayout(changed); + } + if (me.resizer) { + me.resizer.enable(); + } + me.callParent(arguments); + }, + /** + * Fits the window within its current container and automatically replaces the {@link #maximizable 'maximize' tool + * button} with the 'restore' tool button. Also see {@link #toggleMaximize}. + * @param {Boolean} [animate=false] Pass `true` to animate this Window to full size. + * @param {Boolean} initial (private) + * @return {Ext.window.Window} this + */ + maximize: function(animate, initial) { + var me = this, + header = me.header, + tools = me.tools, + width = me.width, + height = me.height, + restore, changed; + if (!me.maximized && !me.maximizing) { + me.maximizing = true; + me.expand(false); + if (!me.hasSavedRestore) { + restore = me.restoreSize = { + width: width ? width : null, + height: height ? height : null + }; + // If we're not positioned yet, default back to 0,0 + if (initial) { + me.restorePos = [ + me.x || 0, + me.y || 0 + ]; + } else { + me.restorePos = me.getPosition(); + } + } + // Manipulate visibility of header tools if there is a header + if (header) { + header.suspendLayouts(); + if (tools.maximize) { + tools.maximize.setType('restore'); + } + if (me.collapseTool) { + me.collapseTool.hide(); + changed = true; + } + me.resumeHeaderLayout(changed); + } + me.el.disableShadow(); + if (me.dd) { + me.dd.disable(); + if (header) { + header.removeCls(header.indicateDragCls); + } + } + if (me.resizer) { + me.resizer.disable(); + } + me.el.addCls(Ext.baseCSSPrefix + 'window-maximized'); + me.container.addCls(Ext.baseCSSPrefix + 'window-maximized-ct'); + me.syncMonitorWindowResize(); + me.fitContainer(animate = (animate || !!me.animateTarget) ? { + callback: function() { + me.maximizing = false; + me.maximized = true; + if (!initial) { + me.fireEvent('maximize', me); + } + } + } : null); + if (!animate) { + me.maximizing = false; + me.maximized = true; + if (!initial) { + me.fireEvent('maximize', me); + } + } + } + return me; + }, + /** + * Restores a {@link #maximizable maximized} window back to its original size and position prior to being maximized + * and also replaces the 'restore' tool button with the 'maximize' tool button. Also see {@link #toggleMaximize}. + * @param {Boolean} [animate=false] Pass `true` to animate the restore. + * @return {Ext.window.Window} this + */ + restore: function(animate) { + var me = this, + tools = me.tools, + header = me.header, + newBox = me.restoreSize, + changed; + if (me.maximized) { + me.hasSavedRestore = null; + me.removeCls(Ext.baseCSSPrefix + 'window-maximized'); + // Manipulate visibility of header tools if there is a header + if (header) { + header.suspendLayouts(); + if (tools.maximize) { + tools.maximize.setType('maximize'); + } + if (me.collapseTool) { + me.collapseTool.show(); + changed = true; + } + me.resumeHeaderLayout(changed); + } + // Restore the position/sizing + newBox.x = me.restorePos[0]; + newBox.y = me.restorePos[1]; + me.setBox(newBox, animate = (animate || !!me.animateTarget) ? { + callback: function() { + me.el.enableShadow(null, true); + me.maximized = false; + me.fireEvent('restore', me); + } + } : null); + // Unset old position/sizing + me.restorePos = me.restoreSize = null; + // Allow users to drag and drop again + if (me.dd) { + me.dd.enable(); + if (header) { + header.addCls(header.indicateDragCls); + } + } + if (me.resizer) { + me.resizer.enable(); + } + me.container.removeCls(Ext.baseCSSPrefix + 'window-maximized-ct'); + me.syncMonitorWindowResize(); + if (!animate) { + me.el.enableShadow(null, true); + me.maximized = false; + me.fireEvent('restore', me); + } + } + return me; + }, + /** + * Synchronizes the presence of our listener for window resize events. This method + * should be called whenever this status might change. + * @private + */ + syncMonitorWindowResize: function() { + var me = this, + currentlyMonitoring = me._monitoringResize, + // all the states where we should be listening to window resize: + yes = me.monitorResize || me.constrain || me.constrainHeader || me.maximized, + // all the states where we veto this: + veto = me.hidden || me.destroying || me.destroyed; + if (yes && !veto) { + // we should be listening... + if (!currentlyMonitoring) { + // but we aren't, so set it up. + // Delay so that we jump over any Viewport resize activity + Ext.on('resize', me.onWindowResize, me, { + buffer: 1 + }); + me._monitoringResize = true; + } + } else if (currentlyMonitoring) { + // we should not be listening, but we are, so tear it down + Ext.un('resize', me.onWindowResize, me); + me._monitoringResize = false; + } + }, + /** + * A shortcut method for toggling between {@link #method-maximize} and {@link #method-restore} based on the current maximized + * state of the window. + * @return {Ext.window.Window} this + */ + toggleMaximize: function() { + return this[this.maximized ? 'restore' : 'maximize'](); + }, + createGhost: function() { + var ghost = this.callParent(arguments); + ghost.xtype = 'window'; + ghost.focusOnToFront = false; + return ghost; + }, + /** + * Gets the configured default focus item. If a {@link #defaultFocus} is set, it will + * receive focus when the Window's `focus` method is called, otherwise the + * Window itself will receive focus. + */ + getDefaultFocus: function() { + var me = this, + result, + defaultComp = me.defaultFocus, + selector; + if (defaultComp !== undefined) { + // Number is index of Button + if (Ext.isNumber(defaultComp)) { + result = me.query('button')[defaultComp]; + } + // String is ID or CQ selector + else if (Ext.isString(defaultComp)) { + selector = defaultComp; + // Try id/itemId match if selector begins with alphanumeric + // and is not compound xtype/id selector with # in the middle + // (https://sencha.jira.com/browse/EXTJS-14925) + if (Ext.validIdRe.test(selector)) { + result = me.down(Ext.makeIdSelector(selector)); + } + // If not found, use as selector + if (!result) { + result = me.down(selector); + } + } + // Otherwise, if it's got a focus method, use it + else if (defaultComp.focus) { + result = defaultComp; + } + } + return result; + }, + privates: { + // Override. Windows are always simple draggable, they do not use Ext.Panel.DDs + // The dd property in a Window is always a ComponentDragger + initDraggable: function() { + /** + * @property {Ext.util.ComponentDragger} dd + * If this Window is configured {@link #cfg-draggable}, this property will contain an instance of + * {@link Ext.util.ComponentDragger} (A subclass of {@link Ext.dd.DragTracker DragTracker}) which handles dragging + * the Window's DOM Element, and constraining according to the {@link #constrain} and {@link #constrainHeader} . + * + * This has implementations of `onBeforeStart`, `onDrag` and `onEnd` which perform the dragging action. If + * extra logic is needed at these points, use {@link Ext.Function#createInterceptor createInterceptor} or + * {@link Ext.Function#createSequence createSequence} to augment the existing implementations. + */ + this.initSimpleDraggable(); + }, + onHeaderClick: function(header, e) { + var delegate; + if (header.el.contains(e.getTarget())) { + delegate = this.getDefaultFocus(); + if (delegate) { + delegate.focus(); + } + } + }, + initResizable: function(resizable) { + var me = this; + me.callParent([ + resizable + ]); + if (me.maximized || me.maximizing) { + me.resizer.disable(); + } + }, + initSimpleDraggable: function() { + var me = this, + dd; + me.callParent(); + dd = me.dd; + if (dd && me.maximized || me.maximizing) { + dd.disable(); + } + }, + onTabGuardFocusEnter: function(e, target) { + var me = this, + el = me.el, + beforeGuard = me.tabGuardBeforeEl, + afterGuard = me.tabGuardAfterEl, + from = e.relatedTarget, + nodes, forward, nextFocus; + nodes = el.findTabbableElements({ + skipSelf: true + }); + // Tabbables might include two tab guards, so remove them + if (nodes[0] === beforeGuard.dom) { + nodes.shift(); + } + if (nodes[nodes.length - 1] === afterGuard.dom) { + nodes.pop(); + } + // Totally possible not to have anything tabbable within the window + // but we have to do something so focus back the window el. At least + // in that case the user will be able to press Escape key to close it. + if (nodes.length === 0) { + nextFocus = el; + } + // The window itself was focused, possibly by clicking or programmatically; + // but this time we do have something tabbable to choose from. + else if (from === el.dom) { + forward = target === beforeGuard.dom; + } + // Focus was within the window and is trying to escape; + // for topmost guard we need to bounce focus back to the last tabbable + // element in the window, and vice versa for the bottom guard. + else if (el.contains(from)) { + forward = !!e.forwardTab; + } else // It is entirely possible that focus was outside the window and + // the user tabbed into the window. In that case we forward the focus + // to the next available element in the natural tab order, i.e. the element + // after the topmost guard, or the element before the bottom guard. + { + forward = target === beforeGuard.dom; + } + nextFocus = nextFocus || (forward ? nodes[0] : nodes[nodes.length - 1]); + if (nextFocus) { + // If there is only one focusable node in the window, focusing it + // while we're in focusenter handler for the tab guard might cause + // race condition where the focusable node will be refocused first + // and then its original blur handler will kick in, removing focus + // styling erroneously. + Ext.fly(nextFocus).focus(nodes.length === 1 ? 1 : 0); + } + } + } +}); + +/** + * A mixin which allows a component to be configured and decorated with a label and/or error message as is + * common for form fields. This is used by e.g. Ext.form.field.Base and Ext.form.FieldContainer + * to let them be managed by the Field layout. + * + * NOTE: This mixin is mainly for internal library use and most users should not need to use it directly. It + * is more likely you will want to use one of the component classes that import this mixin, such as + * Ext.form.field.Base or Ext.form.FieldContainer. + * + * Use of this mixin does not make a component a field in the logical sense, meaning it does not provide any + * logic or state related to values or validation; that is handled by the related Ext.form.field.Field + * mixin. These two mixins may be used separately (for example Ext.form.FieldContainer is Labelable but not a + * Field), or in combination (for example Ext.form.field.Base implements both and has logic for connecting the + * two.) + * + * Component classes which use this mixin should use the Field layout + * or a derivation thereof to properly size and position the label and message according to the component config. + * They must also call the {@link #initLabelable} method during component initialization to ensure the mixin gets + * set up correctly. + */ +Ext.define("Ext.form.Labelable", { + extend: 'Ext.Mixin', + requires: [ + 'Ext.XTemplate', + 'Ext.overrides.dom.Element' + ], + isLabelable: true, + mixinConfig: { + id: 'labelable', + on: { + beforeRender: 'beforeLabelRender', + onRender: 'onLabelRender' + } + }, + config: { + childEls: [ + /** + * @property {Ext.dom.Element} labelEl + * The label Element for this component. Only available after the component has been rendered. + */ + 'labelEl', + /** + * @property {Ext.dom.Element} bodyEl + * The div Element wrapping the component's contents. Only available after the component has been rendered. + */ + 'bodyEl', + /** + * @property {Ext.dom.Element} errorEl + * The div Element that will contain the component's error message(s). Note that depending on the configured + * {@link #msgTarget}, this element may be hidden in favor of some other form of presentation, but will always + * be present in the DOM for use by assistive technologies. + */ + 'errorEl', + 'errorWrapEl', + 'ariaErrorEl', + 'ariaStatusEl', + 'ariaHelpEl', + 'labelTextEl' + ] + }, + /** + * @cfg {String/String[]/Ext.XTemplate} labelableRenderTpl + * The rendering template for the field decorations. Component classes using this mixin + * should include logic to use this as their {@link Ext.Component#renderTpl renderTpl}, + * and implement the {@link #getSubTplMarkup} method to generate the field body content. + * @private + */ + labelableRenderTpl: [ + '{beforeLabelTpl}', + '', + '{afterLabelTpl}', + '', + '', + '
', + '', + '
', + '
', + { + disableFormats: true + } + ], + /** + * @cfg {String/String[]/Ext.XTemplate} activeErrorsTpl + * The template used to format the Array of error messages passed to {@link #setActiveErrors} into a single HTML + * string. if the {@link #msgTarget} is title, it defaults to a list separated by new lines. Otherwise, it + * renders each message as an item in an unordered list. + */ + activeErrorsTpl: undefined, + htmlActiveErrorsTpl: [ + '', + '
    ', + '
  • {.}
  • ', + '
', + '
' + ], + plaintextActiveErrorsTpl: [ + '', + '\n{.}', + '' + ], + ariaActiveErrorsTpl: [ + '', + '{.}', + '' + ], + /** + * @property {Boolean} isFieldLabelable + * Flag denoting that this object is labelable as a field. Always true. + */ + isFieldLabelable: true, + /** + * @cfg {String} formItemCls + * A CSS class to be applied to the outermost element to denote that it is participating in the form field layout. + */ + formItemCls: Ext.baseCSSPrefix + 'form-item', + /** + * @cfg {String} labelCls + * The CSS class to be applied to the label element. This (single) CSS class is used to formulate the renderSelector + * and drives the field layout where it is concatenated with a hyphen ('-') and {@link #labelAlign}. To add + * additional classes, use {@link #labelClsExtra}. + */ + labelCls: Ext.baseCSSPrefix + 'form-item-label', + /** + * @private + */ + topLabelCls: Ext.baseCSSPrefix + 'form-item-label-top', + rightLabelCls: Ext.baseCSSPrefix + 'form-item-label-right', + labelInnerCls: Ext.baseCSSPrefix + 'form-item-label-inner', + labelTextCls: Ext.baseCSSPrefix + 'form-item-label-text', + topLabelSideErrorCls: Ext.baseCSSPrefix + 'form-item-label-top-side-error', + /** + * @cfg {String} labelClsExtra + * An optional string of one or more additional CSS classes to add to the label element. Defaults to empty. + */ + /** + * @cfg {String} errorMsgCls + * The CSS class to be applied to the error message element. + */ + errorMsgCls: Ext.baseCSSPrefix + 'form-error-msg', + errorWrapCls: Ext.baseCSSPrefix + 'form-error-wrap', + errorWrapSideCls: Ext.baseCSSPrefix + 'form-error-wrap-side', + errorWrapUnderCls: Ext.baseCSSPrefix + 'form-error-wrap-under', + errorWrapUnderSideLabelCls: Ext.baseCSSPrefix + 'form-error-wrap-under-side-label', + /** + * @cfg {String} baseBodyCls + * The CSS class to be applied to the body content element. + */ + baseBodyCls: Ext.baseCSSPrefix + 'form-item-body', + invalidIconCls: Ext.baseCSSPrefix + 'form-invalid-icon', + invalidUnderCls: Ext.baseCSSPrefix + 'form-invalid-under', + noLabelCls: Ext.baseCSSPrefix + 'form-item-no-label', + /** + * @cfg {String} fieldBodyCls + * An extra CSS class to be applied to the body content element in addition to {@link #baseBodyCls}. + */ + fieldBodyCls: '', + extraFieldBodyCls: '', + /** + * @cfg {String} invalidCls + * The CSS class to use when marking the component invalid. + */ + invalidCls: Ext.baseCSSPrefix + 'form-invalid', + /** + * @cfg {String} fieldLabel + * The label for the field. It gets appended with the {@link #labelSeparator}, and its position and sizing is + * determined by the {@link #labelAlign} and {@link #labelWidth} configs. + */ + fieldLabel: undefined, + /** + * @cfg {String} labelAlign + * Controls the position and alignment of the {@link #fieldLabel}. Valid values are: + * + * - "left" (the default) - The label is positioned to the left of the field, with its text aligned to the left. + * Its width is determined by the {@link #labelWidth} config. + * - "top" - The label is positioned above the field. + * - "right" - The label is positioned to the left of the field, with its text aligned to the right. + * Its width is determined by the {@link #labelWidth} config. + */ + labelAlign: 'left', + /** + * @cfg {Number} labelWidth + * The width of the {@link #fieldLabel} in pixels. Only applicable if {@link #labelAlign} + * is set to "left" or "right". + */ + labelWidth: 100, + /** + * @cfg {Number} labelPad + * The amount of space in pixels between the {@link #fieldLabel} and the field body. + * This defaults to `5` for compatibility with Ext JS 4, however, as of Ext JS 5 + * the space between the label and the body can optionally be determined by the theme + * using the {@link #$form-label-horizontal-spacing} (for side-aligned labels) and + * {@link #$form-label-vertical-spacing} (for top-aligned labels) SASS variables. + * In order for the stylesheet values as to take effect, you must use a labelPad value + * of `null`. + */ + labelPad: 5, + /** + * @cfg {String} labelSeparator + * Character(s) to be inserted at the end of the {@link #fieldLabel label text}. + * + * Set to empty string to hide the separator completely. + * @locale + */ + labelSeparator: ':', + /** + * @cfg {String} labelStyle + * A CSS style specification string to apply directly to this field's label. + */ + /** + * @cfg {Boolean} hideLabel + * Set to true to completely hide the label element ({@link #fieldLabel} and {@link #labelSeparator}). Also see + * {@link #hideEmptyLabel}, which controls whether space will be reserved for an empty fieldLabel. + */ + hideLabel: false, + /** + * @cfg {Boolean} hideEmptyLabel + * When set to true, the label element ({@link #fieldLabel} and {@link #labelSeparator}) will be automatically + * hidden if the {@link #fieldLabel} is empty. Setting this to false will cause the empty label element to be + * rendered and space to be reserved for it; this is useful if you want a field without a label to line up with + * other labeled fields in the same form. + * + * If you wish to unconditionall hide the label even if a non-empty fieldLabel is configured, then set the + * {@link #hideLabel} config to true. + */ + hideEmptyLabel: true, + /** + * @cfg {Boolean} preventMark + * true to disable displaying any {@link #setActiveError error message} set on this object. + */ + preventMark: false, + /** + * @cfg {Boolean} autoFitErrors + * Whether to adjust the component's body width to make room for 'side' + * {@link #msgTarget error messages}. + */ + autoFitErrors: true, + /** + * @cfg {String} msgTarget + * The location where the error message text should display. Must be one of the following values: + * + * - `qtip` Display a quick tip containing the message when the user hovers over the field. + * This is the default. + * + * **{@link Ext.tip.QuickTipManager#init} must have been called for this setting to work.** + * + * - `title` Display the message in a default browser title attribute popup. + * - `under` Add a block div beneath the field containing the error message. + * - `side` Add an error icon to the right of the field, displaying the message in a popup on hover. + * - `none` Don't display any error message. This might be useful if you are implementing custom error display. + * - `[element id]` Add the error message directly to the innerHTML of the specified element. + */ + msgTarget: 'qtip', + /** + * @private + * Map for msg target lookup, if target is not in this map it is assumed + * to be an element id + */ + msgTargets: { + qtip: 1, + title: 1, + under: 1, + side: 1, + none: 1 + }, + /** + * @cfg {String} activeError + * If specified, then the component will be displayed with this value as its active error when first rendered. Use + * {@link #setActiveError} or {@link #unsetActiveError} to change it after component creation. + */ + /** + * @private + * Tells the layout system that the height can be measured immediately because the width does not need setting. + */ + noWrap: true, + /** + * @cfg {String} [ariaHelp] Optional text description for this object. This text will be + * announced to Assistive Technology users when the object is focused. + * @locale + */ + ariaHelp: undefined, + /** + * @cfg {String} ariaErrorText Localized announcement text for validation errors. This text + * will be used by Assistive Technologies such as screen readers to alert the users when + * field validation fails. + * + * This config is used with {@link Ext.String.format}. '{0}' will be replaced with the actual + * error message(s), '{1}' will be replaced with field label. + * @locale + */ + ariaErrorText: 'Input error. {0}.', + labelableInsertions: [ + /** + * @cfg {String/Array/Ext.XTemplate} beforeBodyEl + * An optional string or `XTemplate` configuration to insert in the field markup + * at the beginning of the input containing element. If an `XTemplate` is used, the component's {@link Ext.Component#renderData render data} + * serves as the context. + */ + 'beforeBodyEl', + /** + * @cfg {String/Array/Ext.XTemplate} afterBodyEl + * An optional string or `XTemplate` configuration to insert in the field markup + * at the end of the input containing element. If an `XTemplate` is used, the component's {@link Ext.Component#renderData render data} + * serves as the context. + */ + 'afterBodyEl', + /** + * @cfg {String/Array/Ext.XTemplate} beforeLabelTpl + * An optional string or `XTemplate` configuration to insert in the field markup + * before the label element. If an `XTemplate` is used, the component's {@link Ext.Component#renderData render data} + * serves as the context. + */ + 'beforeLabelTpl', + /** + * @cfg {String/Array/Ext.XTemplate} afterLabelTpl + * An optional string or `XTemplate` configuration to insert in the field markup + * after the label element. If an `XTemplate` is used, the component's {@link Ext.Component#renderData render data} + * serves as the context. + */ + 'afterLabelTpl', + /** + * @cfg {String/Array/Ext.XTemplate} beforeSubTpl + * An optional string or `XTemplate` configuration to insert in the field markup + * before the {@link #getSubTplMarkup subTpl markup}. If an `XTemplate` is used, the + * component's {@link Ext.Component#renderData render data} serves as the context. + */ + 'beforeSubTpl', + /** + * @cfg {String/Array/Ext.XTemplate} afterSubTpl + * An optional string or `XTemplate` configuration to insert in the field markup + * after the {@link #getSubTplMarkup subTpl markup}. If an `XTemplate` is used, the + * component's {@link Ext.Component#renderData render data} serves as the context. + */ + 'afterSubTpl', + /** + * @cfg {String/Array/Ext.XTemplate} beforeLabelTextTpl + * An optional string or `XTemplate` configuration to insert in the field markup + * before the label text. If an `XTemplate` is used, the component's {@link Ext.Component#renderData render data} + * serves as the context. + */ + 'beforeLabelTextTpl', + /** + * @cfg {String/Array/Ext.XTemplate} afterLabelTextTpl + * An optional string or `XTemplate` configuration to insert in the field markup + * after the label text. If an `XTemplate` is used, the component's {@link Ext.Component#renderData render data} + * serves as the context. + */ + 'afterLabelTextTpl', + /** + * @cfg {String/Array/Ext.XTemplate} labelAttrTpl + * An optional string or `XTemplate` configuration to insert in the field markup + * inside the label element (as attributes). If an `XTemplate` is used, the component's + * {@link Ext.Component#renderData render data} serves as the context. + */ + 'labelAttrTpl' + ], + statics: { + /** + * Use a custom QuickTip instance separate from the main QuickTips singleton, so that we + * can give it a custom frame style. Responds to errorqtip rather than the qtip property. + * @static + * @private + */ + initTip: function() { + var tip = this.tip, + cfg, copy; + if (tip) { + return; + } + cfg = { + id: 'ext-form-error-tip', + // tell the spec runner to ignore this element when checking if the dom is clean + sticky: true, + ui: 'form-invalid' + }; + // On Touch devices, tapping the target shows the qtip + if (Ext.supports.Touch) { + cfg.dismissDelay = 0; + cfg.anchor = 'top'; + cfg.showDelay = 0; + cfg.showOnTap = true; + cfg.listeners = { + beforeshow: function() { + this.minWidth = Ext.fly(this.activeTarget.el).getWidth(); + } + }; + } + tip = this.tip = Ext.create('Ext.tip.QuickTip', cfg); + copy = Ext.apply({}, tip.tagConfig); + copy.attribute = 'errorqtip'; + tip.setTagConfig(copy); + }, + /** + * Destroy the error tip instance. + * @static + */ + destroyTip: function() { + this.tip = Ext.destroy(this.tip); + } + }, + /** + * @event errorchange + * Fires when the active error message is changed via {@link #setActiveError}. + * @param {Ext.form.Labelable} this + * @param {String} error The active error message + */ + /** + * Performs initialization of this mixin. Component classes using this mixin should call this method during their + * own initialization. + */ + initLabelable: function() { + var me = this, + padding = me.padding; + // This Component is rendered as a table. Padding doesn't work on tables + // Before padding can be applied to the encapsulating table element, copy the padding into + // an extraMargins property which is to be added to all computed margins post render :( + if (padding) { + me.padding = undefined; + me.extraMargins = Ext.Element.parseBox(padding); + } + // IE8 hack for https://sencha.jira.com/browse/EXTJS-17536. + // Need to force a relayout of the display:table form item. + // TODO: Remove when IE8 retires. + if (Ext.isIE8) { + me.restoreDisplay = Ext.Function.createDelayed(me.doRestoreDisplay, 0, me); + } + if (!me.activeErrorsTpl) { + if (me.msgTarget === 'title') { + me.activeErrorsTpl = me.plaintextActiveErrorsTpl; + } else { + me.activeErrorsTpl = me.htmlActiveErrorsTpl; + } + } + me.addCls([ + me.formItemCls, + me.formItemCls + '-' + me.ui + ]); + // Prevent first render of active error, at Field render time from signalling a change from undefined to " + me.lastActiveError = ''; + // bubbleEvents on the prototype of a mixin won't work, so call enableBubble + me.enableBubble('errorchange'); + }, + /** + * Returns the trimmed label by slicing off the label separator character. Can be overridden. + * @return {String} The trimmed field label, or empty string if not defined + */ + trimLabelSeparator: function() { + var me = this, + separator = me.labelSeparator, + label = me.fieldLabel || '', + lastChar = label.substr(label.length - 1); + // if the last char is the same as the label separator then slice it off otherwise just return label value + return lastChar === separator ? label.slice(0, -1) : label; + }, + /** + * Returns the label for the field. Defaults to simply returning the {@link #fieldLabel} config. Can be overridden + * to provide a custom generated label. + * @template + * @return {String} The configured field label, or empty string if not defined + */ + getFieldLabel: function() { + return this.trimLabelSeparator(); + }, + /** + * Set the label of this field. + * @param {String} label The new label. The {@link #labelSeparator} will be automatically appended to the label + * string. + */ + setFieldLabel: function(label) { + label = label || ''; + var me = this, + separator = me.labelSeparator, + labelEl = me.labelEl, + errorWrapEl = me.errorWrapEl, + sideLabel = (me.labelAlign !== 'top'), + noLabelCls = me.noLabelCls, + errorWrapUnderSideLabelCls = me.errorWrapUnderSideLabelCls; + me.fieldLabel = label; + if (me.rendered) { + if (Ext.isEmpty(label) && me.hideEmptyLabel) { + me.addCls(noLabelCls); + if (sideLabel && errorWrapEl) { + errorWrapEl.removeCls(errorWrapUnderSideLabelCls); + } + } else { + if (separator) { + label = me.trimLabelSeparator() + separator; + } + me.labelTextEl.dom.innerHTML = label; + me.removeCls(noLabelCls); + if (sideLabel && errorWrapEl) { + errorWrapEl.addCls(errorWrapUnderSideLabelCls); + } + } + me.updateLayout(); + } + }, + setHideLabel: function(hideLabel) { + var me = this; + if (hideLabel !== me.hideLabel) { + me.hideLabel = hideLabel; + if (me.rendered) { + me[hideLabel ? 'addCls' : 'removeCls'](me.noLabelCls); + me.updateLayout(); + } + } + }, + setHideEmptyLabel: function(hideEmptyLabel) { + var me = this, + hide; + if (hideEmptyLabel !== me.hideEmptyLabel) { + me.hideEmptyLabel = hideEmptyLabel; + if (me.rendered && !me.hideLabel) { + hide = hideEmptyLabel && !me.getFieldLabel(); + me[hide ? 'addCls' : 'removeCls'](me.noLabelCls); + me.updateLayout(); + } + } + }, + getInsertionRenderData: function(data, names) { + var i = names.length, + name, value; + while (i--) { + name = names[i]; + value = this[name]; + if (value) { + if (typeof value !== 'string') { + if (!value.isTemplate) { + value = Ext.XTemplate.getTpl(this, name); + } + value = value.apply(data); + } + } + data[name] = value || ''; + } + return data; + }, + /** + * Generates the arguments for the field decorations {@link #labelableRenderTpl + * rendering template}. + * @param {Object} data optional object to use as the base data object. If provided, + * this method will add properties to the base object instead of creating a new one. + * @return {Object} The template arguments + * @protected + */ + getLabelableRenderData: function() { + var me = this, + labelAlign = me.labelAlign, + topLabel = (labelAlign === 'top'), + rightLabel = (labelAlign === 'right'), + sideError = (me.msgTarget === 'side'), + underError = (me.msgTarget === 'under'), + errorMsgCls = me.errorMsgCls, + labelPad = me.labelPad, + labelWidth = me.labelWidth, + labelClsExtra = me.labelClsExtra || '', + errorWrapExtraCls = sideError ? me.errorWrapSideCls : me.errorWrapUnderCls, + labelStyle = '', + labelInnerStyle = '', + labelVisible = me.hasVisibleLabel(), + autoFitErrors = me.autoFitErrors, + defaultBodyWidth = me.defaultBodyWidth, + bodyStyle, data; + if (topLabel) { + labelClsExtra += ' ' + me.topLabelCls; + if (labelPad) { + labelInnerStyle = 'padding-bottom:' + labelPad + 'px;'; + } + if (sideError && !autoFitErrors) { + labelClsExtra += ' ' + me.topLabelSideErrorCls; + } + } else { + if (rightLabel) { + labelClsExtra += ' ' + me.rightLabelCls; + } + if (labelPad) { + labelStyle += me.getHorizontalPaddingStyle() + labelPad + 'px;'; + } + labelStyle += 'width:' + (labelWidth + (labelPad ? labelPad : 0)) + 'px;'; + // inner label needs width as well so that setting width on the outside + // that is smaller than the natural width, will be ensured to take width + // away from the body, and not the label. + labelInnerStyle = 'width:' + labelWidth + 'px'; + } + if (labelVisible) { + if (!topLabel && underError) { + errorWrapExtraCls += ' ' + me.errorWrapUnderSideLabelCls; + } + } + if (defaultBodyWidth) { + // This is here to support textfield's deprecated "size" config + bodyStyle = 'min-width:' + defaultBodyWidth + 'px;max-width:' + defaultBodyWidth + 'px;'; + } + data = { + id: me.id, + inputId: me.getInputId(), + labelCls: me.labelCls, + labelClsExtra: labelClsExtra, + labelStyle: labelStyle + (me.labelStyle || ''), + labelInnerStyle: labelInnerStyle, + labelInnerCls: me.labelInnerCls, + labelTextCls: me.labelTextCls, + skipLabelForAttribute: !!me.skipLabelForAttribute, + unselectableCls: Ext.Element.unselectableCls, + bodyStyle: bodyStyle, + baseBodyCls: me.baseBodyCls, + fieldBodyCls: me.fieldBodyCls, + extraFieldBodyCls: me.extraFieldBodyCls, + errorWrapCls: me.errorWrapCls, + errorWrapExtraCls: errorWrapExtraCls, + renderError: sideError || underError, + invalidMsgCls: sideError ? me.invalidIconCls : underError ? me.invalidUnderCls : '', + errorMsgCls: errorMsgCls, + growCls: me.grow ? me.growCls : '', + tipAnchorTarget: me.id + '-inputEl', + errorWrapStyle: (sideError && !autoFitErrors) ? 'visibility:hidden' : 'display:none', + fieldLabel: me.getFieldLabel(), + labelSeparator: me.labelSeparator, + renderAriaElements: !!me.renderAriaElements, + ariaStatus: '' + }; + if (me.ariaHelp) { + data.ariaHelp = Ext.String.htmlEncode(me.ariaHelp); + } + me.getInsertionRenderData(data, me.labelableInsertions); + return data; + }, + // hook for rtl + getHorizontalPaddingStyle: function() { + return 'padding-right:'; + }, + beforeLabelRender: function() { + var me = this; + me.setFieldDefaults(me.getInherited().fieldDefaults); + if (me.ownerLayout) { + me.addCls(Ext.baseCSSPrefix + me.ownerLayout.type + '-form-item'); + } + if (!me.hasVisibleLabel()) { + me.addCls(me.noLabelCls); + } + }, + onLabelRender: function() { + var me = this, + style = {}, + ExtElement = Ext.Element, + errorWrapEl = me.errorWrapEl, + margins, side; + if (errorWrapEl) { + errorWrapEl.setVisibilityMode((me.msgTarget === 'side' && !me.autoFitErrors) ? ExtElement.VISIBILITY : ExtElement.DISPLAY); + } + if (me.extraMargins) { + margins = me.el.getMargin(); + for (side in margins) { + if (margins.hasOwnProperty(side)) { + style['margin-' + side] = (margins[side] + me.extraMargins[side]) + 'px'; + } + } + me.el.setStyle(style); + } + }, + /** + * Checks if the field has a visible label + * @return {Boolean} True if the field has a visible label + */ + hasVisibleLabel: function() { + if (this.hideLabel) { + return false; + } + return !(this.hideEmptyLabel && !this.getFieldLabel()); + }, + /** + * Gets the markup to be inserted into the outer template's bodyEl. Defaults to empty string, should be implemented + * by classes including this mixin as needed. + * @return {String} The markup to be inserted + * @protected + */ + getSubTplMarkup: function() { + return ''; + }, + /** + * Get the input id, if any, for this component. This is used as the "for" attribute on the label element. + * Implementing subclasses may also use this as e.g. the id for their own input element. + * @return {String} The input id + */ + getInputId: function() { + return ''; + }, + /** + * Gets the active error message for this component, if any. This does not trigger validation on its own, it merely + * returns any message that the component may already hold. + * @return {String} The active error message on the component; if there is no error, an empty string is returned. + */ + getActiveError: function() { + return this.activeError || ''; + }, + /** + * Tells whether the field currently has an active error message. This does not trigger validation on its own, it + * merely looks for any message that the component may already hold. + * @return {Boolean} + */ + hasActiveError: function() { + return !!this.getActiveError(); + }, + /** + * Sets the active error message to the given string. This replaces the entire error message contents with the given + * string. Also see {@link #setActiveErrors} which accepts an Array of messages and formats them according to the + * {@link #activeErrorsTpl}. Note that this only updates the error message element's text and attributes, you'll + * have to call doComponentLayout to actually update the field's layout to match. If the field extends {@link + * Ext.form.field.Base} you should call {@link Ext.form.field.Base#markInvalid markInvalid} instead. + * @param {String} msg The error message + */ + setActiveError: function(msg) { + this.setActiveErrors(msg); + }, + /** + * Gets an Array of any active error messages currently applied to the field. This does not trigger validation on + * its own, it merely returns any messages that the component may already hold. + * @return {String[]} The active error messages on the component; if there are no errors, an empty Array is + * returned. + */ + getActiveErrors: function() { + return this.activeErrors || []; + }, + /** + * Set the active error message to an Array of error messages. The messages are formatted into a single message + * string using the {@link #activeErrorsTpl}. Also see {@link #setActiveError} which allows setting the entire error + * contents with a single string. Note that this only updates the error message element's text and attributes, + * you'll have to call doComponentLayout to actually update the field's layout to match. If the field extends + * {@link Ext.form.field.Base} you should call {@link Ext.form.field.Base#markInvalid markInvalid} instead. + * @param {String[]} errors The error messages + */ + setActiveErrors: function(errors) { + var me = this, + errorWrapEl = me.errorWrapEl, + msgTarget = me.msgTarget, + isSide = msgTarget === 'side', + isQtip = msgTarget === 'qtip', + ariaErrorEl = me.ariaErrorEl, + actionEl, activeError, tpl, targetEl, ariaTpl, errStr, errText; + errors = Ext.Array.from(errors); + tpl = me.lookupTpl('activeErrorsTpl'); + me.activeErrors = errors; + activeError = me.activeError = tpl.apply({ + fieldLabel: me.fieldLabel, + errors: errors, + listCls: Ext.baseCSSPrefix + 'list-plain' + }); + me.renderActiveError(); + if (me.rendered) { + actionEl = me.getActionEl(); + if (isSide) { + me.errorEl.dom.setAttribute('data-errorqtip', activeError); + } else if (isQtip) { + actionEl.dom.setAttribute('data-errorqtip', activeError); + } else if (msgTarget === 'title') { + actionEl.dom.setAttribute('title', activeError); + } + // If msgTarget is title, setting an alert is redundant for ARIA purposes + if (msgTarget !== 'title' && ariaErrorEl) { + ariaTpl = me.lookupTpl('ariaActiveErrorsTpl'); + errStr = ariaTpl.apply({ + errors: errors + }); + // Setting innerHTML on aria-live element will replace inner text node, + // and the browser will fire DOM change event even if the text is the same. + // We don't want the announcement to repeat if the text hasn't changed. + errText = Ext.String.formatEncode(me.ariaErrorText, errStr, me.fieldLabel); + if (ariaErrorEl.dom.innerHTML !== errText) { + ariaErrorEl.dom.innerHTML = errText; + } + // ariaStatusEl is not aria-live so it's OK to change it every time. + // Contents will be announced only upon focusing the field. + me.ariaStatusEl.dom.innerHTML = Ext.String.htmlEncode(errStr); + } + if (isSide || isQtip) { + Ext.form.Labelable.initTip(); + } + if (!me.msgTargets[msgTarget]) { + targetEl = Ext.get(msgTarget); + if (targetEl) { + targetEl.dom.innerHTML = activeError; + } + } + } + if (errorWrapEl) { + errorWrapEl.setVisible(errors.length > 0); + if (isSide && me.autoFitErrors) { + me.labelEl.addCls(me.topLabelSideErrorCls); + } + me.updateLayout(); + } + }, + /** + * Clears the active error message(s). Note that this only clears the error message element's text and attributes, + * you'll have to call doComponentLayout to actually update the field's layout to match. If the field extends {@link + * Ext.form.field.Base} you should call {@link Ext.form.field.Base#clearInvalid clearInvalid} instead. + */ + unsetActiveError: function() { + var me = this, + errorWrapEl = me.errorWrapEl, + ariaErrorEl = me.ariaErrorEl, + msgTarget = me.msgTarget, + restoreDisplay = me.restoreDisplay, + actionEl, targetEl; + if (me.hasActiveError()) { + delete me.activeError; + delete me.activeErrors; + me.renderActiveError(); + if (me.rendered) { + actionEl = me.getActionEl(); + if (msgTarget === 'qtip') { + actionEl.dom.removeAttribute('data-errorqtip'); + } else if (msgTarget === 'title') { + actionEl.dom.removeAttribute('title'); + } + if (msgTarget !== 'title' && ariaErrorEl) { + ariaErrorEl.dom.innerHTML = me.ariaStatusEl.dom.innerHTML = ''; + } + if (!me.msgTargets[msgTarget]) { + targetEl = Ext.get(msgTarget); + if (targetEl) { + targetEl.dom.innerHTML = ''; + } + } + if (errorWrapEl) { + errorWrapEl.hide(); + if (msgTarget === 'side' && me.autoFitErrors) { + me.labelEl.removeCls(me.topLabelSideErrorCls); + } + me.updateLayout(); + // IE8 hack for https://sencha.jira.com/browse/EXTJS-17536. + // Need to force a relayout of the display:table form item. + // TODO: Remove when IE8 retires. + if (restoreDisplay) { + me.el.dom.style.display = 'block'; + me.restoreDisplay(); + } + } + } + } + }, + doRestoreDisplay: function() { + // IE8 hack for https://sencha.jira.com/browse/EXTJS-17536. + // Need to force a relayout of the display:table form item. + // TODO: Remove this method when IE8 retires. + var el = this.el; + if (el && el.dom) { + el.dom.style.display = ''; + } + }, + /** + * @private + * Updates the rendered DOM to match the current activeError. This only updates the content and + * attributes, you'll have to call doComponentLayout to actually update the display. + */ + renderActiveError: function() { + var me = this, + activeError = me.getActiveError(), + hasError = !!activeError; + if (activeError !== me.lastActiveError) { + me.lastActiveError = activeError; + me.fireEvent('errorchange', me, activeError); + } + if (me.rendered && !me.destroyed && !me.preventMark) { + me.toggleInvalidCls(hasError); + // Update the errorEl (There will only be one if msgTarget is 'side' or 'under') with the error message text + if (me.errorEl) { + me.errorEl.dom.innerHTML = activeError; + } + } + }, + /** + * @private + * Add/remove invalid class(es) + * @param {Boolean} hasError + */ + toggleInvalidCls: function(hasError) { + this.el[hasError ? 'addCls' : 'removeCls'](this.invalidCls); + }, + /** + * Applies a set of default configuration values to this Labelable instance. For each of the properties in the given + * object, check if this component hasOwnProperty that config; if not then it's inheriting a default value from its + * prototype and we should apply the default value. + * @param {Object} defaults The defaults to apply to the object. + */ + setFieldDefaults: function(defaults) { + var key; + for (key in defaults) { + if (!this.hasOwnProperty(key)) { + this[key] = defaults[key]; + } + } + } +}, function() { + if (Ext.supports.Touch) { + this.prototype.msgTarget = 'side'; + } +}); + +/** + * This mixin provides a common interface for the logical behavior and state of form fields, including: + * + * - Getter and setter methods for field values + * - Events and methods for tracking value and validity changes + * - Methods for triggering validation + * + * **NOTE**: When implementing custom fields, it is most likely that you will want to extend the {@link Ext.form.field.Base} + * component class rather than using this mixin directly, as BaseField contains additional logic for generating an + * actual DOM complete with {@link Ext.form.Labelable label and error message} display and a form input field, + * plus methods that bind the Field value getters and setters to the input field's value. + * + * If you do want to implement this mixin directly and don't want to extend {@link Ext.form.field.Base}, then + * you will most likely want to override the following methods with custom implementations: {@link #getValue}, + * {@link #setValue}, and {@link #getErrors}. Other methods may be overridden as needed but their base + * implementations should be sufficient for common cases. You will also need to make sure that {@link #initField} + * is called during the component's initialization. + */ +Ext.define('Ext.form.field.Field', { + mixinId: 'field', + /** + * @property {Boolean} isFormField + * Flag denoting that this component is a Field. Always true. + */ + isFormField: true, + config: { + /** + * @cfg {Boolean/String} validation + * This property, when a `String`, contributes its value to the error state of this + * instance as reported by `getErrors`. + */ + validation: null, + /** + * @cfg {Ext.data.Field} validationField + * When binding is used with a model, this maps to the underlying {@link Ext.data.field.Field} if + * it is available. This can be used to validate the value against the model field without needing + * to push the value back into the model. + * + * @private + */ + validationField: null + }, + /** + * @cfg {Object} value + * A value to initialize this field with. + */ + /** + * @cfg {String} name + * The name of the field. By default this is used as the parameter name when including the + * {@link #getSubmitData field value} in a {@link Ext.form.Basic#submit form submit()}. To prevent the field from + * being included in the form submit, set {@link #submitValue} to false. + */ + /** + * @cfg {Boolean} disabled + * True to disable the field. Disabled Fields will not be {@link Ext.form.Basic#submit submitted}. + */ + disabled: false, + /** + * @cfg {Boolean} submitValue + * Setting this to false will prevent the field from being {@link Ext.form.Basic#submit submitted} even when it is + * not disabled. + */ + submitValue: true, + /** + * @cfg {Boolean} validateOnChange + * Specifies whether this field should be validated immediately whenever a change in its value is detected. + * If the validation results in a change in the field's validity, a {@link #validitychange} event will be + * fired. This allows the field to show feedback about the validity of its contents immediately as the user is + * typing. + * + * When set to false, feedback will not be immediate. However the form will still be validated before submitting if + * the clientValidation option to {@link Ext.form.Basic#doAction} is enabled, or if the field or form are validated + * manually. + * + * See also {@link Ext.form.field.Base#checkChangeEvents} for controlling how changes to the field's value are + * detected. + */ + validateOnChange: true, + /** + * @cfg {String[]/String} valuePublishEvent + * The event name(s) to use to publish the {@link #value} + * {@link Ext.form.field.Base#bind} for this field. + * @since 5.0.1 + */ + valuePublishEvent: 'change', + /** + * @private + */ + suspendCheckChange: 0, + /** + * @property {Boolean} dirty + * The dirty state of the field. + * @private + */ + dirty: false, + /** + * @event change + * Fires when the value of a field is changed. The value of a field is + * checked for changes when the field's {@link #setValue} method + * is called and when any of the events listed in + * {@link Ext.form.field.Base#checkChangeEvents checkChangeEvents} are fired. + * @param {Ext.form.field.Field} this + * @param {Object} newValue The new value + * @param {Object} oldValue The original value + */ + /** + * @event validitychange + * Fires when a change in the field's validity is detected. + * @param {Ext.form.field.Field} this + * @param {Boolean} isValid Whether or not the field is now valid + */ + /** + * @event dirtychange + * Fires when a change in the field's {@link #isDirty} state is detected. + * @param {Ext.form.field.Field} this + * @param {Boolean} isDirty Whether or not the field is now dirty + */ + /** + * Initializes this Field mixin on the current instance. Components using this mixin should call this method during + * their own initialization process. + */ + initField: function() { + var me = this, + valuePublishEvent = me.valuePublishEvent, + len, i; + me.initValue(); + var badNames = [ + 'tagName', + 'nodeName', + 'children', + 'childNodes' + ], + name = this.name; + if (name && Ext.Array.indexOf(badNames, name) > -1) { + Ext.log.warn([ + 'It is recommended to not use "', + name, + '" as a field name, because it ', + 'can cause naming collisions during form submission.' + ].join('')); + } + // Vast majority of cases won't be an array + if (Ext.isString(valuePublishEvent)) { + me.on(valuePublishEvent, me.publishValue, me); + } else { + for (i = 0 , len = valuePublishEvent.length; i < len; ++i) { + me.on(valuePublishEvent[i], me.publishValue, me); + } + } + }, + /** + * Initializes the field's value based on the initial config. + */ + initValue: function() { + var me = this; + // Set the initial value if we have one. + // Prevent validation on initial set. + if ('value' in me) { + me.suspendCheckChange++; + me.setValue(me.value); + me.suspendCheckChange--; + } + /** + * @property {Object} originalValue + * The original value of the field as configured in the {@link #value} configuration, or as loaded by the last + * form load operation if the form's {@link Ext.form.Basic#trackResetOnLoad trackResetOnLoad} setting is `true`. + */ + me.initialValue = me.originalValue = me.lastValue = me.getValue(); + }, + /** + * Cleans up values initialized by this Field mixin on the current instance. + * Components using this mixin should call this method before being destroyed. + */ + cleanupField: function() { + delete this._ownerRecord; + }, + // Fields can be editors, and some editors may not have a name property that maps + // to its data index, so it's necessary in these cases to look it up by its dataIndex + // property. See EXTJSIV-11650. + getFieldIdentifier: function() { + return this.isEditorComponent ? this.dataIndex : this.name; + }, + /** + * Returns the {@link Ext.form.field.Field#name name} attribute of the field. This is used as the parameter name + * when including the field value in a {@link Ext.form.Basic#submit form submit()}. + * @return {String} name The field {@link Ext.form.field.Field#name name} + */ + getName: function() { + return this.name; + }, + /** + * Returns the current data value of the field. The type of value returned is particular to the type of the + * particular field (e.g. a Date object for {@link Ext.form.field.Date}). + * @return {Object} value The field value + */ + getValue: function() { + return this.value; + }, + /** + * Sets a data value into the field and runs the change detection and validation. + * @param {Object} value The value to set + * @return {Ext.form.field.Field} this + */ + setValue: function(value) { + var me = this; + me.value = value; + me.checkChange(); + return me; + }, + /** + * Returns whether two field {@link #getValue values} are logically equal. Field implementations may override this + * to provide custom comparison logic appropriate for the particular field's data type. + * @param {Object} value1 The first value to compare + * @param {Object} value2 The second value to compare + * @return {Boolean} True if the values are equal, false if inequal. + */ + isEqual: function(value1, value2) { + return String(value1) === String(value2); + }, + /** + * Returns whether two values are logically equal. + * Similar to {@link #isEqual}, however null or undefined values will be treated as empty strings. + * @private + * @param {Object} value1 The first value to compare + * @param {Object} value2 The second value to compare + * @return {Boolean} True if the values are equal, false if inequal. + */ + isEqualAsString: function(value1, value2) { + return String(Ext.valueFrom(value1, '')) === String(Ext.valueFrom(value2, '')); + }, + /** + * Returns the parameter(s) that would be included in a standard form submit for this field. Typically this will be + * an object with a single name-value pair, the name being this field's {@link #method-getName name} and the value being + * its current stringified value. More advanced field implementations may return more than one name-value pair. + * + * Note that the values returned from this method are not guaranteed to have been successfully {@link #validate + * validated}. + * + * @return {Object} A mapping of submit parameter names to values; each value should be a string, or an array of + * strings if that particular name has multiple values. It can also return null if there are no parameters to be + * submitted. + */ + getSubmitData: function() { + var me = this, + data = null; + if (!me.disabled && me.submitValue) { + data = {}; + data[me.getName()] = '' + me.getValue(); + } + return data; + }, + /** + * Returns the value(s) that should be saved to the {@link Ext.data.Model} instance for this field, when {@link + * Ext.form.Basic#updateRecord} is called. Typically this will be an object with a single name-value pair, the name + * being this field's {@link #method-getName name} and the value being its current data value. More advanced field + * implementations may return more than one name-value pair. The returned values will be saved to the corresponding + * field names in the Model. + * + * Note that the values returned from this method are not guaranteed to have been successfully {@link #validate + * validated}. + * + * @param {Boolean} includeEmptyText Whether or not to include empty text + * @param isSubmitting (private) + * @return {Object} A mapping of submit parameter names to values; each value should be a string, or an array of + * strings if that particular name has multiple values. It can also return null if there are no parameters to be + * submitted. + */ + getModelData: function(includeEmptyText, isSubmitting) { + var me = this, + data = null; + // Note that we need to check if this operation is being called from a Submit action because displayfields aren't + // to be submitted, but they can call this to get their model data. + if (!me.disabled && (me.submitValue || !isSubmitting)) { + data = {}; + data[me.getFieldIdentifier()] = me.getValue(); + } + return data; + }, + /** + * Resets the current field value to the originally loaded value and clears any validation messages. See {@link + * Ext.form.Basic}.{@link Ext.form.Basic#trackResetOnLoad trackResetOnLoad} + */ + reset: function() { + var me = this; + me.beforeReset(); + me.setValue(me.originalValue); + me.clearInvalid(); + // delete here so we reset back to the original state + delete me.wasValid; + }, + /** + * @method + * Template method before a field is reset. + * @protected + */ + beforeReset: Ext.emptyFn, + /** + * Resets the field's {@link #originalValue} property so it matches the current {@link #getValue value}. This is + * called by {@link Ext.form.Basic}.{@link Ext.form.Basic#setValues setValues} if the form's + * {@link Ext.form.Basic#trackResetOnLoad trackResetOnLoad} property is set to true. + */ + resetOriginalValue: function() { + this.originalValue = this.getValue(); + this.checkDirty(); + }, + /** + * Checks whether the value of the field has changed since the last time it was checked. + * If the value has changed, it: + * + * 1. Fires the {@link #change change event}, + * 2. Performs validation if the {@link #validateOnChange} config is enabled, firing the + * {@link #validitychange validitychange event} if the validity has changed, and + * 3. Checks the {@link #isDirty dirty state} of the field and fires the {@link #dirtychange dirtychange event} + * if it has changed. + */ + checkChange: function() { + var me = this, + newVal, oldVal; + if (!me.suspendCheckChange && !me.destroying && !me.destroyed) { + newVal = me.getValue(); + oldVal = me.lastValue; + if (me.didValueChange(newVal, oldVal)) { + me.lastValue = newVal; + me.fireEvent('change', me, newVal, oldVal); + me.onChange(newVal, oldVal); + } + } + }, + /** + * @private + * Checks if the value has changed. Allows subclasses to override for + * any more complex logic. + */ + didValueChange: function(newVal, oldVal) { + return !this.isEqual(newVal, oldVal); + }, + /** + * @private + * Called when the field's value changes. Performs validation if the {@link #validateOnChange} + * config is enabled, and invokes the dirty check. + */ + onChange: function(newVal) { + var me = this; + if (me.validateOnChange) { + me.validate(); + } + me.checkDirty(); + }, + /** + * Publish the value of this field. + * + * @private + */ + publishValue: function() { + var me = this; + if (me.rendered && !me.getErrors().length) { + me.publishState('value', me.getValue()); + } + }, + /** + * @cfg [publishes='value'] + * @inheritdoc Ext.mixin.Bindable#cfg-publishes + */ + /** + * Returns true if the value of this Field has been changed from its {@link #originalValue}. + * Will always return false if the field is disabled. + * + * Note that if the owning {@link Ext.form.Basic form} was configured with + * {@link Ext.form.Basic#trackResetOnLoad trackResetOnLoad} then the {@link #originalValue} is updated when + * the values are loaded by {@link Ext.form.Basic}.{@link Ext.form.Basic#setValues setValues}. + * @return {Boolean} True if this field has been changed from its original value (and is not disabled), + * false otherwise. + */ + isDirty: function() { + var me = this; + return !me.disabled && !me.isEqual(me.getValue(), me.originalValue); + }, + /** + * Checks the {@link #isDirty} state of the field and if it has changed since the last time it was checked, + * fires the {@link #dirtychange} event. + */ + checkDirty: function() { + var me = this, + isDirty = me.isDirty(); + if (isDirty !== me.wasDirty) { + me.dirty = isDirty; + me.fireEvent('dirtychange', me, isDirty); + me.onDirtyChange(isDirty); + me.wasDirty = isDirty; + } + }, + /** + * @method + * @private + * Called when the field's dirty state changes. + * @param {Boolean} isDirty + */ + onDirtyChange: Ext.emptyFn, + /** + * Runs this field's validators and returns an array of error messages for any validation failures. This is called + * internally during validation and would not usually need to be used manually. + * + * Each subclass should override or augment the return value to provide their own errors. + * + * @param {Object} value The value to get errors for (defaults to the current field value) + * @return {String[]} All error messages for this field; an empty Array if none. + */ + getErrors: function(value) { + var errors = [], + validationField = this.getValidationField(), + validation = this.getValidation(), + result; + if (validationField) { + result = validationField.validate(value, null, null, this._ownerRecord); + if (result !== true) { + errors.push(result); + } + } + if (validation && validation !== true) { + errors.push(validation); + } + return errors; + }, + /** + * Returns whether or not the field value is currently valid by {@link #getErrors validating} the field's current + * value. The {@link #validitychange} event will not be fired; use {@link #validate} instead if you want the event + * to fire. **Note**: {@link #disabled} fields are always treated as valid. + * + * Implementations are encouraged to ensure that this method does not have side-effects such as triggering error + * message display. + * + * @return {Boolean} True if the value is valid, else false + */ + isValid: function() { + var me = this; + return me.disabled || Ext.isEmpty(me.getErrors()); + }, + /** + * Returns whether or not the field value is currently valid by {@link #getErrors validating} the field's current + * value, and fires the {@link #validitychange} event if the field's validity has changed since the last validation. + * **Note**: {@link #disabled} fields are always treated as valid. + * + * Custom implementations of this method are allowed to have side-effects such as triggering error message display. + * To validate without side-effects, use {@link #isValid}. + * + * @return {Boolean} True if the value is valid, else false + */ + validate: function() { + return this.checkValidityChange(this.isValid()); + }, + checkValidityChange: function(isValid) { + var me = this; + if (isValid !== me.wasValid) { + me.wasValid = isValid; + me.fireEvent('validitychange', me, isValid); + } + return isValid; + }, + /** + * @private + */ + setValidationField: function(value, record) { + this.callParent([ + value + ]); + this._ownerRecord = record; + }, + /** + * A utility for grouping a set of modifications which may trigger value changes into a single transaction, to + * prevent excessive firing of {@link #change} events. This is useful for instance if the field has sub-fields which + * are being updated as a group; you don't want the container field to check its own changed state for each subfield + * change. + * @param {Function} fn The function to call with change checks suspended. + */ + batchChanges: function(fn) { + try { + this.suspendCheckChange++; + fn(); + } finally { + this.suspendCheckChange--; + } + this.checkChange(); + }, + /** + * Returns whether this Field is a file upload field; if it returns true, forms will use special techniques for + * {@link Ext.form.Basic#submit submitting the form} via AJAX. See {@link Ext.form.Basic#hasUpload} for details. If + * this returns true, the {@link #extractFileInput} method must also be implemented to return the corresponding file + * input element. + * @return {Boolean} + */ + isFileUpload: function() { + return false; + }, + /** + * Only relevant if the instance's {@link #isFileUpload} method returns true. Returns a reference to the file input + * DOM element holding the user's selected file. The input will be appended into the submission form and will not be + * returned, so this method should also create a replacement. + * @return {HTMLElement} + */ + extractFileInput: function() { + return null; + }, + /** + * @method + * Display one or more error messages associated with this field, using + * {@link Ext.form.Labelable#msgTarget} to determine how to display the messages and + * applying {@link Ext.form.Labelable#invalidCls} to the field's UI element. + * + * var formPanel = Ext.create('Ext.form.Panel', { + * title: 'Contact Info', + * width: 300, + * bodyPadding: 10, + * renderTo: Ext.getBody(), + * items: [{ + * xtype: 'textfield', + * name: 'name', + * id: 'nameId', + * fieldLabel: 'Name' + * }], + * bbar: [{ + * text: 'Mark both fields invalid', + * handler: function() { + * var nameField = formPanel.getForm().findField('name'); + * nameField.markInvalid('Name invalid message'); + * + * // multiple error string syntax + * // nameField.markInvalid(['First message', 'Second message']); + * } + * }] + * }); + * + * **Note**: this method does not cause the Field's {@link #validate} or + * {@link #isValid} methods to return `false` if the value does _pass_ validation. + * So simply marking a Field as invalid will not prevent submission of forms + * submitted with the {@link Ext.form.action.Submit#clientValidation} option set. + * + * @param {String/String[]} errors The validation message(s) to display. + */ + markInvalid: Ext.emptyFn, + /** + * @method clearInvalid + * Clear any invalid styles/messages for this field. Components using this mixin should implement this method to + * update the components rendering to clear any existing messages. + * + * **Note**: this method does not cause the Field's {@link #validate} or {@link #isValid} methods to return `true` + * if the value does not _pass_ validation. So simply clearing a field's errors will not necessarily allow + * submission of forms submitted with the {@link Ext.form.action.Submit#clientValidation} option set. + */ + clearInvalid: Ext.emptyFn, + updateValidation: function(validation, oldValidation) { + // Only validate if the validation is changing, not when we initial set it, + // otherwise it will mark the field invalid as soon as it is bound. + if (oldValidation) { + this.validate(); + } + }, + privates: { + resetToInitialValue: function() { + var me = this, + originalValue = me.originalValue; + me.originalValue = me.initialValue; + me.reset(); + me.originalValue = originalValue; + } + } +}); + +/** + * Base class for form fields that provides default event handling, rendering, and other common functionality + * needed by all form field types. Utilizes the {@link Ext.form.field.Field} mixin for value handling and validation, + * and the {@link Ext.form.Labelable} mixin to provide label and error message display. + * + * In most cases you will want to use a subclass, such as {@link Ext.form.field.Text} or {@link Ext.form.field.Checkbox}, + * rather than creating instances of this class directly. However if you are implementing a custom form field, + * using this as the parent class is recommended. + * + * # Values and Conversions + * + * Because Base implements the Field mixin, it has a main value that can be initialized with the + * {@link #value} config and manipulated via the {@link #getValue} and {@link #setValue} methods. This main + * value can be one of many data types appropriate to the current field, for instance a {@link Ext.form.field.Date Date} + * field would use a JavaScript Date object as its value type. However, because the field is rendered as a HTML + * input, this value data type can not always be directly used in the rendered field. + * + * Therefore Base introduces the concept of a "raw value". This is the value of the rendered HTML input field, + * and is normally a String. The {@link #getRawValue} and {@link #setRawValue} methods can be used to directly + * work with the raw value, though it is recommended to use getValue and setValue in most cases. + * + * Conversion back and forth between the main value and the raw value is handled by the {@link #valueToRaw} and + * {@link #rawToValue} methods. If you are implementing a subclass that uses a non-String value data type, you + * should override these methods to handle the conversion. + * + * # Rendering + * + * The content of the field body is defined by the {@link #fieldSubTpl} XTemplate, with its argument data + * created by the {@link #getSubTplData} method. Override this template and/or method to create custom + * field renderings. + */ +Ext.define('Ext.form.field.Base', { + extend: 'Ext.Component', + mixins: [ + 'Ext.form.Labelable', + 'Ext.form.field.Field' + ], + xtype: 'field', + alternateClassName: [ + 'Ext.form.Field', + 'Ext.form.BaseField' + ], + requires: [ + 'Ext.util.DelayedTask', + 'Ext.XTemplate' + ], + /** + * @property focusable + * @inheritdoc + */ + focusable: true, + /** + * @cfg shrinkWrap + * @inheritdoc + */ + shrinkWrap: true, + /** + * @cfg {Ext.XTemplate} fieldSubTpl + * The content of the field body is defined by this config option. + * @private + */ + fieldSubTpl: [ + // note: {id} here is really {inputId}, but {cmpId} is available + ' name="{name}"', + ' value="{[Ext.util.Format.htmlEncode(values.value)]}"', + ' placeholder="{placeholder}"', + '{%if (values.maxLength !== undefined){%} maxlength="{maxLength}"{%}%}', + ' readonly="readonly"', + ' disabled="disabled"', + ' tabindex="{tabIdx}"', + ' style="{fieldStyle}"', + '', + ' {$}="{.}"', + '', + ' {$}="{.}"', + ' class="{fieldCls} {typeCls} {typeCls}-{ui} {editableCls} {inputCls} {fixCls}" autocomplete="off"/>', + { + disableFormats: true + } + ], + /** + * @property defaultBindProperty + * @inheritdoc + */ + defaultBindProperty: 'value', + /** + * @cfg autoEl + * @inheritdoc + */ + autoEl: { + role: 'presentation' + }, + subTplInsertions: [ + /** + * @cfg {String/Array/Ext.XTemplate} inputAttrTpl + * An optional string or `XTemplate` configuration to insert in the field markup + * inside the input element (as attributes). If an `XTemplate` is used, the component's + * {@link #getSubTplData subTpl data} serves as the context. + */ + 'inputAttrTpl' + ], + /** + * @cfg childEls + * @inheritdoc + */ + childEls: [ + /** + * @property {Ext.dom.Element} inputEl + * The input Element for this Field. Only available after the field has been rendered. + */ + 'inputEl' + ], + /** + * @cfg {String} name + * The name of the field. This is used as the parameter name when including the field value + * in a {@link Ext.form.Basic#submit form submit()}. If no name is configured, it falls back to the {@link #inputId}. + * To prevent the field from being included in the form submit, set {@link #submitValue} to false. + */ + /** + * @cfg {String} inputType + * The type attribute for input fields -- e.g. radio, text, password, file. The extended types + * supported by HTML5 inputs (url, email, etc.) may also be used, though using them will cause older browsers to + * fall back to 'text'. + * + * The type 'password' must be used to render that field type currently -- there is no separate Ext component for + * that. You can use {@link Ext.form.field.File} which creates a custom-rendered file upload field, but if you want + * a plain unstyled file input you can use a Base with inputType:'file'. + */ + inputType: 'text', + /** + * @cfg {Boolean} isTextInput + * `true` if this field renders as a text input. + * + * @private + * @since 5.0.1 + */ + isTextInput: true, + /** + * @cfg {Number} tabIndex + * + * Sets a DOM tabIndex for this field. tabIndex may be set to `-1` in order to remove + * the field from the tab rotation. + * + * **Note:** tabIndex only applies to fields that are rendered. It does not effect + * fields built via applyTo + */ + /** + * @cfg {String} invalidText + * The error text to use when marking a field invalid and no message is provided + * @locale + */ + invalidText: 'The value in this field is invalid', + /** + * @cfg {String} fieldCls + * The default CSS class for the field input + */ + fieldCls: Ext.baseCSSPrefix + 'form-field', + /** + * @cfg {String} fieldStyle + * Optional CSS style(s) to be applied to the {@link #inputEl field input element}. Should be a valid argument to + * {@link Ext.dom.Element#applyStyles}. Defaults to undefined. See also the {@link #setFieldStyle} method for changing + * the style after initialization. + */ + /** + * @cfg [publishes=['rawValue', 'value', 'dirty']] + * @inheritdoc + */ + /** + * @cfg {String} focusCls + * The CSS class to use when the field receives focus + */ + focusCls: 'form-focus', + /** + * @cfg {String} dirtyCls + * The CSS class to use when the field value {@link #isDirty is dirty}. + */ + dirtyCls: Ext.baseCSSPrefix + 'form-dirty', + /** + * @cfg {String[]} checkChangeEvents + * A list of event names that will be listened for on the field's {@link #inputEl input element}, which will cause + * the field's value to be checked for changes. If a change is detected, the {@link #change change event} will be + * fired, followed by validation if the {@link #validateOnChange} option is enabled. + * + * Defaults to ['change', 'propertychange', 'keyup'] in Internet Explorer, and ['change', 'input', 'textInput', 'keyup', + * 'dragdrop'] in other browsers. This catches all the ways that field values can be changed in most supported + * browsers; the only known exceptions at the time of writing are: + * + * - Safari 3.2 and older: cut/paste in textareas via the context menu, and dragging text into textareas + * - Opera 10 and 11: dragging text into text fields and textareas, and cut via the context menu in text fields + * and textareas + * - Opera 9: Same as Opera 10 and 11, plus paste from context menu in text fields and textareas + * + * If you need to guarantee on-the-fly change notifications including these edge cases, you can call the + * {@link #checkChange} method on a repeating interval, e.g. using {@link Ext.TaskManager}, or if the field is within + * a {@link Ext.form.Panel}, you can use the FormPanel's {@link Ext.form.Panel#pollForChanges} configuration to set up + * such a task automatically. + */ + checkChangeEvents: Ext.isIE && (!document.documentMode || document.documentMode <= 9) ? [ + 'change', + 'propertychange', + 'keyup' + ] : [ + 'change', + 'input', + 'textInput', + 'keyup', + 'dragdrop' + ], + // While input is supported in IE9, we use attachEvent for events, so we need to fall back here + ignoreChangeRe: /data\-errorqtip|style\.|className/, + /** + * @cfg {Number} checkChangeBuffer + * Defines a timeout in milliseconds for buffering {@link #cfg!checkChangeEvents} that fire in rapid succession. + * Defaults to 50 milliseconds. + */ + checkChangeBuffer: 50, + /** + * @cfg liquidLayout + * @inheritdoc + */ + liquidLayout: true, + /** + * @cfg {Boolean} readOnly + * true to mark the field as readOnly in HTML. + */ + readOnly: false, + /** + * @cfg {String} readOnlyCls + * The CSS class applied to the component's main element when it is {@link #readOnly}. + */ + readOnlyCls: Ext.baseCSSPrefix + 'form-readonly', + /** + * @cfg {String} inputId + * The id that will be given to the generated input DOM element. Defaults to an automatically generated id. If you + * configure this manually, you must make sure it is unique in the document. + */ + /** + * @cfg {Boolean} [validateOnBlur=true] + * Whether the field should validate when it loses focus. This will cause fields to be validated + * as the user steps through the fields in the form regardless of whether they are making changes to those fields + * along the way. See also {@link #validateOnChange}. + */ + validateOnBlur: true, + /** + * @cfg {Boolean} [validateOnFocusLeave=false] Set to `true` to validate the field + * when focus leaves the field's component hierarchy entirely. + * + * The difference between {@link #validateOnBlur} and this option is that the former + * will happen when field's _input element_ blurs. In complex fields such as ComboBox + * or Date focus may leave the input element to the drop-down picker, which will cause + * {@link #validateOnBlur} to happen prematurely. + * + * Using this option is recommended for accessible applications. The default value + * is `false` for backwards compatibility; this option and {@link #validateOnBlur} + * are mutually exclusive. + * + * @since 6.5.3 + */ + validateOnFocusLeave: false, + /** + * @cfg {String} formatText + * Helpful text describing acceptable format for field values. This text will be + * announced by Assistive Technologies such as screen readers when the field is + * focused. + * + * This option is superseded by {@link #ariaHelp}. + * + * @deprecated 6.2.0 This config is deprecated. + * @locale + */ + /** + * @private + */ + hasFocus: false, + /** + * @cfg baseCls + * @inheritdoc + */ + baseCls: Ext.baseCSSPrefix + 'field', + /** + * @cfg fieldBodyCls + * @inheritdoc + */ + fieldBodyCls: Ext.baseCSSPrefix + 'field-body', + webkitBorderBoxBugCls: Ext.baseCSSPrefix + 'webkit-border-box-bug', + /** + * @property maskOnDisable + * @inheritdoc + */ + maskOnDisable: false, + // Instructs the layout to stretch the inputEl to 100% width when laying + // out under fixed conditions. Defaults to true for all fields except check/radio + // Doesn't seem worth it to introduce a whole new layout class just for this flag + stretchInputElFixed: true, + // Form fields render their ARIA attributes to the inputEl + /** + * @property ariaEl + * @inheritdoc + */ + ariaEl: 'inputEl', + /** + * @property focusEl + * @inheritdoc + */ + focusEl: 'inputEl', + renderAriaElements: true, + /** + * @event specialkey + * Fires when any key related to navigation (arrows, tab, enter, esc, etc.) is pressed. To handle other keys + * see {@link Ext.util.KeyMap}. You can check {@link Ext.event.Event#getKey} to determine which key was + * pressed. For example: + * + * var form = new Ext.form.Panel({ + * ... + * items: [{ + * fieldLabel: 'Field 1', + * name: 'field1', + * allowBlank: false + * },{ + * fieldLabel: 'Field 2', + * name: 'field2', + * listeners: { + * specialkey: function(field, e){ + * // e.HOME, e.END, e.PAGE_UP, e.PAGE_DOWN, + * // e.TAB, e.ESC, arrow keys: e.LEFT, e.RIGHT, e.UP, e.DOWN + * if (e.getKey() == e.ENTER) { + * var form = field.up('form').getForm(); + * form.submit(); + * } + * } + * } + * } + * ], + * ... + * }); + * + * @param {Ext.form.field.Base} this + * @param {Ext.event.Event} e The event object + */ + /** + * @event writeablechange + * Fires when this field changes its read-only status. + * @param {Ext.form.field.Base} this + * @param {Boolean} Read only flag + */ + initComponent: function() { + var me = this; + me.callParent(); + me.subTplData = me.subTplData || {}; + // Init mixins + me.initLabelable(); + me.initField(); + me.initDefaultName(); + // validateOnBlur and validateOnFocusLeave are mutually exclusive, + // with latter taking precedence + if (me.validateOnFocusLeave) { + me.validateOnBlur = false; + } + // Add to protoEl before render + if (me.readOnly) { + me.addCls(me.readOnlyCls); + } + me.addCls(Ext.baseCSSPrefix + 'form-type-' + me.inputType); + // formatText is superseded by ariaHelp but we still apply it for compatibility + if (me.format && me.formatText && !me.ariaHelp) { + me.ariaHelp = Ext.String.format(me.formatText, me.format); + } + }, + /** + * @private + */ + initDefaultName: function() { + var me = this; + // Default name to inputId + if (!me.name) { + me.name = me.getInputId(); + } + }, + /** + * Returns the input id for this field. If none was specified via the {@link #inputId} config, then an id will be + * automatically generated. + */ + getInputId: function() { + return this.inputId || (this.inputId = this.id + '-inputEl'); + }, + /** + * Creates and returns the data object to be used when rendering the {@link #fieldSubTpl}. + * @return {Object} The template data + * @template + */ + getSubTplData: function(fieldData) { + var me = this, + id = me.id, + type = me.inputType, + inputId = me.getInputId(), + inputCls = me.inputCls || '', + fixCls = '', + data, ariaAttr, inputElAttr; + if (Ext.supports.WebKitInputTableBoxModelBug) { + // workaround for https://bugs.webkit.org/show_bug.cgi?id=137693 + // Can't use inputCls or typeCls here since they will be appended + // with ui in different subclasses which breaks things. + fixCls += me.webkitBorderBoxBugCls; + } + data = Ext.apply({ + ui: me.ui, + id: inputId, + cmpId: id, + name: me.name || inputId, + disabled: me.disabled, + readOnly: me.readOnly, + value: me.getRawValue(), + type: type, + fieldCls: me.fieldCls, + fieldStyle: me.getFieldStyle(), + childElCls: fieldData.childElCls, + tabIdx: me.tabIndex, + inputCls: inputCls, + typeCls: Ext.baseCSSPrefix + 'form-' + (me.isTextInput ? 'text' : type), + fixCls: fixCls, + ariaEl: me.ariaEl + }, me.subTplData); + if (me.ariaRole) { + ariaAttr = {}; + if (!me.ariaStaticRoles[me.ariaRole]) { + // When ARIA attributes are rendered they should always reflect + // component's state. This contrasts with the standard HTML attributes + // like disabled and readonly, which are only present when enabled. + ariaAttr['aria-hidden'] = !!me.hidden; + ariaAttr['aria-disabled'] = !!me.disabled; + // For most of the fields ariaEl === inputEl but certain types like Combo boxes + // and their descendants are compound widgets and need to have ARIA attributes + // on different elements. + inputElAttr = { + // Input fields start out as valid + 'aria-invalid': false, + 'aria-readonly': !!me.readOnly + }; + // aria-label is not present by default, and aria-labelledby + // generally should not be used for fields' inputEls since usually + // they are referenced by their respective